I'm announcing the release of the 6.1.75 kernel.
All users of the 6.1 kernel series must upgrade.
The updated 6.1.y git tree can be found at: git://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable.git linux-6.1.y and can be browsed at the normal kernel.org git web browser: https://git.kernel.org/?p=linux/kernel/git/stable/linux-stable.git%3Ba=summa...
thanks,
greg k-h
------------
Documentation/devicetree/bindings/gpio/xlnx,gpio-xilinx.yaml | 2 Documentation/devicetree/bindings/media/mediatek,mdp3-rdma.yaml | 29 - Documentation/devicetree/bindings/media/mediatek,mdp3-wrot.yaml | 23 Documentation/devicetree/bindings/media/rockchip-isp1.yaml | 11 Documentation/driver-api/pci/p2pdma.rst | 16 Makefile | 2 arch/arm/boot/dts/qcom-apq8064.dtsi | 2 arch/arm/boot/dts/qcom-sdx65.dtsi | 2 arch/arm/boot/dts/stm32mp157a-dk1-scmi.dts | 2 arch/arm/boot/dts/stm32mp157c-dk2-scmi.dts | 2 arch/arm/boot/dts/stm32mp157c-ed1-scmi.dts | 2 arch/arm/boot/dts/stm32mp157c-ev1-scmi.dts | 3 arch/arm/mach-davinci/Kconfig | 2 arch/arm64/boot/dts/freescale/imx8mm.dtsi | 4 arch/arm64/boot/dts/hisilicon/hikey970-pmic.dtsi | 3 arch/arm64/boot/dts/marvell/armada-3720-turris-mox.dts | 2 arch/arm64/boot/dts/mediatek/mt8183.dtsi | 6 arch/arm64/boot/dts/qcom/ipq6018.dtsi | 73 +- arch/arm64/boot/dts/qcom/qrb5165-rb5.dts | 2 arch/arm64/boot/dts/qcom/sc7180.dtsi | 2 arch/arm64/boot/dts/qcom/sc7280-chrome-common.dtsi | 24 arch/arm64/boot/dts/qcom/sc7280.dtsi | 20 arch/arm64/boot/dts/qcom/sc8280xp.dtsi | 2 arch/arm64/boot/dts/qcom/sdm845-db845c.dts | 2 arch/arm64/boot/dts/qcom/sdm845.dtsi | 2 arch/arm64/boot/dts/qcom/sm6350.dtsi | 2 arch/arm64/boot/dts/qcom/sm8150-hdk.dts | 12 arch/arm64/boot/dts/qcom/sm8150.dtsi | 2 arch/arm64/boot/dts/qcom/sm8250.dtsi | 2 arch/arm64/boot/dts/qcom/sm8350.dtsi | 4 arch/arm64/boot/dts/renesas/r8a779g0-white-hawk-cpu.dtsi | 3 arch/arm64/boot/dts/ti/k3-am62a-main.dtsi | 4 arch/arm64/boot/dts/ti/k3-am65-main.dtsi | 2 arch/arm64/kvm/vgic/vgic-its.c | 5 arch/arm64/kvm/vgic/vgic-mmio-v3.c | 27 arch/csky/include/asm/jump_label.h | 5 arch/loongarch/include/asm/elf.h | 5 arch/loongarch/kernel/elf.c | 5 arch/loongarch/kernel/process.c | 1 arch/loongarch/net/bpf_jit.c | 5 arch/mips/alchemy/devboards/db1200.c | 2 arch/mips/alchemy/devboards/db1550.c | 2 arch/mips/include/asm/dmi.h | 2 arch/mips/kernel/setup.c | 4 arch/mips/kernel/smp.c | 4 arch/powerpc/Kconfig | 1 arch/powerpc/Makefile | 17 arch/powerpc/lib/Makefile | 4 arch/powerpc/perf/imc-pmu.c | 6 arch/powerpc/platforms/44x/Kconfig | 1 arch/powerpc/platforms/powernv/opal-irqchip.c | 2 arch/powerpc/platforms/powernv/opal-powercap.c | 6 arch/powerpc/platforms/powernv/opal-xscom.c | 5 arch/powerpc/platforms/pseries/hotplug-memory.c | 9 arch/riscv/include/asm/sections.h | 1 arch/riscv/include/asm/xip_fixup.h | 2 arch/riscv/kernel/module.c | 3 arch/riscv/kernel/patch.c | 11 arch/riscv/kernel/vmlinux-xip.lds.S | 2 arch/riscv/kernel/vmlinux.lds.S | 2 arch/riscv/mm/pageattr.c | 275 ++++++++-- arch/s390/include/asm/pci_io.h | 32 - arch/s390/pci/pci_mmio.c | 12 arch/x86/kernel/cpu/mce/inject.c | 1 arch/x86/kernel/kvmclock.c | 12 arch/x86/lib/misc.c | 2 block/bio.c | 38 - block/blk-mq.c | 16 block/blk-settings.c | 2 block/genhd.c | 5 block/ioctl.c | 11 crypto/af_alg.c | 14 crypto/scompress.c | 6 drivers/acpi/acpi_extlog.c | 7 drivers/acpi/acpi_lpit.c | 2 drivers/acpi/acpi_lpss.c | 3 drivers/acpi/acpi_video.c | 12 drivers/acpi/property.c | 4 drivers/android/binder_alloc.c | 22 drivers/base/node.c | 9 drivers/base/swnode.c | 3 drivers/block/loop.c | 52 - drivers/block/null_blk/main.c | 13 drivers/bluetooth/btmtkuart.c | 11 drivers/clk/clk-si5341.c | 4 drivers/clk/qcom/gpucc-sm8150.c | 4 drivers/clk/qcom/videocc-sm8150.c | 5 drivers/clk/renesas/rzg2l-cpg.c | 91 ++- drivers/clk/zynqmp/clk-mux-zynqmp.c | 2 drivers/clk/zynqmp/divider.c | 66 -- drivers/clocksource/timer-ti-dm.c | 4 drivers/cpufreq/cpufreq-dt-platdev.c | 2 drivers/cpufreq/imx-cpufreq-dt.c | 2 drivers/cpufreq/imx6q-cpufreq.c | 4 drivers/cpufreq/scmi-cpufreq.c | 7 drivers/cpufreq/tegra20-cpufreq.c | 2 drivers/crypto/ccp/ccp-ops.c | 5 drivers/crypto/hisilicon/hpre/hpre_main.c | 122 ++-- drivers/crypto/hisilicon/qm.c | 98 +++ drivers/crypto/hisilicon/sec2/sec.h | 7 drivers/crypto/hisilicon/sec2/sec_crypto.c | 13 drivers/crypto/hisilicon/sec2/sec_main.c | 70 +- drivers/crypto/hisilicon/zip/zip_main.c | 175 ++++-- drivers/crypto/inside-secure/safexcel_cipher.c | 19 drivers/crypto/sa2ul.c | 3 drivers/crypto/sahara.c | 248 +++------ drivers/crypto/virtio/virtio_crypto_common.h | 2 drivers/crypto/virtio/virtio_crypto_core.c | 26 drivers/cxl/core/port.c | 2 drivers/cxl/core/region.c | 2 drivers/edac/thunderx_edac.c | 10 drivers/firmware/meson/meson_sm.c | 5 drivers/firmware/ti_sci.c | 10 drivers/gpu/drm/amd/amdgpu/amdgpu_debugfs.c | 4 drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c | 2 drivers/gpu/drm/amd/amdkfd/kfd_migrate.c | 7 drivers/gpu/drm/amd/amdkfd/kfd_topology.c | 21 drivers/gpu/drm/amd/pm/legacy-dpm/kv_dpm.c | 4 drivers/gpu/drm/amd/pm/legacy-dpm/legacy_dpm.c | 52 - drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c | 5 drivers/gpu/drm/amd/pm/powerplay/hwmgr/smu7_hwmgr.c | 6 drivers/gpu/drm/bridge/cadence/cdns-mhdp8546-hdcp.c | 3 drivers/gpu/drm/bridge/tc358767.c | 2 drivers/gpu/drm/bridge/ti-tpd12s015.c | 4 drivers/gpu/drm/drm_drv.c | 10 drivers/gpu/drm/mediatek/mtk_disp_merge.c | 2 drivers/gpu/drm/mediatek/mtk_dp.c | 1 drivers/gpu/drm/mediatek/mtk_mdp_rdma.c | 3 drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c | 4 drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c | 4 drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.c | 6 drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.h | 4 drivers/gpu/drm/msm/disp/dpu1/dpu_hw_lm.c | 6 drivers/gpu/drm/msm/disp/dpu1/dpu_hw_lm.h | 3 drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.c | 20 drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.h | 8 drivers/gpu/drm/msm/disp/mdp4/mdp4_crtc.c | 9 drivers/gpu/drm/msm/dsi/phy/dsi_phy.c | 4 drivers/gpu/drm/nouveau/nv04_fence.c | 2 drivers/gpu/drm/omapdrm/omap_drv.c | 9 drivers/gpu/drm/panel/panel-elida-kd35t133.c | 2 drivers/gpu/drm/panel/panel-sitronix-st7701.c | 2 drivers/gpu/drm/panfrost/panfrost_gpu.c | 70 +- drivers/gpu/drm/radeon/r100.c | 4 drivers/gpu/drm/radeon/r600_cs.c | 4 drivers/gpu/drm/radeon/radeon_display.c | 7 drivers/gpu/drm/radeon/radeon_vm.c | 8 drivers/gpu/drm/radeon/si.c | 4 drivers/gpu/drm/radeon/sumo_dpm.c | 4 drivers/gpu/drm/radeon/trinity_dpm.c | 4 drivers/gpu/drm/tidss/tidss_dispc.c | 63 ++ drivers/gpu/drm/tidss/tidss_kms.c | 4 drivers/gpu/drm/tilcdc/tilcdc_drv.c | 2 drivers/gpu/drm/vmwgfx/vmwgfx_bo.c | 7 drivers/gpu/drm/vmwgfx/vmwgfx_cotable.c | 8 drivers/gpu/drm/vmwgfx/vmwgfx_drv.h | 20 drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c | 12 drivers/gpu/drm/vmwgfx/vmwgfx_gem.c | 24 drivers/gpu/drm/vmwgfx/vmwgfx_kms.c | 10 drivers/gpu/drm/vmwgfx/vmwgfx_overlay.c | 3 drivers/gpu/drm/vmwgfx/vmwgfx_resource.c | 18 drivers/gpu/drm/vmwgfx/vmwgfx_shader.c | 5 drivers/gpu/drm/vmwgfx/vmwgfx_surface.c | 27 drivers/hid/wacom_wac.c | 32 - drivers/i2c/busses/i2c-s3c2410.c | 40 - drivers/iio/adc/ad7091r-base.c | 6 drivers/iio/adc/ad9467.c | 105 ++- drivers/iio/adc/adi-axi-adc.c | 74 -- drivers/infiniband/hw/hns/hns_roce_hw_v2.c | 6 drivers/infiniband/hw/hns/hns_roce_pd.c | 2 drivers/infiniband/hw/mthca/mthca_cmd.c | 4 drivers/infiniband/hw/mthca/mthca_main.c | 2 drivers/infiniband/ulp/iser/iscsi_iser.h | 2 drivers/infiniband/ulp/iser/iser_initiator.c | 5 drivers/infiniband/ulp/iser/iser_memory.c | 8 drivers/infiniband/ulp/iser/iser_verbs.c | 1 drivers/input/keyboard/atkbd.c | 12 drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c | 1 drivers/iommu/dma-iommu.c | 3 drivers/leds/Kconfig | 1 drivers/md/md.c | 22 drivers/md/raid1.c | 12 drivers/md/raid5.c | 12 drivers/media/dvb-core/dvbdev.c | 2 drivers/media/dvb-frontends/m88ds3103.c | 7 drivers/media/platform/mediatek/jpeg/mtk_jpeg_core.c | 1 drivers/media/platform/mediatek/jpeg/mtk_jpeg_dec_hw.c | 6 drivers/media/platform/nxp/imx-mipi-csis.c | 4 drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 6 drivers/media/platform/verisilicon/hantro_drv.c | 2 drivers/media/platform/verisilicon/hantro_v4l2.c | 3 drivers/media/usb/cx231xx/cx231xx-core.c | 2 drivers/media/usb/pvrusb2/pvrusb2-context.c | 3 drivers/mfd/intel-lpss.c | 2 drivers/mfd/syscon.c | 4 drivers/misc/habanalabs/common/habanalabs_ioctl.c | 2 drivers/mmc/host/Kconfig | 10 drivers/mtd/mtd_blkdevs.c | 4 drivers/mtd/nand/raw/fsl_ifc_nand.c | 2 drivers/net/amt.c | 6 drivers/net/dsa/vitesse-vsc73xx-core.c | 2 drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_main.c | 26 drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_rx.c | 6 drivers/net/ethernet/mellanox/mlxsw/spectrum_acl_erp.c | 8 drivers/net/ethernet/qualcomm/rmnet/rmnet_config.c | 2 drivers/net/ethernet/renesas/ravb_main.c | 2 drivers/net/ethernet/stmicro/stmmac/stmmac.h | 1 drivers/net/ethernet/stmicro/stmmac/stmmac_ethtool.c | 10 drivers/net/ethernet/stmicro/stmmac/stmmac_main.c | 1 drivers/net/ethernet/ti/am65-cpsw-nuss.c | 5 drivers/net/phy/micrel.c | 1 drivers/net/wireless/ath/ath11k/ahb.c | 4 drivers/net/wireless/intel/iwlwifi/mvm/phy-ctxt.c | 11 drivers/net/wireless/intel/iwlwifi/mvm/tx.c | 2 drivers/net/wireless/marvell/libertas/Kconfig | 2 drivers/net/wireless/marvell/mwifiex/cfg80211.c | 2 drivers/net/wireless/marvell/mwifiex/fw.h | 1 drivers/net/wireless/marvell/mwifiex/ioctl.h | 1 drivers/net/wireless/marvell/mwifiex/uap_cmd.c | 8 drivers/net/wireless/mediatek/mt76/eeprom.c | 2 drivers/net/wireless/mediatek/mt76/mt76.h | 3 drivers/net/wireless/mediatek/mt76/mt7615/sdio.c | 2 drivers/net/wireless/mediatek/mt76/mt7921/mcu.c | 11 drivers/net/wireless/mediatek/mt76/mt7921/sdio.c | 4 drivers/net/wireless/mediatek/mt76/mt7921/sdio_mac.c | 3 drivers/net/wireless/mediatek/mt76/sdio.c | 18 drivers/net/wireless/purelifi/plfxlc/usb.c | 5 drivers/net/wireless/realtek/rtlwifi/pci.c | 79 -- drivers/net/wireless/realtek/rtlwifi/pci.h | 5 drivers/net/wireless/realtek/rtlwifi/rtl8188ee/phy.c | 14 drivers/net/wireless/realtek/rtlwifi/rtl8192c/phy_common.c | 12 drivers/net/wireless/realtek/rtlwifi/rtl8192c/phy_common.h | 1 drivers/net/wireless/realtek/rtlwifi/rtl8192ce/phy.c | 6 drivers/net/wireless/realtek/rtlwifi/rtl8192ce/phy.h | 1 drivers/net/wireless/realtek/rtlwifi/rtl8192cu/phy.c | 6 drivers/net/wireless/realtek/rtlwifi/rtl8192de/phy.c | 15 drivers/net/wireless/realtek/rtlwifi/rtl8192ee/phy.c | 16 drivers/net/wireless/realtek/rtlwifi/rtl8192se/phy.c | 15 drivers/net/wireless/realtek/rtlwifi/rtl8821ae/phy.c | 5 drivers/net/wireless/realtek/rtlwifi/wifi.h | 7 drivers/net/wireless/realtek/rtw88/mac80211.c | 4 drivers/net/xen-netback/netback.c | 44 + drivers/nvme/target/tcp.c | 20 drivers/nvme/target/trace.h | 5 drivers/of/base.c | 1 drivers/of/unittest-data/tests-phandle.dtsi | 10 drivers/of/unittest.c | 74 +- drivers/pci/controller/dwc/pci-keystone.c | 9 drivers/pci/controller/dwc/pcie-designware-ep.c | 1 drivers/pci/controller/pcie-mediatek-gen3.c | 85 +-- drivers/pci/controller/pcie-mediatek.c | 10 drivers/platform/x86/intel/vsec.c | 46 + drivers/platform/x86/intel/vsec.h | 7 drivers/power/supply/bq256xx_charger.c | 5 drivers/power/supply/cw2015_battery.c | 2 drivers/pwm/core.c | 2 drivers/pwm/pwm-jz4740.c | 7 drivers/pwm/pwm-stm32.c | 63 +- drivers/scsi/fnic/fnic_debugfs.c | 3 drivers/scsi/hisi_sas/hisi_sas_main.c | 4 drivers/scsi/hisi_sas/hisi_sas_v3_hw.c | 9 drivers/scsi/mpi3mr/mpi3mr_app.c | 16 drivers/scsi/mpi3mr/mpi3mr_os.c | 10 drivers/soc/qcom/llcc-qcom.c | 8 drivers/spi/Kconfig | 3 drivers/spi/spi-sh-msiof.c | 17 drivers/spmi/spmi-mtk-pmif.c | 20 drivers/staging/media/rkvdec/rkvdec.c | 3 drivers/target/target_core_file.c | 10 drivers/tty/serial/8250/8250_bcm2835aux.c | 2 drivers/tty/serial/8250/8250_exar.c | 5 drivers/tty/serial/8250/8250_omap.c | 2 drivers/tty/serial/imx.c | 36 - drivers/tty/serial/omap-serial.c | 27 drivers/tty/serial/sc16is7xx.c | 8 drivers/tty/serial/serial_core.c | 33 - drivers/tty/tty.h | 2 drivers/tty/tty_io.c | 35 - drivers/tty/tty_ioctl.c | 2 drivers/ufs/core/ufshcd.c | 7 drivers/usb/cdns3/cdns3-gadget.c | 142 +++-- drivers/usb/cdns3/cdns3-gadget.h | 3 drivers/usb/chipidea/core.c | 7 drivers/usb/class/cdc-acm.c | 3 drivers/usb/dwc3/core.c | 39 - drivers/usb/dwc3/ep0.c | 5 drivers/usb/host/xhci-mtk.c | 40 + drivers/usb/host/xhci-mtk.h | 2 drivers/usb/mon/mon_bin.c | 7 drivers/usb/phy/phy-mxs-usb.c | 3 drivers/usb/typec/class.c | 4 drivers/vdpa/alibaba/eni_vdpa.c | 6 drivers/video/fbdev/core/fb_defio.c | 8 drivers/video/fbdev/imxfb.c | 27 drivers/watchdog/bcm2835_wdt.c | 3 drivers/watchdog/hpwdt.c | 2 drivers/watchdog/rti_wdt.c | 13 drivers/watchdog/watchdog_dev.c | 3 fs/efivarfs/super.c | 15 fs/erofs/zdata.c | 5 fs/f2fs/data.c | 7 fs/f2fs/file.c | 7 fs/f2fs/namei.c | 2 fs/f2fs/node.c | 6 fs/f2fs/xattr.c | 11 fs/gfs2/rgrp.c | 2 fs/namespace.c | 11 fs/nfs/blocklayout/blocklayout.c | 7 fs/nfs/direct.c | 5 fs/nfs/internal.h | 2 fs/nfs/nfs4proc.c | 3 fs/nfs/pnfs.c | 3 fs/pstore/ram_core.c | 2 fs/smb/server/asn1.c | 5 fs/smb/server/connection.c | 6 fs/smb/server/connection.h | 2 fs/smb/server/oplock.c | 6 fs/smb/server/smb2pdu.c | 22 fs/smb/server/smb_common.c | 6 fs/smb/server/transport_rdma.c | 11 fs/smb/server/transport_tcp.c | 13 include/crypto/if_alg.h | 3 include/drm/drm_bridge.h | 2 include/dt-bindings/clock/qcom,videocc-sm8150.h | 4 include/linux/bio.h | 9 include/linux/blkdev.h | 3 include/linux/bpf.h | 43 + include/linux/clk-provider.h | 4 include/linux/hisi_acc_qm.h | 20 include/linux/iio/adc/adi-axi-adc.h | 4 include/linux/netfilter_bridge.h | 6 include/linux/of.h | 17 include/linux/rcupdate.h | 12 include/linux/skbuff.h | 2 include/net/bluetooth/hci_core.h | 1 include/uapi/linux/bpf.h | 3 init/do_mounts.c | 9 io_uring/rw.c | 10 kernel/bpf/arraymap.c | 12 kernel/bpf/hashtab.c | 6 kernel/bpf/lpm_trie.c | 3 kernel/bpf/map_in_map.c | 13 kernel/bpf/map_in_map.h | 2 kernel/bpf/stackmap.c | 11 kernel/bpf/syscall.c | 41 + kernel/bpf/verifier.c | 27 kernel/debug/kdb/kdb_main.c | 2 kernel/dma/coherent.c | 4 kernel/rcu/tasks.h | 2 kernel/time/tick-sched.c | 5 lib/kunit/debugfs.c | 4 net/bluetooth/hci_conn.c | 8 net/bluetooth/hci_debugfs.c | 12 net/bluetooth/hci_event.c | 11 net/bridge/br_netfilter_hooks.c | 42 + net/bridge/br_netfilter_ipv6.c | 14 net/core/rtnetlink.c | 14 net/dns_resolver/dns_key.c | 2 net/ethtool/features.c | 9 net/ipv4/af_inet.c | 1 net/ipv4/ipmr.c | 13 net/ipv4/netfilter/nf_reject_ipv4.c | 9 net/ipv4/udp.c | 12 net/ipv6/ip6_tunnel.c | 26 net/ipv6/mcast.c | 4 net/ipv6/netfilter/nf_reject_ipv6.c | 11 net/ipv6/udp.c | 16 net/mptcp/options.c | 6 net/mptcp/subflow.c | 17 net/ncsi/internal.h | 7 net/ncsi/ncsi-netlink.c | 4 net/ncsi/ncsi-pkt.h | 7 net/ncsi/ncsi-rsp.c | 26 net/netfilter/ipset/ip_set_hash_netiface.c | 8 net/netfilter/ipvs/ip_vs_xmit.c | 4 net/netfilter/nf_log_syslog.c | 13 net/netfilter/nf_queue.c | 6 net/netfilter/nf_tables_api.c | 27 net/netfilter/nfnetlink_log.c | 8 net/netfilter/nft_limit.c | 19 net/netfilter/xt_physdev.c | 2 net/netlabel/netlabel_calipso.c | 49 - net/sched/act_ct.c | 12 net/sctp/socket.c | 13 net/sunrpc/xprtmultipath.c | 2 net/unix/unix_bpf.c | 21 net/vmw_vsock/virtio_transport_common.c | 13 scripts/Makefile.compiler | 4 security/apparmor/policy_unpack.c | 4 security/selinux/hooks.c | 7 sound/pci/hda/patch_realtek.c | 3 sound/pci/oxygen/oxygen_mixer.c | 2 sound/soc/codecs/cs35l33.c | 4 sound/soc/codecs/cs35l34.c | 4 sound/soc/codecs/rt5645.c | 8 sound/soc/intel/common/soc-acpi-intel-glk-match.c | 14 sound/soc/mediatek/common/mtk-dsp-sof-common.c | 2 sound/usb/mixer_scarlett_gen2.c | 223 +++++--- tools/include/uapi/linux/bpf.h | 3 tools/lib/api/io.h | 1 tools/perf/util/bpf-event.c | 8 tools/perf/util/bpf-event.h | 12 tools/perf/util/env.c | 50 + tools/perf/util/env.h | 4 tools/perf/util/genelf.c | 6 tools/perf/util/header.c | 13 tools/perf/util/hisi-ptt.c | 1 tools/testing/selftests/alsa/mixer-test.c | 4 tools/testing/selftests/bpf/prog_tests/bpf_iter.c | 2 tools/testing/selftests/bpf/prog_tests/time_tai.c | 2 tools/testing/selftests/bpf/progs/bpf_iter_task_stack.c | 5 tools/testing/selftests/bpf/progs/xdp_synproxy_kern.c | 4 tools/testing/selftests/drivers/net/mlxsw/qos_pfc.sh | 18 tools/testing/selftests/drivers/net/mlxsw/spectrum-2/tc_flower.sh | 52 + tools/testing/selftests/net/arp_ndisc_untracked_subnets.sh | 2 tools/testing/selftests/net/fib_nexthop_multiprefix.sh | 4 tools/testing/selftests/powerpc/math/fpu_preempt.c | 9 tools/testing/selftests/powerpc/math/vmx_preempt.c | 10 tools/testing/selftests/sgx/Makefile | 2 tools/testing/selftests/sgx/load.c | 9 tools/testing/selftests/sgx/sigstruct.c | 5 tools/testing/selftests/sgx/test_encl.c | 8 422 files changed, 3531 insertions(+), 2105 deletions(-)
Abhinav Singh (1): drm/nouveau/fence:: fix warning directly dereferencing a rcu pointer
Adam Ford (1): arm64: dts: imx8mm: Reduce GPU to nominal speed
Ahmad Fatoum (1): ARM: dts: stm32: don't mix SCMI and non-SCMI board compatibles
Alex Deucher (1): drm/amdgpu/debugfs: fix error code when smc register accessors are NULL
Alexandra Diupina (1): cpufreq: scmi: process the result of devm_of_clk_add_hw_provider()
Alexandre Ghiti (5): riscv: Check if the code to patch lies in the exit section riscv: Fix module_alloc() that did not reset the linear mapping permissions riscv: Fix set_memory_XX() and set_direct_map_XX() by splitting huge linear mappings riscv: Fix set_direct_map_default_noflush() to reset _PAGE_EXEC riscv: Fix wrong usage of lm_alias() when splitting a huge linear mapping
Amir Goldstein (1): scsi: target: core: add missing file_{start,end}_write()
Amit Cohen (2): mlxsw: spectrum_acl_erp: Fix error flow of pool allocation failure selftests: mlxsw: qos_pfc: Adjust the test to support 8 lanes
Amit Kumar Mahapatra (1): spi: spi-zynqmp-gqspi: fix driver kconfig dependencies
Andrei Matei (1): bpf: Fix verification of indirect var-off stack access
Andrii Nakryiko (2): bpf: enforce precision of R0 on callback return bpf: fix check for attempt to corrupt spilled pointer
Andy Shevchenko (2): ACPI: LPSS: Fix the fractional clock divider flags mfd: intel-lpss: Fix the fractional clock divider flags
AngeloGioacchino Del Regno (3): drm/panfrost: Really power off GPU cores in panfrost_gpu_power_off() drm/panfrost: Ignore core_mask for poweroff and disable PWRTRANS irq ASoC: mediatek: sof-common: Add NULL check for normal_link string
Anton Protopopov (1): bpf: add percpu stats for bpf_map elements insertions/deletions
Ard Biesheuvel (1): efivarfs: Free s_fs_info on unmount
Arnaldo Carvalho de Melo (1): libapi: Add missing linux/types.h header to get the __u64 type on io.h
Arnd Bergmann (6): EDAC/thunderx: Fix possible out-of-bounds string access csky: fix arch_jump_label_transform_static override wifi: libertas: stop selecting wext ARM: davinci: always select CONFIG_CPU_ARM926T nvmet: re-fix tracing strncpy() warning nvme: trace: avoid memcpy overflow warning
Arseniy Krasnov (1): virtio/vsock: fix logic which reduces credit update messages
Artem Chernyshev (1): scsi: fnic: Return error if vmalloc() failed
Asmaa Mnebhi (2): mlxbf_gige: Fix intermittent no ip issue mlxbf_gige: Enable the GigE port in mlxbf_gige_open
Atul Dhudase (1): soc: qcom: llcc: Fix dis_cap_alloc and retain_on_pc configuration
Bart Van Assche (2): scsi: ufs: core: Simplify power management during async scan md/raid1: Use blk_opf_t for read and write operations
Benjamin Coddington (1): blocklayoutdriver: Fix reference leak of pnfs_device_node
Bin Li (1): ALSA: hda/realtek: Enable headset mic on Lenovo M70 Gen5
Brent Lu (1): ASoC: Intel: glk_rt5682_max98357a: fix board id mismatch
Carlos Llamas (3): binder: fix async space check for 0-sized buffers binder: fix unused alloc->free_async_space binder: fix race between mmput() and do_exit()
Chandrakanth patil (2): scsi: mpi3mr: Refresh sdev queue depth after controller reset scsi: mpi3mr: Block PEL Enable Command on Controller Reset and Unrecoverable State
Chao Yu (4): f2fs: fix to avoid dirent corruption f2fs: fix to wait on block writeback for post_read case f2fs: fix to check compress file in f2fs_move_file_range() f2fs: fix to update iostat correctly in f2fs_filemap_fault()
Chen Ni (2): KEYS: encrypted: Add check for strsep crypto: sa2ul - Return crypto_aead_setkey to transfer the error
Chengchang Tang (1): RDMA/hns: Fix memory leak in free_mr_init()
Chenghai Huang (1): crypto: hisilicon/zip - add zip comp high perf mode configuration
Chengming Zhou (1): crypto: scomp - fix req->dst buffer overflow
Chih-Kang Chang (1): wifi: rtw88: fix RX filter in FIF_ALLMULTI flag
Chris Morgan (2): drm/panel-elida-kd35t133: hold panel in reset for unprepare drm/panel: st7701: Fix AVCL calculation
Christian A. Ehrhardt (1): of: Fix double free in of_parse_phandle_with_args_map
Christian Brauner (1): fs: indicate request originates from old mount API
Christian Marangi (2): arm64: dts: qcom: ipq6018: improve pcie phy pcs reg table wifi: mt76: fix broken precal loading from MTD for mt7915
Christoph Hellwig (2): null_blk: don't cap max_hw_sectors to BLK_DEF_MAX_SECTORS loop: fix the the direct I/O support check when used on top of block devices
Christoph Niedermaier (2): serial: imx: Ensure that imx_uart_rs485_config() is called with enabled clock serial: imx: Correct clock error message in function probe()
Christophe JAILLET (6): firmware: ti_sci: Fix an off-by-one in ti_sci_debugfs_create() media: dvb-frontends: m88ds3103: Fix a memory leak in an error handling path of m88ds3103_probe() MIPS: Alchemy: Fix an out-of-bound access in db1200_dev_setup() MIPS: Alchemy: Fix an out-of-bound access in db1550_dev_setup() vdpa: Fix an error handling path in eni_vdpa_probe() kdb: Fix a potential buffer overflow in kdb_local()
Chukun Pan (1): arm64: dts: qcom: ipq6018: fix clock rates for GCC_USB0_MOCK_UTMI_CLK
Chunfeng Yun (1): usb: xhci-mtk: fix a short packet issue of gen1 isoc-in transfer
Claudiu Beznea (3): clk: renesas: rzg2l-cpg: Reuse code in rzg2l_cpg_reset() clk: renesas: rzg2l: Check reset monitor registers net: phy: micrel: populate .soft_reset for KSZ9131
Colin Ian King (1): x86/lib: Fix overflow when counting digits
Curtis Klein (1): watchdog: set cdev owner before adding
Dafna Hirschfeld (1): drm/amdkfd: fixes for HMM mem allocation
Dan Carpenter (2): wifi: plfxlc: check for allocation failure in plfxlc_usb_wreq_async() media: dvbdev: drop refcount on error path in dvb_device_open()
Dang Huynh (1): leds: aw2013: Select missing dependency REGMAP_I2C
Dario Binacchi (2): drm/bridge: Fix typo in post_disable() description fbdev: imxfb: fix left margin setting
David E. Box (1): platform/x86/intel/vsec: Fix xa_alloc memory leak
David Howells (1): keys, dns: Fix size check of V1 server-list header
David Lin (1): wifi: mwifiex: configure BSSID consistently when starting AP
Deepak R Varma (1): drm/amdkfd: Use resource_size() helper function
Dinghao Liu (1): crypto: ccp - fix memleak in ccp_init_dm_workarea
Dmitry Baryshkov (4): ARM: dts: qcom: apq8064: correct XOADC register address arm64: dts: qcom: sm8150-hdk: fix SS USB regulators drm/msm/mdp4: flush vblank event on disable drm/drv: propagate errors from drm_modeset_register_all()
Dmitry Rokosov (1): firmware: meson_sm: populate platform devices from sm device tree data
Douglas Anderson (7): arm64: dts: qcom: sc7180: Make watchdog bark interrupt edge triggered arm64: dts: qcom: sc7280: Make watchdog bark interrupt edge triggered arm64: dts: qcom: sdm845: Make watchdog bark interrupt edge triggered arm64: dts: qcom: sm8150: Make watchdog bark interrupt edge triggered arm64: dts: qcom: sm8250: Make watchdog bark interrupt edge triggered arm64: dts: qcom: sc8280xp: Make watchdog bark interrupt edge triggered arm64: dts: qcom: sm6350: Make watchdog bark interrupt edge triggered
Eric Dumazet (9): sctp: support MSG_ERRQUEUE flag in recvmsg() sctp: fix busy polling ip6_tunnel: fix NEXTHDR_FRAGMENT handling in ip6_tnl_parse_tlv_enc_lim() mptcp: mptcp_parse_option() fix for MPTCPOPT_MP_JOIN mptcp: strict validation before using mp_opt->hmac mptcp: use OPTION_MPTCP_MPJ_SYNACK in subflow_finish_connect() mptcp: use OPTION_MPTCP_MPJ_SYN in subflow_check_req() mptcp: refine opt_mp_capable determination udp: annotate data-races around up->pending
Fedor Pchelkin (2): apparmor: avoid crash when parsed profile name is empty ipvs: avoid stat macros calls from preemptible context
Florian Lehner (1): bpf, lpm: Fix check prefixlen before walking trie
Florian Westphal (1): netfilter: nf_tables: mark newset as dead on transaction abort
Francesco Dolcini (1): Bluetooth: btmtkuart: fix recv_buf() return value
Frank Li (3): usb: cdns3: fix uvc failure work since sg support enabled usb: cdns3: fix iso transfer error when mult is not zero usb: cdns3: Fix uvc fail when DMA cross 4k boundery since sg enabled
Frederik Haxel (1): riscv: Fixed wrong register in XIP_FIXUP_FLASH_OFFSET macro
Gao Xiang (1): erofs: fix memory leak on short-lived bounced pages
Gavrilov Ilia (1): calipso: fix memory leak in netlbl_calipso_add_pass()
Geert Uytterhoeven (2): arm64: dts: renesas: white-hawk-cpu: Fix missing serial console pin control of: unittest: Fix of_count_phandle_with_args() expected value message
Geoffrey D. Bennett (5): ALSA: scarlett2: Add missing error check to scarlett2_config_save() ALSA: scarlett2: Add missing error check to scarlett2_usb_set_config() ALSA: scarlett2: Allow passing any output to line_out_remap() ALSA: scarlett2: Add missing error checks to *_ctl_get() ALSA: scarlett2: Add clamp() in scarlett2_mixer_ctl_put()
Gonglei (Arei) (1): crypto: virtio - Handle dataq logic with tasklet
Greg Kroah-Hartman (1): Linux 6.1.75
Gregory Price (1): base/node.c: initialize the accessor list before registering
Gui-Dong Han (2): usb: mon: Fix atomicity violation in mon_bin_vma_fault Bluetooth: Fix atomicity violation in {min,max}_key_size_set
Hangbin Liu (2): selftests/net: specify the interface when do arping selftests/net: fix grep checking for fib_nexthop_multiprefix
Hans de Goede (2): ASoC: rt5645: Drop double EF20 entry from dmi_platform_data[] Input: atkbd - use ab83 as id when skipping the getid command
Hao Sun (1): bpf: Reject variable offset alu on PTR_TO_FLOW_KEYS
Heikki Krogerus (1): Revert "usb: typec: class: fix typec_altmode_put_partner to put plugs"
Heiko Carstens (1): tick-sched: Fix idle and iowait sleeptime accounting vs CPU hotplug
Hengqi Chen (1): LoongArch: BPF: Prevent out-of-bounds memory access
Herbert Xu (1): crypto: af_alg - Disallow multiple in-flight AIO requests
Hou Tao (2): bpf: Add map and need_defer parameters to .map_fd_put_ptr() bpf: Defer the free of inner map when necessary
Hsiao Chien Sung (2): drm/mediatek: Return error if MDP RDMA failed to enable the clock drm/mediatek: Fix underrun in VDO1 when switches off the layer
Huang Ying (1): cxl/port: Fix decoder initialization when nr_targets > interleave_ways
Hugo Villeneuve (2): serial: sc16is7xx: add check for unsupported SPI modes during probe serial: sc16is7xx: set safe default SPI clock frequency
Ian Rogers (1): perf env: Avoid recursively taking env->bpf_progs.lock
Ilias Apalodimas (1): efivarfs: force RO when remounting if SetVariable is not supported
Ilpo Järvinen (2): wifi: rtlwifi: Remove bogus and dangerous ASPM disable/enable code wifi: rtlwifi: Convert LNKCTL change to PCIe cap RMW accessors
Isaac J. Manjarres (1): iommu/dma: Trace bounce buffer usage when mapping buffers
Jan Beulich (1): xen-netback: don't produce zero-size SKB frags
Jan Palus (1): power: supply: cw2015: correct time_to_empty units in sysfs
Jason Gerecke (1): HID: wacom: Correct behavior when processing some confidence == false touches
Jay Buddhabhatti (2): drivers: clk: zynqmp: calculate closest mux rate drivers: clk: zynqmp: update divider round rate logic
Jens Axboe (2): io_uring/rw: ensure io->bytes_done is always initialized block: ensure we hold a queue reference when using queue limits
Jeroen van Ingen Schenau (1): selftests/bpf: Fix erroneous bitmask operation
Jerry Hoemann (1): watchdog/hpwdt: Only claim UNKNOWN NMI if from iLO
Jessica Zhang (2): drm/msm/dpu: Set input_sel bit for INTF drm/msm/dpu: Drop enable and frame_count parameters from dpu_hw_setup_misr()
Jianjun Wang (1): PCI: mediatek-gen3: Fix translation window size calculation
Jim Harris (1): cxl/region: fix x9 interleave typo
Jiri Olsa (1): bpf: Fix re-attachment branch in bpf_tracing_prog_attach
Jiri Slaby (SUSE) (4): tty: change tty_write_lock()'s ndelay parameter to bool tty: early return from send_break() on TTY_DRIVER_HARDWARE_BREAK tty: don't check for signal_pending() in send_break() tty: use 'if' in send_break() instead of 'goto'
Jo Van Bulck (3): selftests/sgx: Fix uninitialized pointer dereference in error path selftests/sgx: Fix uninitialized pointer dereferences in encl_get_entry selftests/sgx: Include memory clobber for inline asm in test enclave
Joakim Zhang (1): dma-mapping: clear dev->dma_mem to NULL after freeing it
Johan Hovold (2): arm64: dts: qcom: sc7280: fix usb_2 wakeup interrupt types arm64: dts: hisilicon: hikey970-pmic: fix regulator cells properties
Johannes Berg (2): wifi: iwlwifi: mvm: set siso/mimo chains to 1 in FW SMPS request wifi: iwlwifi: mvm: send TX path flush in rfkill
John Fastabend (1): bpf: sockmap, fix proto update hook to avoid dup calls
Jordan Rome (2): bpf: Add crosstask check to __bpf_get_stack selftests/bpf: Add assert for user stacks in test_task_stack
Junxian Huang (1): RDMA/hns: Fix inappropriate err code for unsupported operations
Keith Busch (1): block: make BLK_DEF_MAX_SECTORS unsigned
Kirill A. Shutemov (1): x86/kvm: Do not try to disable kvmclock if it was not enabled
Konrad Dybcio (7): arm64: dts: qcom: sc7280: Fix up GPU SIDs arm64: dts: qcom: sc7280: Mark Adreno SMMU as DMA coherent arm64: dts: qcom: sc7280: Mark SDHCI hosts as cache-coherent arm64: dts: qcom: ipq6018: Use lowercase hex arm64: dts: qcom: ipq6018: Pad addresses to 8 hex digits arm64: dts: qcom: ipq6018: Fix up indentation drm/msm/dsi: Use pm_runtime_resume_and_get to prevent refcnt leaks
Krzysztof Kozlowski (3): ARM: dts: qcom: sdx65: correct SPMI node name arm64: dts: qcom: qrb5165-rb5: correct LED panic indicator arm64: dts: qcom: sdm845-db845c: correct LED panic indicator
Kunwu Chan (6): powerpc/powernv: Add a null pointer check to scom_debug_init_one() powerpc/powernv: Add a null pointer check in opal_event_init() powerpc/powernv: Add a null pointer check in opal_powercap_init() powerpc/imc-pmu: Add a null pointer check in update_events_in_group() mfd: syscon: Fix null pointer dereference in of_syscon_register() net: dsa: vsc73xx: Add null pointer check to vsc73xx_gpio_probe
Leon Romanovsky (1): RDMA/usnic: Silence uninitialized symbol smatch warnings
Leone Fernando (1): ipmr: support IP_PKTINFO on cache report IGMP msg
Li Nan (3): block: Set memalloc_noio to false on device_add_disk() error path block: add check of 'minors' and 'first_minor' in device_add_disk() ksmbd: validate the zero field of packet header
Lin Ma (1): net: qualcomm: rmnet: fix global oob in rmnet_policy
Lino Sanfilippo (5): serial: core: fix sanitizing check for RTS settings serial: core: make sure RS485 cannot be enabled when it is not supported serial: core, imx: do not set RS485 enabled if it is not supported serial: 8250_exar: Set missing rs485_supported flag serial: omap: do not override settings for RS485 support
Linus Walleij (2): ASoC: cs35l33: Fix GPIO name and drop legacy include ASoC: cs35l34: Fix GPIO name and drop legacy include
Luca Weiss (2): wifi: ath11k: Defer on rproc_get failure arm64: dts: qcom: sc7280: Mark some nodes as 'reserved'
Ludvig Pärsson (1): ethtool: netlink: Add missing ethnl_ops_begin/complete
Luiz Augusto von Dentz (1): Bluetooth: Fix bogus check for re-auth no supported with non-ssp
Marc Zyngier (1): KVM: arm64: vgic-v4: Restore pending state on host userspace write
Marcelo Schmitt (1): iio: adc: ad7091r: Pass iio_dev to event handler
Marek Szyprowski (2): i2c: s3c24xx: fix read transfers in polling mode i2c: s3c24xx: fix transferring more than one message in polling mode
Mario Limonciello (1): drm/amd: Enable PCIe PME from D3
Masahiro Yamada (2): powerpc: remove checks for binutils older than 2.25 powerpc: add crtsavres.o to always-y instead of extra-y
Matthew Wilcox (Oracle) (2): block: Fix iterating over an empty bio with bio_for_each_folio_all block: Remove special-casing of compound pages
Maurizio Lombardi (3): nvmet-tcp: Fix a kernel panic when host sends an invalid H2C PDU length nvmet-tcp: fix a crash in nvmet_req_complete() nvmet-tcp: Fix the H2C expected PDU len calculation
Mehdi Djait (1): media: dt-bindings: media: rkisp1: Fix the port description for the parallel interface
Michael Ellerman (2): selftests/powerpc: Fix error handling in FPU/VMX preemption tests powerpc/64s: Increase default stack size to 32KB
Michal Simek (1): dt-bindings: gpio: xilinx: Fix node address in gpio
Mickaël Salaün (1): selinux: Fix error priority for bind with AF_UNSPEC on PF_INET6 socket
Mimi Zohar (1): Revert "KEYS: encrypted: Add check for strsep"
Min Li (1): block: add check that partition length needs to be aligned with block size
Ming Yen Hsieh (1): wifi: mt76: mt7921: fix country count limitation for CLC
Mirsad Todorovac (2): kselftest/alsa - mixer-test: fix the number of parameters to ksft_exit_fail_msg() kselftest/alsa - mixer-test: Fix the print format specifier warning
Moudy Ho (2): dt-bindings: media: mediatek: mdp3: correct RDMA and WROT node with generic names arm64: dts: mediatek: mt8183: correct MDP3 DMA-related nodes
Nam Cao (2): fbdev: flush deferred work in fb_deferred_io_fsync() fbdev: flush deferred IO before closing
Namhyung Kim (1): perf genelf: Set ELF program header addresses properly
Namjae Jeon (3): ksmbd: validate mech token in session setup ksmbd: fix UAF issue in ksmbd_tcp_new_connection() ksmbd: only v2 leases handle the directory
Nathan Lynch (1): powerpc/pseries/memhp: Fix access beyond end of drmem array
Nia Espera (1): arm64: dts: qcom: sm8350: Fix DMA0 address
Nicolas Dichtel (1): Revert "net: rtnetlink: Enslave device before bringing it up"
Nikita Kiryushin (2): ACPI: video: check for error while searching for backlight device parent ACPI: LPIT: Avoid u32 multiplication overflow
Nikita Yushchenko (1): net: ravb: Fix dma_addr_t truncation in error case
Nikita Zhandarovich (5): crypto: safexcel - Add error handling for dma_map_sg() calls drm/radeon/r600_cs: Fix possible int overflows in r600_cs_check_reg() drm/radeon/r100: Fix integer overflow issues in r100_cs_track_check() drm/radeon: check return value of radeon_ring_lock() ipv6: mcast: fix data-race in ipv6_mc_down / mld_ifc_work
Niklas Cassel (1): PCI: dwc: endpoint: Fix dw_pcie_ep_raise_msix_irq() alignment support
Niklas Schnelle (1): s390/pci: fix max size calculation in zpci_memcpy_toio()
Nitin Yadav (1): arm64: dts: ti: k3-am62a-main: Fix GPIO pin count in DT nodes
Nuno Sa (3): iio: adc: ad9467: fix reset gpio handling iio: adc: ad9467: don't ignore error codes iio: adc: ad9467: fix scale setting
NÃcolas F. R. A. Prado (2): drm/mediatek: dp: Add phy_mtk_dp module as pre-dependency spmi: mtk-pmif: Serialize PMIF status check and command submission
Olga Kornievskaia (1): SUNRPC: fix _xprt_switch_find_current_entry logic
Oliver Neukum (1): usb: cdc-acm: return correct error code on unsupported break
Oliver Upton (1): KVM: arm64: vgic-its: Avoid potential UAF in LPI translation cache
Osama Muhammad (1): gfs2: Fix kernel NULL pointer dereference in gfs2_rgrp_dump
Ovidiu Panait (12): crypto: sahara - remove FLAGS_NEW_KEY logic crypto: sahara - fix cbc selftest failure crypto: sahara - fix ahash selftest failure crypto: sahara - fix processing requests with cryptlen < sg->length crypto: sahara - fix error handling in sahara_hw_descriptor_create() crypto: sahara - avoid skcipher fallback code duplication crypto: sahara - handle zero-length aes requests crypto: sahara - fix ahash reqsize crypto: sahara - fix wait_for_completion_timeout() error handling crypto: sahara - improve error handling in sahara_sha_process() crypto: sahara - fix processing hash requests with req->nbytes < sg->length crypto: sahara - do not resize req->src when doing hash operations
Pablo Neira Ayuso (6): netfilter: nf_tables: check if catch-all set element is active in next generation netfilter: nf_tables: reject invalid set policy netfilter: nft_limit: do not ignore unsupported flags netfilter: nf_tables: do not allow mismatch field size and set key length netfilter: nf_tables: skip dead set elements in netlink dump netfilter: nf_tables: reject NFT_SET_CONCAT with not field length description
Paolo Abeni (1): mptcp: relax check on MPC passive fallback
Paul E. McKenney (1): rcu-tasks: Provide rcu_trace_implies_rcu_gp()
Paul Geurts (1): serial: imx: fix tx statemachine deadlock
Paul Kocialkowski (2): media: verisilicon: Hook the (TRY_)DECODER_CMD stateless ioctls media: rkvdec: Hook the (TRY_)DECODER_CMD stateless ioctls
Pavel Tikhomirov (4): netfilter: nfnetlink_log: use proper helper for fetching physinif netfilter: nf_queue: remove excess nf_bridge variable netfilter: propagate net to nf_bridge_get_physindev netfilter: bridge: replace physindev with physinif in nf_bridge_info
Peter Delevoryas (1): net/ncsi: Fix netlink major/minor version numbers
Peter Robinson (2): mmc: sdhci_am654: Fix TI SoC dependencies mmc: sdhci_omap: Fix TI SoC dependencies
Philipp Zabel (2): pwm: stm32: Use hweight32 in stm32_pwm_detect_channels pwm: stm32: Fix enable count for clk in .probe()
Qiang Ma (1): net: stmmac: ethtool: Fixed calltrace caused by unbalanced disable_irq_wake calls
RD Babiera (1): usb: typec: class: fix typec_altmode_put_partner to put plugs
Randy Dunlap (2): powerpc/44x: select I2C for CURRITUCK ARM: 9330/1: davinci: also select PINCTRL
Ricardo B. Marliere (1): media: pvrusb2: fix use after free on context disconnection
Richard Fitzgerald (1): kunit: debugfs: Fix unchecked dereference in debugfs_print_results()
Rob Clark (1): iommu/arm-smmu-qcom: Add missing GMU entry to match table
Rob Herring (2): of: Add of_property_present() helper cpufreq: Use of_property_present() for testing DT property presence
Ronald Monthero (1): mtd: rawnand: Increment IFC_TIMEOUT_MSECS for nand controller response
Sakari Ailus (2): acpi: property: Let args be NULL in __acpi_node_get_property_reference software node: Let args be NULL in software_node_get_reference_args
Sanjuán GarcÃa, Jorge (1): net: ethernet: ti: am65-cpsw: Fix max mtu to fit ethernet frames
Satya Priya Kakitapalli (4): clk: qcom: gpucc-sm8150: Update the gpu_cc_pll1 config dt-bindings: clock: Update the videocc resets for sm8150 clk: qcom: videocc-sm8150: Update the videocc resets clk: qcom: videocc-sm8150: Add missing PLL config property
Serge Semin (2): mips: dmi: Fix early remap on MIPS32 mips: Fix incorrect max_low_pfn adjustment
Sergey Gorenko (1): IB/iser: Prevent invalidating wrong MR
Sergey Shtylyov (1): pstore: ram_core: fix possible overflow in persistent_ram_init_ecc()
Siddharth Vadapalli (1): PCI: keystone: Fix race condition when initializing PHYs
Sjoerd Simons (1): arm64: dts: armada-3720-turris-mox: set irq type for RTC
Song Liu (1): Revert "Revert "md/raid5: Wait for MD_SB_CHANGE_PENDING in raid5d""
Srinivas Pandruvada (3): platform/x86/intel/vsec: Enhance and Export intel_vsec_add_aux() platform/x86/intel/vsec: Support private data platform/x86/intel/vsec: Use mutex for ida_alloc() and ida_free()
Srinivasan Shanmugam (1): drm/amdkfd: Confirm list is non-empty before utilizing list_first_entry in kfd_topology.c
Stefan Berger (1): rootfs: Fix support for rootfstype= when root= is given
Stefan Wahren (2): watchdog: bcm2835_wdt: Fix WDIOC_SETTIMEOUT handling serial: 8250_bcm2835aux: Restore clock error handling
Stefan Wiehler (1): mips/smp: Call rcutree_report_cpu_starting() earlier
Su Hui (11): wifi: rtlwifi: rtl8821ae: phy: fix an undefined bitwise shift behavior wifi: rtlwifi: add calculate_bit_shift() wifi: rtlwifi: rtl8188ee: phy: using calculate_bit_shift() wifi: rtlwifi: rtl8192c: using calculate_bit_shift() wifi: rtlwifi: rtl8192cu: using calculate_bit_shift() wifi: rtlwifi: rtl8192ce: using calculate_bit_shift() wifi: rtlwifi: rtl8192de: using calculate_bit_shift() wifi: rtlwifi: rtl8192ee: using calculate_bit_shift() wifi: rtlwifi: rtl8192se: using calculate_bit_shift() clk: si5341: fix an error code problem in si5341_output_clk_set_rate power: supply: bq256xx: fix some problem in bq256xx_hw_init
Tadeusz Struk (1): PCI/P2PDMA: Remove reference to pci_p2pdma_map_sg()
Taehee Yoo (1): amt: do not use overwrapped cb area
Takashi Iwai (1): ALSA: oxygen: Fix right channel of capture volume mixer
Tao Liu (1): net/sched: act_ct: fix skb leak and crash on ooo frags
Thinh Nguyen (2): Revert "usb: dwc3: Soft reset phy on probe for host" Revert "usb: dwc3: don't reset device side if dwc3 was configured as host-only"
Théo Lebrun (1): clk: fixed-rate: fix clk_hw_register_fixed_rate_with_accuracy_parent_hw
Tomi Valkeinen (12): arm64: dts: ti: k3-am65-main: Fix DSS irq trigger type Revert "drm/tidss: Annotate dma-fence critical section in commit path" Revert "drm/omapdrm: Annotate dma-fence critical section in commit path" drm/tilcdc: Fix irq free on unload drm/tidss: Move reset to the end of dispc_init() drm/tidss: Return error value from from softreset drm/tidss: Check for K2G in in dispc_softreset() drm/tidss: Fix dss reset drm/bridge: cdns-mhdp8546: Fix use of uninitialized variable drm/bridge: tc358767: Fix return value on error case media: imx-mipi-csis: Fix clock handling in remove() media: rkisp1: Fix media device memory leak
Tony Lindgren (1): clocksource/drivers/timer-ti-dm: Fix make W=n kerneldoc warnings
Tony Luck (1): ACPI: extlog: Clear Extended Error Log status when RAS_CEC handled the error
Trond Myklebust (2): NFSv4.1/pnfs: Ensure we handle the error NFS4ERR_RETURNCONFLICT pNFS: Fix the pnfs block driver's calculation of layoutget size
Uttkarsh Aggarwal (1): usb: dwc: ep0: Update request status in dwc3_ep0_stall_restart
Uwe Kleine-König (5): drm/bridge: tpd12s015: Drop buggy __exit annotation for remove function pwm: stm32: Use regmap_clear_bits and regmap_set_bits where applicable pwm: jz4740: Don't use dev_err_probe() in .request() pwm: Fix out-of-bounds access in of_pwm_single_xlate() serial: 8250: omap: Don't skip resource freeing if pm_runtime_resume_and_get() failed
Vignesh Raghavendra (1): watchdog: rti_wdt: Drop runtime pm reference count when watchdog is unused
Wang Zhao (1): wifi: mt76: mt7921s: fix workqueue problem causes STA association fail
Wenkai Lin (1): crypto: hisilicon/qm - add a function to set qm algs
Wolfram Sang (1): spi: sh-msiof: Enforce fixed DTDL for R-Car H3
Xi Ruoyao (1): LoongArch: Fix and simplify fcsr initialization on execve()
Xingyuan Mo (1): accel/habanalabs: fix information leak in sec_attest_info()
Xu Yang (2): usb: phy: mxs: remove CONFIG_USB_OTG condition for mxs_phy_is_otg_host() usb: chipidea: wait controller resume finished for wakeup irq
Yang Yingliang (1): drm/radeon: check the alloc_workqueue return value in radeon_crtc_init()
Yazen Ghannam (1): x86/mce/inject: Clear test status value
YiFei Zhu (1): selftests/bpf: Relax time_tai test for equal timestamps in tai_forward
Yicong Yang (2): perf header: Fix one memory leakage in perf_event__fprintf_event_update() perf hisi-ptt: Fix one memory leakage in hisi_ptt_process_auxtrace_event()
Yihang Li (3): scsi: hisi_sas: Replace with standard error code return value scsi: hisi_sas: Rollback some operations if FLR failed scsi: hisi_sas: Correct the number of global debugfs registers
Yo-Jung Lin (1): ALSA: hda/realtek: Enable mute/micmute LEDs and limit mic boost on HP ZBook
Yu Kuai (1): md: synchronize flush io with array reconfiguration
Zack Rusin (2): drm/vmwgfx: Fix possible invalid drm gem put calls drm/vmwgfx: Keep a gem reference to user bos in surfaces
Zhao Mengmeng (1): selftests/sgx: Skip non X86_64 platform
ZhaoLong Wang (1): mtd: Fix gluebi NULL pointer dereference caused by ftl notifier
Zheng Wang (1): media: mtk-jpeg: Remove cancel worker in mtk_jpeg_remove to avoid the crash of multi-core JPEG devices
Zhiguo Niu (1): f2fs: fix to check return value of f2fs_recover_xattr_data
Zhipeng Lu (8): drm/radeon/dpm: fix a memleak in sumo_parse_power_table drm/radeon/trinity_dpm: fix a memleak in trinity_parse_power_table media: cx231xx: fix a memleak in cx231xx_init_isoc drm/amd/pm: fix a double-free in si_dpm_init drivers/amd/pm: fix a use-after-free in kv_parse_power_table gpu/drm/radeon: fix two memleaks in radeon_vm_init drm/amd/pm: fix a double-free in amdgpu_parse_extended_power_table drm/amd/pm/smu7: fix a memleak in smu7_hwmgr_backend_init
Zhiqi Song (4): crypto: hisilicon/qm - save capability registers in qm init process crypto: hisilicon/hpre - save capability registers in probe process crypto: hisilicon/sec2 - save capability registers in probe process crypto: hisilicon/zip - save capability registers in probe process
kyrie wu (1): media: mtk-jpegdec: export jpeg decoder functions
qizhong cheng (1): PCI: mediatek: Clear interrupt status before dispatching handler
wangyangxin (1): crypto: virtio - Wait for tasklet to complete on device remove
Çağhan Demir (1): ALSA: hda/relatek: Enable Mute LED on HP Laptop 15s-fq2xxx
diff --git a/Documentation/devicetree/bindings/gpio/xlnx,gpio-xilinx.yaml b/Documentation/devicetree/bindings/gpio/xlnx,gpio-xilinx.yaml index f333ee2288e7..11ae8ec3c739 100644 --- a/Documentation/devicetree/bindings/gpio/xlnx,gpio-xilinx.yaml +++ b/Documentation/devicetree/bindings/gpio/xlnx,gpio-xilinx.yaml @@ -126,7 +126,7 @@ examples: - | #include <dt-bindings/interrupt-controller/arm-gic.h>
- gpio@e000a000 { + gpio@a0020000 { compatible = "xlnx,xps-gpio-1.00.a"; reg = <0xa0020000 0x10000>; #gpio-cells = <2>; diff --git a/Documentation/devicetree/bindings/media/mediatek,mdp3-rdma.yaml b/Documentation/devicetree/bindings/media/mediatek,mdp3-rdma.yaml index 9cfc0c7d23e0..46730687c662 100644 --- a/Documentation/devicetree/bindings/media/mediatek,mdp3-rdma.yaml +++ b/Documentation/devicetree/bindings/media/mediatek,mdp3-rdma.yaml @@ -61,6 +61,9 @@ properties: - description: used for 1st data pipe from RDMA - description: used for 2nd data pipe from RDMA
+ '#dma-cells': + const: 1 + required: - compatible - reg @@ -70,6 +73,7 @@ required: - clocks - iommus - mboxes + - '#dma-cells'
additionalProperties: false
@@ -80,16 +84,17 @@ examples: #include <dt-bindings/power/mt8183-power.h> #include <dt-bindings/memory/mt8183-larb-port.h>
- mdp3_rdma0: mdp3-rdma0@14001000 { - compatible = "mediatek,mt8183-mdp3-rdma"; - reg = <0x14001000 0x1000>; - mediatek,gce-client-reg = <&gce SUBSYS_1400XXXX 0x1000 0x1000>; - mediatek,gce-events = <CMDQ_EVENT_MDP_RDMA0_SOF>, - <CMDQ_EVENT_MDP_RDMA0_EOF>; - power-domains = <&spm MT8183_POWER_DOMAIN_DISP>; - clocks = <&mmsys CLK_MM_MDP_RDMA0>, - <&mmsys CLK_MM_MDP_RSZ1>; - iommus = <&iommu>; - mboxes = <&gce 20 CMDQ_THR_PRIO_LOWEST>, - <&gce 21 CMDQ_THR_PRIO_LOWEST>; + dma-controller@14001000 { + compatible = "mediatek,mt8183-mdp3-rdma"; + reg = <0x14001000 0x1000>; + mediatek,gce-client-reg = <&gce SUBSYS_1400XXXX 0x1000 0x1000>; + mediatek,gce-events = <CMDQ_EVENT_MDP_RDMA0_SOF>, + <CMDQ_EVENT_MDP_RDMA0_EOF>; + power-domains = <&spm MT8183_POWER_DOMAIN_DISP>; + clocks = <&mmsys CLK_MM_MDP_RDMA0>, + <&mmsys CLK_MM_MDP_RSZ1>; + iommus = <&iommu>; + mboxes = <&gce 20 CMDQ_THR_PRIO_LOWEST>, + <&gce 21 CMDQ_THR_PRIO_LOWEST>; + #dma-cells = <1>; }; diff --git a/Documentation/devicetree/bindings/media/mediatek,mdp3-wrot.yaml b/Documentation/devicetree/bindings/media/mediatek,mdp3-wrot.yaml index 0baa77198fa2..64ea98aa0592 100644 --- a/Documentation/devicetree/bindings/media/mediatek,mdp3-wrot.yaml +++ b/Documentation/devicetree/bindings/media/mediatek,mdp3-wrot.yaml @@ -50,6 +50,9 @@ properties: iommus: maxItems: 1
+ '#dma-cells': + const: 1 + required: - compatible - reg @@ -58,6 +61,7 @@ required: - power-domains - clocks - iommus + - '#dma-cells'
additionalProperties: false
@@ -68,13 +72,14 @@ examples: #include <dt-bindings/power/mt8183-power.h> #include <dt-bindings/memory/mt8183-larb-port.h>
- mdp3_wrot0: mdp3-wrot0@14005000 { - compatible = "mediatek,mt8183-mdp3-wrot"; - reg = <0x14005000 0x1000>; - mediatek,gce-client-reg = <&gce SUBSYS_1400XXXX 0x5000 0x1000>; - mediatek,gce-events = <CMDQ_EVENT_MDP_WROT0_SOF>, - <CMDQ_EVENT_MDP_WROT0_EOF>; - power-domains = <&spm MT8183_POWER_DOMAIN_DISP>; - clocks = <&mmsys CLK_MM_MDP_WROT0>; - iommus = <&iommu>; + dma-controller@14005000 { + compatible = "mediatek,mt8183-mdp3-wrot"; + reg = <0x14005000 0x1000>; + mediatek,gce-client-reg = <&gce SUBSYS_1400XXXX 0x5000 0x1000>; + mediatek,gce-events = <CMDQ_EVENT_MDP_WROT0_SOF>, + <CMDQ_EVENT_MDP_WROT0_EOF>; + power-domains = <&spm MT8183_POWER_DOMAIN_DISP>; + clocks = <&mmsys CLK_MM_MDP_WROT0>; + iommus = <&iommu>; + #dma-cells = <1>; }; diff --git a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml index b3661d7d4357..2a0ad332f5ce 100644 --- a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml +++ b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml @@ -90,15 +90,16 @@ properties: description: connection point for input on the parallel interface
properties: - bus-type: - enum: [5, 6] - endpoint: $ref: video-interfaces.yaml# unevaluatedProperties: false
- required: - - bus-type + properties: + bus-type: + enum: [5, 6] + + required: + - bus-type
anyOf: - required: diff --git a/Documentation/driver-api/pci/p2pdma.rst b/Documentation/driver-api/pci/p2pdma.rst index 44deb52beeb4..d0b241628cf1 100644 --- a/Documentation/driver-api/pci/p2pdma.rst +++ b/Documentation/driver-api/pci/p2pdma.rst @@ -83,19 +83,9 @@ this to include other types of resources like doorbells. Client Drivers --------------
-A client driver typically only has to conditionally change its DMA map -routine to use the mapping function :c:func:`pci_p2pdma_map_sg()` instead -of the usual :c:func:`dma_map_sg()` function. Memory mapped in this -way does not need to be unmapped. - -The client may also, optionally, make use of -:c:func:`is_pci_p2pdma_page()` to determine when to use the P2P mapping -functions and when to use the regular mapping functions. In some -situations, it may be more appropriate to use a flag to indicate a -given request is P2P memory and map appropriately. It is important to -ensure that struct pages that back P2P memory stay out of code that -does not have support for them as other code may treat the pages as -regular memory which may not be appropriate. +A client driver only has to use the mapping API :c:func:`dma_map_sg()` +and :c:func:`dma_unmap_sg()` functions as usual, and the implementation +will do the right thing for the P2P capable memory.
Orchestrator Drivers diff --git a/Makefile b/Makefile index 63125d1ffd9c..7cd49d9eadbf 100644 --- a/Makefile +++ b/Makefile @@ -1,7 +1,7 @@ # SPDX-License-Identifier: GPL-2.0 VERSION = 6 PATCHLEVEL = 1 -SUBLEVEL = 74 +SUBLEVEL = 75 EXTRAVERSION = NAME = Curry Ramen
diff --git a/arch/arm/boot/dts/qcom-apq8064.dtsi b/arch/arm/boot/dts/qcom-apq8064.dtsi index 4b57e9f5bc64..2b3927a829b7 100644 --- a/arch/arm/boot/dts/qcom-apq8064.dtsi +++ b/arch/arm/boot/dts/qcom-apq8064.dtsi @@ -750,7 +750,7 @@ pwrkey@1c {
xoadc: xoadc@197 { compatible = "qcom,pm8921-adc"; - reg = <197>; + reg = <0x197>; interrupts-extended = <&pmicintc 78 IRQ_TYPE_EDGE_RISING>; #address-cells = <2>; #size-cells = <0>; diff --git a/arch/arm/boot/dts/qcom-sdx65.dtsi b/arch/arm/boot/dts/qcom-sdx65.dtsi index ecb9171e4da5..ebb78b489e63 100644 --- a/arch/arm/boot/dts/qcom-sdx65.dtsi +++ b/arch/arm/boot/dts/qcom-sdx65.dtsi @@ -401,7 +401,7 @@ restart@c264000 { reg = <0x0c264000 0x1000>; };
- spmi_bus: qcom,spmi@c440000 { + spmi_bus: spmi@c440000 { compatible = "qcom,spmi-pmic-arb"; reg = <0xc440000 0xd00>, <0xc600000 0x2000000>, diff --git a/arch/arm/boot/dts/stm32mp157a-dk1-scmi.dts b/arch/arm/boot/dts/stm32mp157a-dk1-scmi.dts index e539cc80bef8..942a6ca38d97 100644 --- a/arch/arm/boot/dts/stm32mp157a-dk1-scmi.dts +++ b/arch/arm/boot/dts/stm32mp157a-dk1-scmi.dts @@ -11,7 +11,7 @@
/ { model = "STMicroelectronics STM32MP157A-DK1 SCMI Discovery Board"; - compatible = "st,stm32mp157a-dk1-scmi", "st,stm32mp157a-dk1", "st,stm32mp157"; + compatible = "st,stm32mp157a-dk1-scmi", "st,stm32mp157";
reserved-memory { optee@de000000 { diff --git a/arch/arm/boot/dts/stm32mp157c-dk2-scmi.dts b/arch/arm/boot/dts/stm32mp157c-dk2-scmi.dts index 97e4f94b0a24..99c4ff1f5c21 100644 --- a/arch/arm/boot/dts/stm32mp157c-dk2-scmi.dts +++ b/arch/arm/boot/dts/stm32mp157c-dk2-scmi.dts @@ -11,7 +11,7 @@
/ { model = "STMicroelectronics STM32MP157C-DK2 SCMI Discovery Board"; - compatible = "st,stm32mp157c-dk2-scmi", "st,stm32mp157c-dk2", "st,stm32mp157"; + compatible = "st,stm32mp157c-dk2-scmi", "st,stm32mp157";
reserved-memory { optee@de000000 { diff --git a/arch/arm/boot/dts/stm32mp157c-ed1-scmi.dts b/arch/arm/boot/dts/stm32mp157c-ed1-scmi.dts index 9cf0a44d2f47..21010458b36f 100644 --- a/arch/arm/boot/dts/stm32mp157c-ed1-scmi.dts +++ b/arch/arm/boot/dts/stm32mp157c-ed1-scmi.dts @@ -11,7 +11,7 @@
/ { model = "STMicroelectronics STM32MP157C-ED1 SCMI eval daughter"; - compatible = "st,stm32mp157c-ed1-scmi", "st,stm32mp157c-ed1", "st,stm32mp157"; + compatible = "st,stm32mp157c-ed1-scmi", "st,stm32mp157";
reserved-memory { optee@fe000000 { diff --git a/arch/arm/boot/dts/stm32mp157c-ev1-scmi.dts b/arch/arm/boot/dts/stm32mp157c-ev1-scmi.dts index 3b9dd6f4ccc9..d37637149919 100644 --- a/arch/arm/boot/dts/stm32mp157c-ev1-scmi.dts +++ b/arch/arm/boot/dts/stm32mp157c-ev1-scmi.dts @@ -11,8 +11,7 @@
/ { model = "STMicroelectronics STM32MP157C-EV1 SCMI eval daughter on eval mother"; - compatible = "st,stm32mp157c-ev1-scmi", "st,stm32mp157c-ev1", "st,stm32mp157c-ed1", - "st,stm32mp157"; + compatible = "st,stm32mp157c-ev1-scmi", "st,stm32mp157c-ed1", "st,stm32mp157";
reserved-memory { optee@fe000000 { diff --git a/arch/arm/mach-davinci/Kconfig b/arch/arm/mach-davinci/Kconfig index c8cbd9a30791..672ffb0b5f3a 100644 --- a/arch/arm/mach-davinci/Kconfig +++ b/arch/arm/mach-davinci/Kconfig @@ -4,12 +4,14 @@ menuconfig ARCH_DAVINCI bool "TI DaVinci" depends on ARCH_MULTI_V5 depends on CPU_LITTLE_ENDIAN + select CPU_ARM926T select DAVINCI_TIMER select ZONE_DMA select PM_GENERIC_DOMAINS if PM select PM_GENERIC_DOMAINS_OF if PM && OF select REGMAP_MMIO select RESET_CONTROLLER + select PINCTRL select PINCTRL_SINGLE
if ARCH_DAVINCI diff --git a/arch/arm64/boot/dts/freescale/imx8mm.dtsi b/arch/arm64/boot/dts/freescale/imx8mm.dtsi index d583db18f74c..7a410d73600b 100644 --- a/arch/arm64/boot/dts/freescale/imx8mm.dtsi +++ b/arch/arm64/boot/dts/freescale/imx8mm.dtsi @@ -1303,7 +1303,7 @@ gpu_3d: gpu@38000000 { assigned-clocks = <&clk IMX8MM_CLK_GPU3D_CORE>, <&clk IMX8MM_GPU_PLL_OUT>; assigned-clock-parents = <&clk IMX8MM_GPU_PLL_OUT>; - assigned-clock-rates = <0>, <1000000000>; + assigned-clock-rates = <0>, <800000000>; power-domains = <&pgc_gpu>; };
@@ -1318,7 +1318,7 @@ gpu_2d: gpu@38008000 { assigned-clocks = <&clk IMX8MM_CLK_GPU2D_CORE>, <&clk IMX8MM_GPU_PLL_OUT>; assigned-clock-parents = <&clk IMX8MM_GPU_PLL_OUT>; - assigned-clock-rates = <0>, <1000000000>; + assigned-clock-rates = <0>, <800000000>; power-domains = <&pgc_gpu>; };
diff --git a/arch/arm64/boot/dts/hisilicon/hikey970-pmic.dtsi b/arch/arm64/boot/dts/hisilicon/hikey970-pmic.dtsi index 970047f2dabd..c06e011a6c3f 100644 --- a/arch/arm64/boot/dts/hisilicon/hikey970-pmic.dtsi +++ b/arch/arm64/boot/dts/hisilicon/hikey970-pmic.dtsi @@ -25,9 +25,6 @@ pmic: pmic@0 { gpios = <&gpio28 0 0>;
regulators { - #address-cells = <1>; - #size-cells = <0>; - ldo3: ldo3 { /* HDMI */ regulator-name = "ldo3"; regulator-min-microvolt = <1500000>; diff --git a/arch/arm64/boot/dts/marvell/armada-3720-turris-mox.dts b/arch/arm64/boot/dts/marvell/armada-3720-turris-mox.dts index 200f97e1c4c9..37350e5fa253 100644 --- a/arch/arm64/boot/dts/marvell/armada-3720-turris-mox.dts +++ b/arch/arm64/boot/dts/marvell/armada-3720-turris-mox.dts @@ -130,7 +130,7 @@ rtc@6f { compatible = "microchip,mcp7940x"; reg = <0x6f>; interrupt-parent = <&gpiosb>; - interrupts = <5 0>; /* GPIO2_5 */ + interrupts = <5 IRQ_TYPE_EDGE_FALLING>; /* GPIO2_5 */ }; };
diff --git a/arch/arm64/boot/dts/mediatek/mt8183.dtsi b/arch/arm64/boot/dts/mediatek/mt8183.dtsi index 10779a9947fe..d5d9b954c449 100644 --- a/arch/arm64/boot/dts/mediatek/mt8183.dtsi +++ b/arch/arm64/boot/dts/mediatek/mt8183.dtsi @@ -1586,7 +1586,7 @@ mmsys: syscon@14000000 { mediatek,gce-client-reg = <&gce SUBSYS_1400XXXX 0 0x1000>; };
- mdp3-rdma0@14001000 { + dma-controller0@14001000 { compatible = "mediatek,mt8183-mdp3-rdma"; reg = <0 0x14001000 0 0x1000>; mediatek,gce-client-reg = <&gce SUBSYS_1400XXXX 0x1000 0x1000>; @@ -1598,6 +1598,7 @@ mdp3-rdma0@14001000 { iommus = <&iommu M4U_PORT_MDP_RDMA0>; mboxes = <&gce 20 CMDQ_THR_PRIO_LOWEST 0>, <&gce 21 CMDQ_THR_PRIO_LOWEST 0>; + #dma-cells = <1>; };
mdp3-rsz0@14003000 { @@ -1618,7 +1619,7 @@ mdp3-rsz1@14004000 { clocks = <&mmsys CLK_MM_MDP_RSZ1>; };
- mdp3-wrot0@14005000 { + dma-controller@14005000 { compatible = "mediatek,mt8183-mdp3-wrot"; reg = <0 0x14005000 0 0x1000>; mediatek,gce-client-reg = <&gce SUBSYS_1400XXXX 0x5000 0x1000>; @@ -1627,6 +1628,7 @@ mdp3-wrot0@14005000 { power-domains = <&spm MT8183_POWER_DOMAIN_DISP>; clocks = <&mmsys CLK_MM_MDP_WROT0>; iommus = <&iommu M4U_PORT_MDP_WROT0>; + #dma-cells = <1>; };
mdp3-wdma@14006000 { diff --git a/arch/arm64/boot/dts/qcom/ipq6018.dtsi b/arch/arm64/boot/dts/qcom/ipq6018.dtsi index 43ff8f1f1475..1533c61cb106 100644 --- a/arch/arm64/boot/dts/qcom/ipq6018.dtsi +++ b/arch/arm64/boot/dts/qcom/ipq6018.dtsi @@ -146,7 +146,7 @@ reserved-memory { ranges;
rpm_msg_ram: memory@60000 { - reg = <0x0 0x60000 0x0 0x6000>; + reg = <0x0 0x00060000 0x0 0x6000>; no-map; };
@@ -181,7 +181,7 @@ soc: soc {
prng: qrng@e1000 { compatible = "qcom,prng-ee"; - reg = <0x0 0xe3000 0x0 0x1000>; + reg = <0x0 0x000e3000 0x0 0x1000>; clocks = <&gcc GCC_PRNG_AHB_CLK>; clock-names = "core"; }; @@ -201,8 +201,8 @@ crypto: crypto@73a000 { compatible = "qcom,crypto-v5.1"; reg = <0x0 0x0073a000 0x0 0x6000>; clocks = <&gcc GCC_CRYPTO_AHB_CLK>, - <&gcc GCC_CRYPTO_AXI_CLK>, - <&gcc GCC_CRYPTO_CLK>; + <&gcc GCC_CRYPTO_AXI_CLK>, + <&gcc GCC_CRYPTO_CLK>; clock-names = "iface", "bus", "core"; dmas = <&cryptobam 2>, <&cryptobam 3>; dma-names = "rx", "tx"; @@ -272,7 +272,7 @@ blsp1_uart3: serial@78b1000 { reg = <0x0 0x078b1000 0x0 0x200>; interrupts = <GIC_SPI 306 IRQ_TYPE_LEVEL_HIGH>; clocks = <&gcc GCC_BLSP1_UART3_APPS_CLK>, - <&gcc GCC_BLSP1_AHB_CLK>; + <&gcc GCC_BLSP1_AHB_CLK>; clock-names = "core", "iface"; status = "disabled"; }; @@ -285,7 +285,7 @@ blsp1_spi1: spi@78b5000 { interrupts = <GIC_SPI 95 IRQ_TYPE_LEVEL_HIGH>; spi-max-frequency = <50000000>; clocks = <&gcc GCC_BLSP1_QUP1_SPI_APPS_CLK>, - <&gcc GCC_BLSP1_AHB_CLK>; + <&gcc GCC_BLSP1_AHB_CLK>; clock-names = "core", "iface"; dmas = <&blsp_dma 12>, <&blsp_dma 13>; dma-names = "tx", "rx"; @@ -300,7 +300,7 @@ blsp1_spi2: spi@78b6000 { interrupts = <GIC_SPI 96 IRQ_TYPE_LEVEL_HIGH>; spi-max-frequency = <50000000>; clocks = <&gcc GCC_BLSP1_QUP2_SPI_APPS_CLK>, - <&gcc GCC_BLSP1_AHB_CLK>; + <&gcc GCC_BLSP1_AHB_CLK>; clock-names = "core", "iface"; dmas = <&blsp_dma 14>, <&blsp_dma 15>; dma-names = "tx", "rx"; @@ -358,8 +358,8 @@ qpic_nand: nand@79b0000 { clock-names = "core", "aon";
dmas = <&qpic_bam 0>, - <&qpic_bam 1>, - <&qpic_bam 2>; + <&qpic_bam 1>, + <&qpic_bam 2>; dma-names = "tx", "rx", "cmd"; pinctrl-0 = <&qpic_pins>; pinctrl-names = "default"; @@ -372,10 +372,10 @@ intc: interrupt-controller@b000000 { #size-cells = <2>; interrupt-controller; #interrupt-cells = <0x3>; - reg = <0x0 0x0b000000 0x0 0x1000>, /*GICD*/ - <0x0 0x0b002000 0x0 0x1000>, /*GICC*/ - <0x0 0x0b001000 0x0 0x1000>, /*GICH*/ - <0x0 0x0b004000 0x0 0x1000>; /*GICV*/ + reg = <0x0 0x0b000000 0x0 0x1000>, /*GICD*/ + <0x0 0x0b002000 0x0 0x1000>, /*GICC*/ + <0x0 0x0b001000 0x0 0x1000>, /*GICH*/ + <0x0 0x0b004000 0x0 0x1000>; /*GICV*/ interrupts = <GIC_PPI 9 IRQ_TYPE_LEVEL_HIGH>; ranges = <0 0 0 0xb00a000 0 0xffd>;
@@ -388,7 +388,7 @@ v2m@0 {
pcie_phy: phy@84000 { compatible = "qcom,ipq6018-qmp-pcie-phy"; - reg = <0x0 0x84000 0x0 0x1bc>; /* Serdes PLL */ + reg = <0x0 0x00084000 0x0 0x1bc>; /* Serdes PLL */ status = "disabled"; #address-cells = <2>; #size-cells = <2>; @@ -404,9 +404,10 @@ pcie_phy: phy@84000 { "common";
pcie_phy0: phy@84200 { - reg = <0x0 0x84200 0x0 0x16c>, /* Serdes Tx */ - <0x0 0x84400 0x0 0x200>, /* Serdes Rx */ - <0x0 0x84800 0x0 0x4f4>; /* PCS: Lane0, COM, PCIE */ + reg = <0x0 0x00084200 0x0 0x16c>, /* Serdes Tx */ + <0x0 0x00084400 0x0 0x200>, /* Serdes Rx */ + <0x0 0x00084800 0x0 0x1f0>, /* PCS: Lane0, COM, PCIE */ + <0x0 0x00084c00 0x0 0xf4>; /* pcs_misc */ #phy-cells = <0>;
clocks = <&gcc GCC_PCIE0_PIPE_CLK>; @@ -628,7 +629,7 @@ mdio: mdio@90000 { #address-cells = <1>; #size-cells = <0>; compatible = "qcom,ipq6018-mdio", "qcom,ipq4019-mdio"; - reg = <0x0 0x90000 0x0 0x64>; + reg = <0x0 0x00090000 0x0 0x64>; clocks = <&gcc GCC_MDIO_AHB_CLK>; clock-names = "gcc_mdio_ahb_clk"; status = "disabled"; @@ -636,7 +637,7 @@ mdio: mdio@90000 {
qusb_phy_1: qusb@59000 { compatible = "qcom,ipq6018-qusb2-phy"; - reg = <0x0 0x059000 0x0 0x180>; + reg = <0x0 0x00059000 0x0 0x180>; #phy-cells = <0>;
clocks = <&gcc GCC_USB1_PHY_CFG_AHB_CLK>, @@ -668,23 +669,23 @@ usb2: usb@70f8800 { status = "disabled";
dwc_1: usb@7000000 { - compatible = "snps,dwc3"; - reg = <0x0 0x7000000 0x0 0xcd00>; - interrupts = <GIC_SPI 99 IRQ_TYPE_LEVEL_HIGH>; - phys = <&qusb_phy_1>; - phy-names = "usb2-phy"; - tx-fifo-resize; - snps,is-utmi-l1-suspend; - snps,hird-threshold = /bits/ 8 <0x0>; - snps,dis_u2_susphy_quirk; - snps,dis_u3_susphy_quirk; - dr_mode = "host"; + compatible = "snps,dwc3"; + reg = <0x0 0x07000000 0x0 0xcd00>; + interrupts = <GIC_SPI 99 IRQ_TYPE_LEVEL_HIGH>; + phys = <&qusb_phy_1>; + phy-names = "usb2-phy"; + tx-fifo-resize; + snps,is-utmi-l1-suspend; + snps,hird-threshold = /bits/ 8 <0x0>; + snps,dis_u2_susphy_quirk; + snps,dis_u3_susphy_quirk; + dr_mode = "host"; }; };
ssphy_0: ssphy@78000 { compatible = "qcom,ipq6018-qmp-usb3-phy"; - reg = <0x0 0x78000 0x0 0x1C4>; + reg = <0x0 0x00078000 0x0 0x1c4>; #address-cells = <2>; #size-cells = <2>; ranges; @@ -701,7 +702,7 @@ ssphy_0: ssphy@78000 { usb0_ssphy: phy@78200 { reg = <0x0 0x00078200 0x0 0x130>, /* Tx */ <0x0 0x00078400 0x0 0x200>, /* Rx */ - <0x0 0x00078800 0x0 0x1F8>, /* PCS */ + <0x0 0x00078800 0x0 0x1f8>, /* PCS */ <0x0 0x00078600 0x0 0x044>; /* PCS misc */ #phy-cells = <0>; #clock-cells = <0>; @@ -713,7 +714,7 @@ usb0_ssphy: phy@78200 {
qusb_phy_0: qusb@79000 { compatible = "qcom,ipq6018-qusb2-phy"; - reg = <0x0 0x079000 0x0 0x180>; + reg = <0x0 0x00079000 0x0 0x180>; #phy-cells = <0>;
clocks = <&gcc GCC_USB0_PHY_CFG_AHB_CLK>, @@ -726,7 +727,7 @@ qusb_phy_0: qusb@79000 {
usb3: usb@8af8800 { compatible = "qcom,ipq6018-dwc3", "qcom,dwc3"; - reg = <0x0 0x8AF8800 0x0 0x400>; + reg = <0x0 0x8af8800 0x0 0x400>; #address-cells = <2>; #size-cells = <2>; ranges; @@ -745,14 +746,14 @@ usb3: usb@8af8800 { <&gcc GCC_USB0_MOCK_UTMI_CLK>; assigned-clock-rates = <133330000>, <133330000>, - <20000000>; + <24000000>;
resets = <&gcc GCC_USB0_BCR>; status = "disabled";
dwc_0: usb@8a00000 { compatible = "snps,dwc3"; - reg = <0x0 0x8A00000 0x0 0xcd00>; + reg = <0x0 0x8a00000 0x0 0xcd00>; interrupts = <GIC_SPI 140 IRQ_TYPE_LEVEL_HIGH>; phys = <&qusb_phy_0>, <&usb0_ssphy>; phy-names = "usb2-phy", "usb3-phy"; diff --git a/arch/arm64/boot/dts/qcom/qrb5165-rb5.dts b/arch/arm64/boot/dts/qcom/qrb5165-rb5.dts index 9731a7c63d53..1defbe0404e2 100644 --- a/arch/arm64/boot/dts/qcom/qrb5165-rb5.dts +++ b/arch/arm64/boot/dts/qcom/qrb5165-rb5.dts @@ -63,8 +63,8 @@ led-user4 { function = LED_FUNCTION_INDICATOR; color = <LED_COLOR_ID_GREEN>; gpios = <&pm8150_gpios 10 GPIO_ACTIVE_HIGH>; - linux,default-trigger = "panic-indicator"; default-state = "off"; + panic-indicator; };
led-wlan { diff --git a/arch/arm64/boot/dts/qcom/sc7180.dtsi b/arch/arm64/boot/dts/qcom/sc7180.dtsi index 6f0ee4e13ef1..78e537f1d796 100644 --- a/arch/arm64/boot/dts/qcom/sc7180.dtsi +++ b/arch/arm64/boot/dts/qcom/sc7180.dtsi @@ -3378,7 +3378,7 @@ watchdog@17c10000 { compatible = "qcom,apss-wdt-sc7180", "qcom,kpss-wdt"; reg = <0 0x17c10000 0 0x1000>; clocks = <&sleep_clk>; - interrupts = <GIC_SPI 0 IRQ_TYPE_LEVEL_HIGH>; + interrupts = <GIC_SPI 0 IRQ_TYPE_EDGE_RISING>; };
timer@17c20000{ diff --git a/arch/arm64/boot/dts/qcom/sc7280-chrome-common.dtsi b/arch/arm64/boot/dts/qcom/sc7280-chrome-common.dtsi index 25f31c81b2b7..efe6ea538ad2 100644 --- a/arch/arm64/boot/dts/qcom/sc7280-chrome-common.dtsi +++ b/arch/arm64/boot/dts/qcom/sc7280-chrome-common.dtsi @@ -56,6 +56,26 @@ mba_mem: memory@9c700000 { }; };
+&lpass_aon { + status = "okay"; +}; + +&lpass_core { + status = "okay"; +}; + +&lpass_hm { + status = "okay"; +}; + +&lpasscc { + status = "okay"; +}; + +&pdc_reset { + status = "okay"; +}; + /* The PMIC PON code isn't compatible w/ how Chrome EC/BIOS handle things. */ &pmk8350_pon { status = "disabled"; @@ -93,6 +113,10 @@ &rmtfs_mem { reg = <0x0 0x9c900000 0x0 0x800000>; };
+&watchdog { + status = "okay"; +}; + &wifi { status = "okay";
diff --git a/arch/arm64/boot/dts/qcom/sc7280.dtsi b/arch/arm64/boot/dts/qcom/sc7280.dtsi index aea356c63b9a..7fc8c2045022 100644 --- a/arch/arm64/boot/dts/qcom/sc7280.dtsi +++ b/arch/arm64/boot/dts/qcom/sc7280.dtsi @@ -888,6 +888,7 @@ sdhc_1: mmc@7c4000 {
bus-width = <8>; supports-cqe; + dma-coherent;
qcom,dll-config = <0x0007642c>; qcom,ddr-config = <0x80040868>; @@ -2187,6 +2188,7 @@ lpasscc: lpasscc@3000000 { clocks = <&gcc GCC_CFG_NOC_LPASS_CLK>; clock-names = "iface"; #clock-cells = <1>; + status = "reserved"; /* Owned by ADSP firmware */ };
lpass_rx_macro: codec@3200000 { @@ -2339,6 +2341,7 @@ lpass_aon: clock-controller@3380000 { clock-names = "bi_tcxo", "bi_tcxo_ao", "iface"; #clock-cells = <1>; #power-domain-cells = <1>; + status = "reserved"; /* Owned by ADSP firmware */ };
lpass_core: clock-controller@3900000 { @@ -2349,6 +2352,7 @@ lpass_core: clock-controller@3900000 { power-domains = <&lpass_hm LPASS_CORE_CC_LPASS_CORE_HM_GDSC>; #clock-cells = <1>; #power-domain-cells = <1>; + status = "reserved"; /* Owned by ADSP firmware */ };
lpass_cpu: audio@3987000 { @@ -2419,6 +2423,7 @@ lpass_hm: clock-controller@3c00000 { clock-names = "bi_tcxo"; #clock-cells = <1>; #power-domain-cells = <1>; + status = "reserved"; /* Owned by ADSP firmware */ };
lpass_ag_noc: interconnect@3c40000 { @@ -2529,7 +2534,8 @@ gpu: gpu@3d00000 { "cx_mem", "cx_dbgc"; interrupts = <GIC_SPI 300 IRQ_TYPE_LEVEL_HIGH>; - iommus = <&adreno_smmu 0 0x401>; + iommus = <&adreno_smmu 0 0x400>, + <&adreno_smmu 1 0x400>; operating-points-v2 = <&gpu_opp_table>; qcom,gmu = <&gmu>; interconnects = <&gem_noc MASTER_GFX3D 0 &mc_virt SLAVE_EBI1 0>; @@ -2696,6 +2702,7 @@ adreno_smmu: iommu@3da0000 { "gpu_cc_hub_aon_clk";
power-domains = <&gpucc GPU_CC_CX_GDSC>; + dma-coherent; };
remoteproc_mpss: remoteproc@4080000 { @@ -3265,6 +3272,7 @@ sdhc_2: mmc@8804000 { operating-points-v2 = <&sdhc2_opp_table>;
bus-width = <4>; + dma-coherent;
qcom,dll-config = <0x0007642c>;
@@ -3386,8 +3394,8 @@ usb_2: usb@8cf8800 { assigned-clock-rates = <19200000>, <200000000>;
interrupts-extended = <&intc GIC_SPI 240 IRQ_TYPE_LEVEL_HIGH>, - <&pdc 12 IRQ_TYPE_EDGE_RISING>, - <&pdc 13 IRQ_TYPE_EDGE_RISING>; + <&pdc 12 IRQ_TYPE_EDGE_BOTH>, + <&pdc 13 IRQ_TYPE_EDGE_BOTH>; interrupt-names = "hs_phy_irq", "dp_hs_phy_irq", "dm_hs_phy_irq"; @@ -4195,6 +4203,7 @@ pdc_reset: reset-controller@b5e0000 { compatible = "qcom,sc7280-pdc-global"; reg = <0 0x0b5e0000 0 0x20000>; #reset-cells = <1>; + status = "reserved"; /* Owned by firmware */ };
tsens0: thermal-sensor@c263000 { @@ -5186,11 +5195,12 @@ gic-its@17a40000 { }; };
- watchdog@17c10000 { + watchdog: watchdog@17c10000 { compatible = "qcom,apss-wdt-sc7280", "qcom,kpss-wdt"; reg = <0 0x17c10000 0 0x1000>; clocks = <&sleep_clk>; - interrupts = <GIC_SPI 0 IRQ_TYPE_LEVEL_HIGH>; + interrupts = <GIC_SPI 0 IRQ_TYPE_EDGE_RISING>; + status = "reserved"; /* Owned by Gunyah hyp */ };
timer@17c20000 { diff --git a/arch/arm64/boot/dts/qcom/sc8280xp.dtsi b/arch/arm64/boot/dts/qcom/sc8280xp.dtsi index 405835ad28bc..7e3aaf5de3f5 100644 --- a/arch/arm64/boot/dts/qcom/sc8280xp.dtsi +++ b/arch/arm64/boot/dts/qcom/sc8280xp.dtsi @@ -1653,7 +1653,7 @@ watchdog@17c10000 { compatible = "qcom,apss-wdt-sc8280xp", "qcom,kpss-wdt"; reg = <0 0x17c10000 0 0x1000>; clocks = <&sleep_clk>; - interrupts = <GIC_SPI 0 IRQ_TYPE_LEVEL_HIGH>; + interrupts = <GIC_SPI 0 IRQ_TYPE_EDGE_RISING>; };
timer@17c20000 { diff --git a/arch/arm64/boot/dts/qcom/sdm845-db845c.dts b/arch/arm64/boot/dts/qcom/sdm845-db845c.dts index 8c9ccf5b4ea4..135ff4368c4a 100644 --- a/arch/arm64/boot/dts/qcom/sdm845-db845c.dts +++ b/arch/arm64/boot/dts/qcom/sdm845-db845c.dts @@ -66,8 +66,8 @@ led-0 { function = LED_FUNCTION_INDICATOR; color = <LED_COLOR_ID_GREEN>; gpios = <&pm8998_gpio 13 GPIO_ACTIVE_HIGH>; - linux,default-trigger = "panic-indicator"; default-state = "off"; + panic-indicator; };
led-1 { diff --git a/arch/arm64/boot/dts/qcom/sdm845.dtsi b/arch/arm64/boot/dts/qcom/sdm845.dtsi index 52c9f5639f8a..1e6841902900 100644 --- a/arch/arm64/boot/dts/qcom/sdm845.dtsi +++ b/arch/arm64/boot/dts/qcom/sdm845.dtsi @@ -5019,7 +5019,7 @@ watchdog@17980000 { compatible = "qcom,apss-wdt-sdm845", "qcom,kpss-wdt"; reg = <0 0x17980000 0 0x1000>; clocks = <&sleep_clk>; - interrupts = <GIC_SPI 0 IRQ_TYPE_LEVEL_HIGH>; + interrupts = <GIC_SPI 0 IRQ_TYPE_EDGE_RISING>; };
apss_shared: mailbox@17990000 { diff --git a/arch/arm64/boot/dts/qcom/sm6350.dtsi b/arch/arm64/boot/dts/qcom/sm6350.dtsi index cea7ca3f326f..9da373090593 100644 --- a/arch/arm64/boot/dts/qcom/sm6350.dtsi +++ b/arch/arm64/boot/dts/qcom/sm6350.dtsi @@ -1462,7 +1462,7 @@ watchdog@17c10000 { compatible = "qcom,apss-wdt-sm6350", "qcom,kpss-wdt"; reg = <0 0x17c10000 0 0x1000>; clocks = <&sleep_clk>; - interrupts = <GIC_SPI 0 IRQ_TYPE_LEVEL_HIGH>; + interrupts = <GIC_SPI 0 IRQ_TYPE_EDGE_RISING>; };
timer@17c20000 { diff --git a/arch/arm64/boot/dts/qcom/sm8150-hdk.dts b/arch/arm64/boot/dts/qcom/sm8150-hdk.dts index 3331ee957d64..368da4c7f41b 100644 --- a/arch/arm64/boot/dts/qcom/sm8150-hdk.dts +++ b/arch/arm64/boot/dts/qcom/sm8150-hdk.dts @@ -126,8 +126,6 @@ vdda_qrefs_0p875_5: vdda_sp_sensor: vdda_ufs_2ln_core_1: vdda_ufs_2ln_core_2: - vdda_usb_ss_dp_core_1: - vdda_usb_ss_dp_core_2: vdda_qlink_lv: vdda_qlink_lv_ck: vreg_l5a_0p875: ldo5 { @@ -209,6 +207,12 @@ vreg_l17a_3p0: ldo17 { regulator-max-microvolt = <3008000>; regulator-initial-mode = <RPMH_REGULATOR_MODE_HPM>; }; + + vreg_l18a_0p8: ldo18 { + regulator-min-microvolt = <880000>; + regulator-max-microvolt = <880000>; + regulator-initial-mode = <RPMH_REGULATOR_MODE_HPM>; + }; };
pm8150l-rpmh-regulators { @@ -439,13 +443,13 @@ &usb_2_hsphy { &usb_1_qmpphy { status = "okay"; vdda-phy-supply = <&vreg_l3c_1p2>; - vdda-pll-supply = <&vdda_usb_ss_dp_core_1>; + vdda-pll-supply = <&vreg_l18a_0p8>; };
&usb_2_qmpphy { status = "okay"; vdda-phy-supply = <&vreg_l3c_1p2>; - vdda-pll-supply = <&vdda_usb_ss_dp_core_1>; + vdda-pll-supply = <&vreg_l5a_0p875>; };
&usb_1 { diff --git a/arch/arm64/boot/dts/qcom/sm8150.dtsi b/arch/arm64/boot/dts/qcom/sm8150.dtsi index c586378fc6bc..c3c12b0cd416 100644 --- a/arch/arm64/boot/dts/qcom/sm8150.dtsi +++ b/arch/arm64/boot/dts/qcom/sm8150.dtsi @@ -3940,7 +3940,7 @@ watchdog@17c10000 { compatible = "qcom,apss-wdt-sm8150", "qcom,kpss-wdt"; reg = <0 0x17c10000 0 0x1000>; clocks = <&sleep_clk>; - interrupts = <GIC_SPI 0 IRQ_TYPE_LEVEL_HIGH>; + interrupts = <GIC_SPI 0 IRQ_TYPE_EDGE_RISING>; };
timer@17c20000 { diff --git a/arch/arm64/boot/dts/qcom/sm8250.dtsi b/arch/arm64/boot/dts/qcom/sm8250.dtsi index 4d9b30f0b284..3d02adbc0b62 100644 --- a/arch/arm64/boot/dts/qcom/sm8250.dtsi +++ b/arch/arm64/boot/dts/qcom/sm8250.dtsi @@ -4879,7 +4879,7 @@ watchdog@17c10000 { compatible = "qcom,apss-wdt-sm8250", "qcom,kpss-wdt"; reg = <0 0x17c10000 0 0x1000>; clocks = <&sleep_clk>; - interrupts = <GIC_SPI 0 IRQ_TYPE_LEVEL_HIGH>; + interrupts = <GIC_SPI 0 IRQ_TYPE_EDGE_RISING>; };
timer@17c20000 { diff --git a/arch/arm64/boot/dts/qcom/sm8350.dtsi b/arch/arm64/boot/dts/qcom/sm8350.dtsi index 793768a2c9e1..888bf4cd73c3 100644 --- a/arch/arm64/boot/dts/qcom/sm8350.dtsi +++ b/arch/arm64/boot/dts/qcom/sm8350.dtsi @@ -903,9 +903,9 @@ spi19: spi@894000 { }; };
- gpi_dma0: dma-controller@9800000 { + gpi_dma0: dma-controller@900000 { compatible = "qcom,sm8350-gpi-dma", "qcom,sm6350-gpi-dma"; - reg = <0 0x09800000 0 0x60000>; + reg = <0 0x00900000 0 0x60000>; interrupts = <GIC_SPI 244 IRQ_TYPE_LEVEL_HIGH>, <GIC_SPI 245 IRQ_TYPE_LEVEL_HIGH>, <GIC_SPI 246 IRQ_TYPE_LEVEL_HIGH>, diff --git a/arch/arm64/boot/dts/renesas/r8a779g0-white-hawk-cpu.dtsi b/arch/arm64/boot/dts/renesas/r8a779g0-white-hawk-cpu.dtsi index 895f0bd9f754..541b1e73b65e 100644 --- a/arch/arm64/boot/dts/renesas/r8a779g0-white-hawk-cpu.dtsi +++ b/arch/arm64/boot/dts/renesas/r8a779g0-white-hawk-cpu.dtsi @@ -125,6 +125,9 @@ &extalr_clk { };
&hscif0 { + pinctrl-0 = <&hscif0_pins>; + pinctrl-names = "default"; + status = "okay"; };
diff --git a/arch/arm64/boot/dts/ti/k3-am62a-main.dtsi b/arch/arm64/boot/dts/ti/k3-am62a-main.dtsi index bc4b50bcd177..9301ea388802 100644 --- a/arch/arm64/boot/dts/ti/k3-am62a-main.dtsi +++ b/arch/arm64/boot/dts/ti/k3-am62a-main.dtsi @@ -245,7 +245,7 @@ main_gpio0: gpio@600000 { <193>, <194>, <195>; interrupt-controller; #interrupt-cells = <2>; - ti,ngpio = <87>; + ti,ngpio = <92>; ti,davinci-gpio-unbanked = <0>; power-domains = <&k3_pds 77 TI_SCI_PD_EXCLUSIVE>; clocks = <&k3_clks 77 0>; @@ -263,7 +263,7 @@ main_gpio1: gpio@601000 { <183>, <184>, <185>; interrupt-controller; #interrupt-cells = <2>; - ti,ngpio = <88>; + ti,ngpio = <52>; ti,davinci-gpio-unbanked = <0>; power-domains = <&k3_pds 78 TI_SCI_PD_EXCLUSIVE>; clocks = <&k3_clks 78 0>; diff --git a/arch/arm64/boot/dts/ti/k3-am65-main.dtsi b/arch/arm64/boot/dts/ti/k3-am65-main.dtsi index ebb1c5ce7aec..83dd8993027a 100644 --- a/arch/arm64/boot/dts/ti/k3-am65-main.dtsi +++ b/arch/arm64/boot/dts/ti/k3-am65-main.dtsi @@ -856,7 +856,7 @@ dss: dss@4a00000 { assigned-clocks = <&k3_clks 67 2>; assigned-clock-parents = <&k3_clks 67 5>;
- interrupts = <GIC_SPI 166 IRQ_TYPE_EDGE_RISING>; + interrupts = <GIC_SPI 166 IRQ_TYPE_LEVEL_HIGH>;
dma-coherent;
diff --git a/arch/arm64/kvm/vgic/vgic-its.c b/arch/arm64/kvm/vgic/vgic-its.c index 00ad6587bee9..3c344e4cd4ca 100644 --- a/arch/arm64/kvm/vgic/vgic-its.c +++ b/arch/arm64/kvm/vgic/vgic-its.c @@ -584,7 +584,11 @@ static struct vgic_irq *vgic_its_check_cache(struct kvm *kvm, phys_addr_t db, unsigned long flags;
raw_spin_lock_irqsave(&dist->lpi_list_lock, flags); + irq = __vgic_its_check_cache(dist, db, devid, eventid); + if (irq) + vgic_get_irq_kref(irq); + raw_spin_unlock_irqrestore(&dist->lpi_list_lock, flags);
return irq; @@ -763,6 +767,7 @@ int vgic_its_inject_cached_translation(struct kvm *kvm, struct kvm_msi *msi) raw_spin_lock_irqsave(&irq->irq_lock, flags); irq->pending_latch = true; vgic_queue_irq_unlock(kvm, irq, flags); + vgic_put_irq(kvm, irq);
return 0; } diff --git a/arch/arm64/kvm/vgic/vgic-mmio-v3.c b/arch/arm64/kvm/vgic/vgic-mmio-v3.c index 871a45d4fc84..ae5a3a717655 100644 --- a/arch/arm64/kvm/vgic/vgic-mmio-v3.c +++ b/arch/arm64/kvm/vgic/vgic-mmio-v3.c @@ -365,19 +365,26 @@ static int vgic_v3_uaccess_write_pending(struct kvm_vcpu *vcpu, struct vgic_irq *irq = vgic_get_irq(vcpu->kvm, vcpu, intid + i);
raw_spin_lock_irqsave(&irq->irq_lock, flags); - if (test_bit(i, &val)) { - /* - * pending_latch is set irrespective of irq type - * (level or edge) to avoid dependency that VM should - * restore irq config before pending info. - */ - irq->pending_latch = true; - vgic_queue_irq_unlock(vcpu->kvm, irq, flags); - } else { + + /* + * pending_latch is set irrespective of irq type + * (level or edge) to avoid dependency that VM should + * restore irq config before pending info. + */ + irq->pending_latch = test_bit(i, &val); + + if (irq->hw && vgic_irq_is_sgi(irq->intid)) { + irq_set_irqchip_state(irq->host_irq, + IRQCHIP_STATE_PENDING, + irq->pending_latch); irq->pending_latch = false; - raw_spin_unlock_irqrestore(&irq->irq_lock, flags); }
+ if (irq->pending_latch) + vgic_queue_irq_unlock(vcpu->kvm, irq, flags); + else + raw_spin_unlock_irqrestore(&irq->irq_lock, flags); + vgic_put_irq(vcpu->kvm, irq); }
diff --git a/arch/csky/include/asm/jump_label.h b/arch/csky/include/asm/jump_label.h index d488ba6084bc..98a3f4b168bd 100644 --- a/arch/csky/include/asm/jump_label.h +++ b/arch/csky/include/asm/jump_label.h @@ -43,5 +43,10 @@ static __always_inline bool arch_static_branch_jump(struct static_key *key, return true; }
+enum jump_label_type; +void arch_jump_label_transform_static(struct jump_entry *entry, + enum jump_label_type type); +#define arch_jump_label_transform_static arch_jump_label_transform_static + #endif /* __ASSEMBLY__ */ #endif /* __ASM_CSKY_JUMP_LABEL_H */ diff --git a/arch/loongarch/include/asm/elf.h b/arch/loongarch/include/asm/elf.h index 9b16a3b8e706..f16bd42456e4 100644 --- a/arch/loongarch/include/asm/elf.h +++ b/arch/loongarch/include/asm/elf.h @@ -241,8 +241,6 @@ void loongarch_dump_regs64(u64 *uregs, const struct pt_regs *regs); do { \ current->thread.vdso = &vdso_info; \ \ - loongarch_set_personality_fcsr(state); \ - \ if (personality(current->personality) != PER_LINUX) \ set_personality(PER_LINUX); \ } while (0) @@ -259,7 +257,6 @@ do { \ clear_thread_flag(TIF_32BIT_ADDR); \ \ current->thread.vdso = &vdso_info; \ - loongarch_set_personality_fcsr(state); \ \ p = personality(current->personality); \ if (p != PER_LINUX32 && p != PER_LINUX) \ @@ -340,6 +337,4 @@ extern int arch_elf_pt_proc(void *ehdr, void *phdr, struct file *elf, extern int arch_check_elf(void *ehdr, bool has_interpreter, void *interp_ehdr, struct arch_elf_state *state);
-extern void loongarch_set_personality_fcsr(struct arch_elf_state *state); - #endif /* _ASM_ELF_H */ diff --git a/arch/loongarch/kernel/elf.c b/arch/loongarch/kernel/elf.c index 183e94fc9c69..0fa81ced28dc 100644 --- a/arch/loongarch/kernel/elf.c +++ b/arch/loongarch/kernel/elf.c @@ -23,8 +23,3 @@ int arch_check_elf(void *_ehdr, bool has_interpreter, void *_interp_ehdr, { return 0; } - -void loongarch_set_personality_fcsr(struct arch_elf_state *state) -{ - current->thread.fpu.fcsr = boot_cpu_data.fpu_csr0; -} diff --git a/arch/loongarch/kernel/process.c b/arch/loongarch/kernel/process.c index 90a5de746332..1259bc312979 100644 --- a/arch/loongarch/kernel/process.c +++ b/arch/loongarch/kernel/process.c @@ -82,6 +82,7 @@ void start_thread(struct pt_regs *regs, unsigned long pc, unsigned long sp) euen = regs->csr_euen & ~(CSR_EUEN_FPEN); regs->csr_euen = euen; lose_fpu(0); + current->thread.fpu.fcsr = boot_cpu_data.fpu_csr0;
clear_thread_flag(TIF_LSX_CTX_LIVE); clear_thread_flag(TIF_LASX_CTX_LIVE); diff --git a/arch/loongarch/net/bpf_jit.c b/arch/loongarch/net/bpf_jit.c index 40ed49d9adff..4e86441e6319 100644 --- a/arch/loongarch/net/bpf_jit.c +++ b/arch/loongarch/net/bpf_jit.c @@ -402,7 +402,6 @@ static int build_insn(const struct bpf_insn *insn, struct jit_ctx *ctx, bool ext const u8 dst = regmap[insn->dst_reg]; const s16 off = insn->off; const s32 imm = insn->imm; - const u64 imm64 = (u64)(insn + 1)->imm << 32 | (u32)insn->imm; const bool is32 = BPF_CLASS(insn->code) == BPF_ALU || BPF_CLASS(insn->code) == BPF_JMP32;
switch (code) { @@ -806,8 +805,12 @@ static int build_insn(const struct bpf_insn *insn, struct jit_ctx *ctx, bool ext
/* dst = imm64 */ case BPF_LD | BPF_IMM | BPF_DW: + { + const u64 imm64 = (u64)(insn + 1)->imm << 32 | (u32)insn->imm; + move_imm(ctx, dst, imm64, is32); return 1; + }
/* dst = *(size *)(src + off) */ case BPF_LDX | BPF_MEM | BPF_B: diff --git a/arch/mips/alchemy/devboards/db1200.c b/arch/mips/alchemy/devboards/db1200.c index f521874ebb07..67f067706af2 100644 --- a/arch/mips/alchemy/devboards/db1200.c +++ b/arch/mips/alchemy/devboards/db1200.c @@ -847,7 +847,7 @@ int __init db1200_dev_setup(void) i2c_register_board_info(0, db1200_i2c_devs, ARRAY_SIZE(db1200_i2c_devs)); spi_register_board_info(db1200_spi_devs, - ARRAY_SIZE(db1200_i2c_devs)); + ARRAY_SIZE(db1200_spi_devs));
/* SWITCHES: S6.8 I2C/SPI selector (OFF=I2C ON=SPI) * S6.7 AC97/I2S selector (OFF=AC97 ON=I2S) diff --git a/arch/mips/alchemy/devboards/db1550.c b/arch/mips/alchemy/devboards/db1550.c index fd91d9c9a252..6c6837181f55 100644 --- a/arch/mips/alchemy/devboards/db1550.c +++ b/arch/mips/alchemy/devboards/db1550.c @@ -589,7 +589,7 @@ int __init db1550_dev_setup(void) i2c_register_board_info(0, db1550_i2c_devs, ARRAY_SIZE(db1550_i2c_devs)); spi_register_board_info(db1550_spi_devs, - ARRAY_SIZE(db1550_i2c_devs)); + ARRAY_SIZE(db1550_spi_devs));
c = clk_get(NULL, "psc0_intclk"); if (!IS_ERR(c)) { diff --git a/arch/mips/include/asm/dmi.h b/arch/mips/include/asm/dmi.h index 27415a288adf..dc397f630c66 100644 --- a/arch/mips/include/asm/dmi.h +++ b/arch/mips/include/asm/dmi.h @@ -5,7 +5,7 @@ #include <linux/io.h> #include <linux/memblock.h>
-#define dmi_early_remap(x, l) ioremap_cache(x, l) +#define dmi_early_remap(x, l) ioremap(x, l) #define dmi_early_unmap(x, l) iounmap(x) #define dmi_remap(x, l) ioremap_cache(x, l) #define dmi_unmap(x) iounmap(x) diff --git a/arch/mips/kernel/setup.c b/arch/mips/kernel/setup.c index 7c540572f1f7..e46e7ec76b4f 100644 --- a/arch/mips/kernel/setup.c +++ b/arch/mips/kernel/setup.c @@ -326,11 +326,11 @@ static void __init bootmem_init(void) panic("Incorrect memory mapping !!!");
if (max_pfn > PFN_DOWN(HIGHMEM_START)) { + max_low_pfn = PFN_DOWN(HIGHMEM_START); #ifdef CONFIG_HIGHMEM - highstart_pfn = PFN_DOWN(HIGHMEM_START); + highstart_pfn = max_low_pfn; highend_pfn = max_pfn; #else - max_low_pfn = PFN_DOWN(HIGHMEM_START); max_pfn = max_low_pfn; #endif } diff --git a/arch/mips/kernel/smp.c b/arch/mips/kernel/smp.c index 1d93b85271ba..002c91fcb842 100644 --- a/arch/mips/kernel/smp.c +++ b/arch/mips/kernel/smp.c @@ -333,10 +333,11 @@ early_initcall(mips_smp_ipi_init); */ asmlinkage void start_secondary(void) { - unsigned int cpu; + unsigned int cpu = raw_smp_processor_id();
cpu_probe(); per_cpu_trap_init(false); + rcu_cpu_starting(cpu); mips_clockevent_init(); mp_ops->init_secondary(); cpu_report(); @@ -348,7 +349,6 @@ asmlinkage void start_secondary(void) */
calibrate_delay(); - cpu = smp_processor_id(); cpu_data[cpu].udelay_val = loops_per_jiffy;
set_cpu_sibling_map(cpu); diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index 6050e6e10d32..2c94f9cf1ce0 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig @@ -806,6 +806,7 @@ config THREAD_SHIFT int "Thread shift" if EXPERT range 13 15 default "15" if PPC_256K_PAGES + default "15" if PPC_PSERIES || PPC_POWERNV default "14" if PPC64 default "13" help diff --git a/arch/powerpc/Makefile b/arch/powerpc/Makefile index 054844153b1f..487e4967b60d 100644 --- a/arch/powerpc/Makefile +++ b/arch/powerpc/Makefile @@ -42,18 +42,13 @@ machine-$(CONFIG_PPC64) += 64 machine-$(CONFIG_CPU_LITTLE_ENDIAN) += le UTS_MACHINE := $(subst $(space),,$(machine-y))
-# XXX This needs to be before we override LD below -ifdef CONFIG_PPC32 -KBUILD_LDFLAGS_MODULE += arch/powerpc/lib/crtsavres.o -else -ifeq ($(call ld-ifversion, -ge, 22500, y),y) +ifeq ($(CONFIG_PPC64)$(CONFIG_LD_IS_BFD),yy) # Have the linker provide sfpr if possible. # There is a corresponding test in arch/powerpc/lib/Makefile KBUILD_LDFLAGS_MODULE += --save-restore-funcs else KBUILD_LDFLAGS_MODULE += arch/powerpc/lib/crtsavres.o endif -endif
ifdef CONFIG_CPU_LITTLE_ENDIAN KBUILD_CFLAGS += -mlittle-endian @@ -391,17 +386,7 @@ endif endif
PHONY += checkbin -# Check toolchain versions: -# - gcc-4.6 is the minimum kernel-wide version so nothing required. checkbin: - @if test "x${CONFIG_LD_IS_LLD}" != "xy" -a \ - "x$(call ld-ifversion, -le, 22400, y)" = "xy" ; then \ - echo -n '*** binutils 2.24 miscompiles weak symbols ' ; \ - echo 'in some circumstances.' ; \ - echo '*** binutils 2.23 do not define the TOC symbol ' ; \ - echo -n '*** Please use a different binutils version.' ; \ - false ; \ - fi @if test "x${CONFIG_FTRACE_MCOUNT_USE_RECORDMCOUNT}" = "xy" -a \ "x${CONFIG_LD_IS_BFD}" = "xy" -a \ "${CONFIG_LD_VERSION}" = "23700" ; then \ diff --git a/arch/powerpc/lib/Makefile b/arch/powerpc/lib/Makefile index 8560c912186d..9b394bab17eb 100644 --- a/arch/powerpc/lib/Makefile +++ b/arch/powerpc/lib/Makefile @@ -42,8 +42,8 @@ obj-$(CONFIG_FUNCTION_ERROR_INJECTION) += error-inject.o # 64-bit linker creates .sfpr on demand for final link (vmlinux), # so it is only needed for modules, and only for older linkers which # do not support --save-restore-funcs -ifeq ($(call ld-ifversion, -lt, 22500, y),y) -extra-$(CONFIG_PPC64) += crtsavres.o +ifndef CONFIG_LD_IS_BFD +always-$(CONFIG_PPC64) += crtsavres.o endif
obj-$(CONFIG_PPC_BOOK3S_64) += copyuser_power7.o copypage_power7.o \ diff --git a/arch/powerpc/perf/imc-pmu.c b/arch/powerpc/perf/imc-pmu.c index ada817c49b72..56d82f7f9734 100644 --- a/arch/powerpc/perf/imc-pmu.c +++ b/arch/powerpc/perf/imc-pmu.c @@ -299,6 +299,8 @@ static int update_events_in_group(struct device_node *node, struct imc_pmu *pmu) attr_group->attrs = attrs; do { ev_val_str = kasprintf(GFP_KERNEL, "event=0x%x", pmu->events[i].value); + if (!ev_val_str) + continue; dev_str = device_str_attr_create(pmu->events[i].name, ev_val_str); if (!dev_str) continue; @@ -306,6 +308,8 @@ static int update_events_in_group(struct device_node *node, struct imc_pmu *pmu) attrs[j++] = dev_str; if (pmu->events[i].scale) { ev_scale_str = kasprintf(GFP_KERNEL, "%s.scale", pmu->events[i].name); + if (!ev_scale_str) + continue; dev_str = device_str_attr_create(ev_scale_str, pmu->events[i].scale); if (!dev_str) continue; @@ -315,6 +319,8 @@ static int update_events_in_group(struct device_node *node, struct imc_pmu *pmu)
if (pmu->events[i].unit) { ev_unit_str = kasprintf(GFP_KERNEL, "%s.unit", pmu->events[i].name); + if (!ev_unit_str) + continue; dev_str = device_str_attr_create(ev_unit_str, pmu->events[i].unit); if (!dev_str) continue; diff --git a/arch/powerpc/platforms/44x/Kconfig b/arch/powerpc/platforms/44x/Kconfig index 25b80cd558f8..fc79f8466933 100644 --- a/arch/powerpc/platforms/44x/Kconfig +++ b/arch/powerpc/platforms/44x/Kconfig @@ -173,6 +173,7 @@ config ISS4xx config CURRITUCK bool "IBM Currituck (476fpe) Support" depends on PPC_47x + select I2C select SWIOTLB select 476FPE select FORCE_PCI diff --git a/arch/powerpc/platforms/powernv/opal-irqchip.c b/arch/powerpc/platforms/powernv/opal-irqchip.c index d55652b5f6fa..391f50535200 100644 --- a/arch/powerpc/platforms/powernv/opal-irqchip.c +++ b/arch/powerpc/platforms/powernv/opal-irqchip.c @@ -275,6 +275,8 @@ int __init opal_event_init(void) else name = kasprintf(GFP_KERNEL, "opal");
+ if (!name) + continue; /* Install interrupt handler */ rc = request_irq(r->start, opal_interrupt, r->flags & IRQD_TRIGGER_MASK, name, NULL); diff --git a/arch/powerpc/platforms/powernv/opal-powercap.c b/arch/powerpc/platforms/powernv/opal-powercap.c index 7bfe4cbeb35a..ea917266aa17 100644 --- a/arch/powerpc/platforms/powernv/opal-powercap.c +++ b/arch/powerpc/platforms/powernv/opal-powercap.c @@ -196,6 +196,12 @@ void __init opal_powercap_init(void)
j = 0; pcaps[i].pg.name = kasprintf(GFP_KERNEL, "%pOFn", node); + if (!pcaps[i].pg.name) { + kfree(pcaps[i].pattrs); + kfree(pcaps[i].pg.attrs); + goto out_pcaps_pattrs; + } + if (has_min) { powercap_add_attr(min, "powercap-min", &pcaps[i].pattrs[j]); diff --git a/arch/powerpc/platforms/powernv/opal-xscom.c b/arch/powerpc/platforms/powernv/opal-xscom.c index 6b4eed2ef4fa..f67235d1ba2c 100644 --- a/arch/powerpc/platforms/powernv/opal-xscom.c +++ b/arch/powerpc/platforms/powernv/opal-xscom.c @@ -165,6 +165,11 @@ static int scom_debug_init_one(struct dentry *root, struct device_node *dn, ent->chip = chip; snprintf(ent->name, 16, "%08x", chip); ent->path.data = (void *)kasprintf(GFP_KERNEL, "%pOF", dn); + if (!ent->path.data) { + kfree(ent); + return -ENOMEM; + } + ent->path.size = strlen((char *)ent->path.data);
dir = debugfs_create_dir(ent->name, root); diff --git a/arch/powerpc/platforms/pseries/hotplug-memory.c b/arch/powerpc/platforms/pseries/hotplug-memory.c index 2e3a317722a8..051a777ba1b2 100644 --- a/arch/powerpc/platforms/pseries/hotplug-memory.c +++ b/arch/powerpc/platforms/pseries/hotplug-memory.c @@ -500,14 +500,15 @@ static int dlpar_memory_remove_by_index(u32 drc_index) } }
- if (!lmb_found) + if (!lmb_found) { + pr_debug("Failed to look up LMB for drc index %x\n", drc_index); rc = -EINVAL; - - if (rc) + } else if (rc) { pr_debug("Failed to hot-remove memory at %llx\n", lmb->base_addr); - else + } else { pr_debug("Memory at %llx was hot-removed\n", lmb->base_addr); + }
return rc; } diff --git a/arch/riscv/include/asm/sections.h b/arch/riscv/include/asm/sections.h index 32336e8a17cb..a393d5035c54 100644 --- a/arch/riscv/include/asm/sections.h +++ b/arch/riscv/include/asm/sections.h @@ -13,6 +13,7 @@ extern char _start_kernel[]; extern char __init_data_begin[], __init_data_end[]; extern char __init_text_begin[], __init_text_end[]; extern char __alt_start[], __alt_end[]; +extern char __exittext_begin[], __exittext_end[];
static inline bool is_va_kernel_text(uintptr_t va) { diff --git a/arch/riscv/include/asm/xip_fixup.h b/arch/riscv/include/asm/xip_fixup.h index d4ffc3c37649..b65bf6306f69 100644 --- a/arch/riscv/include/asm/xip_fixup.h +++ b/arch/riscv/include/asm/xip_fixup.h @@ -13,7 +13,7 @@ add \reg, \reg, t0 .endm .macro XIP_FIXUP_FLASH_OFFSET reg - la t1, __data_loc + la t0, __data_loc REG_L t1, _xip_phys_offset sub \reg, \reg, t1 add \reg, \reg, t0 diff --git a/arch/riscv/kernel/module.c b/arch/riscv/kernel/module.c index 91fe16bfaa07..a331001e33e6 100644 --- a/arch/riscv/kernel/module.c +++ b/arch/riscv/kernel/module.c @@ -424,7 +424,8 @@ void *module_alloc(unsigned long size) { return __vmalloc_node_range(size, 1, MODULES_VADDR, MODULES_END, GFP_KERNEL, - PAGE_KERNEL, 0, NUMA_NO_NODE, + PAGE_KERNEL, VM_FLUSH_RESET_PERMS, + NUMA_NO_NODE, __builtin_return_address(0)); } #endif diff --git a/arch/riscv/kernel/patch.c b/arch/riscv/kernel/patch.c index e099961453cc..160e5c1caa9c 100644 --- a/arch/riscv/kernel/patch.c +++ b/arch/riscv/kernel/patch.c @@ -13,6 +13,7 @@ #include <asm/fixmap.h> #include <asm/ftrace.h> #include <asm/patch.h> +#include <asm/sections.h>
struct patch_insn { void *addr; @@ -23,6 +24,14 @@ struct patch_insn { int riscv_patch_in_stop_machine = false;
#ifdef CONFIG_MMU + +static inline bool is_kernel_exittext(uintptr_t addr) +{ + return system_state < SYSTEM_RUNNING && + addr >= (uintptr_t)__exittext_begin && + addr < (uintptr_t)__exittext_end; +} + /* * The fix_to_virt(, idx) needs a const value (not a dynamic variable of * reg-a0) or BUILD_BUG_ON failed with "idx >= __end_of_fixed_addresses". @@ -33,7 +42,7 @@ static __always_inline void *patch_map(void *addr, const unsigned int fixmap) uintptr_t uintaddr = (uintptr_t) addr; struct page *page;
- if (core_kernel_text(uintaddr)) + if (core_kernel_text(uintaddr) || is_kernel_exittext(uintaddr)) page = phys_to_page(__pa_symbol(addr)); else if (IS_ENABLED(CONFIG_STRICT_MODULE_RWX)) page = vmalloc_to_page(addr); diff --git a/arch/riscv/kernel/vmlinux-xip.lds.S b/arch/riscv/kernel/vmlinux-xip.lds.S index 75e0fa8a700a..24a2fdd3be6a 100644 --- a/arch/riscv/kernel/vmlinux-xip.lds.S +++ b/arch/riscv/kernel/vmlinux-xip.lds.S @@ -29,10 +29,12 @@ SECTIONS HEAD_TEXT_SECTION INIT_TEXT_SECTION(PAGE_SIZE) /* we have to discard exit text and such at runtime, not link time */ + __exittext_begin = .; .exit.text : { EXIT_TEXT } + __exittext_end = .;
.text : { _text = .; diff --git a/arch/riscv/kernel/vmlinux.lds.S b/arch/riscv/kernel/vmlinux.lds.S index 4e6c88aa4d87..d478e063b878 100644 --- a/arch/riscv/kernel/vmlinux.lds.S +++ b/arch/riscv/kernel/vmlinux.lds.S @@ -72,10 +72,12 @@ SECTIONS __soc_builtin_dtb_table_end = .; } /* we have to discard exit text and such at runtime, not link time */ + __exittext_begin = .; .exit.text : { EXIT_TEXT } + __exittext_end = .;
__init_text_end = .; . = ALIGN(SECTION_ALIGN); diff --git a/arch/riscv/mm/pageattr.c b/arch/riscv/mm/pageattr.c index ea3d61de065b..9587e4487415 100644 --- a/arch/riscv/mm/pageattr.c +++ b/arch/riscv/mm/pageattr.c @@ -5,6 +5,7 @@
#include <linux/pagewalk.h> #include <linux/pgtable.h> +#include <linux/vmalloc.h> #include <asm/tlbflush.h> #include <asm/bitops.h> #include <asm/set_memory.h> @@ -25,19 +26,6 @@ static unsigned long set_pageattr_masks(unsigned long val, struct mm_walk *walk) return new_val; }
-static int pageattr_pgd_entry(pgd_t *pgd, unsigned long addr, - unsigned long next, struct mm_walk *walk) -{ - pgd_t val = READ_ONCE(*pgd); - - if (pgd_leaf(val)) { - val = __pgd(set_pageattr_masks(pgd_val(val), walk)); - set_pgd(pgd, val); - } - - return 0; -} - static int pageattr_p4d_entry(p4d_t *p4d, unsigned long addr, unsigned long next, struct mm_walk *walk) { @@ -96,7 +84,6 @@ static int pageattr_pte_hole(unsigned long addr, unsigned long next, }
static const struct mm_walk_ops pageattr_ops = { - .pgd_entry = pageattr_pgd_entry, .p4d_entry = pageattr_p4d_entry, .pud_entry = pageattr_pud_entry, .pmd_entry = pageattr_pmd_entry, @@ -104,12 +91,181 @@ static const struct mm_walk_ops pageattr_ops = { .pte_hole = pageattr_pte_hole, };
+#ifdef CONFIG_64BIT +static int __split_linear_mapping_pmd(pud_t *pudp, + unsigned long vaddr, unsigned long end) +{ + pmd_t *pmdp; + unsigned long next; + + pmdp = pmd_offset(pudp, vaddr); + + do { + next = pmd_addr_end(vaddr, end); + + if (next - vaddr >= PMD_SIZE && + vaddr <= (vaddr & PMD_MASK) && end >= next) + continue; + + if (pmd_leaf(*pmdp)) { + struct page *pte_page; + unsigned long pfn = _pmd_pfn(*pmdp); + pgprot_t prot = __pgprot(pmd_val(*pmdp) & ~_PAGE_PFN_MASK); + pte_t *ptep_new; + int i; + + pte_page = alloc_page(GFP_KERNEL); + if (!pte_page) + return -ENOMEM; + + ptep_new = (pte_t *)page_address(pte_page); + for (i = 0; i < PTRS_PER_PTE; ++i, ++ptep_new) + set_pte(ptep_new, pfn_pte(pfn + i, prot)); + + smp_wmb(); + + set_pmd(pmdp, pfn_pmd(page_to_pfn(pte_page), PAGE_TABLE)); + } + } while (pmdp++, vaddr = next, vaddr != end); + + return 0; +} + +static int __split_linear_mapping_pud(p4d_t *p4dp, + unsigned long vaddr, unsigned long end) +{ + pud_t *pudp; + unsigned long next; + int ret; + + pudp = pud_offset(p4dp, vaddr); + + do { + next = pud_addr_end(vaddr, end); + + if (next - vaddr >= PUD_SIZE && + vaddr <= (vaddr & PUD_MASK) && end >= next) + continue; + + if (pud_leaf(*pudp)) { + struct page *pmd_page; + unsigned long pfn = _pud_pfn(*pudp); + pgprot_t prot = __pgprot(pud_val(*pudp) & ~_PAGE_PFN_MASK); + pmd_t *pmdp_new; + int i; + + pmd_page = alloc_page(GFP_KERNEL); + if (!pmd_page) + return -ENOMEM; + + pmdp_new = (pmd_t *)page_address(pmd_page); + for (i = 0; i < PTRS_PER_PMD; ++i, ++pmdp_new) + set_pmd(pmdp_new, + pfn_pmd(pfn + ((i * PMD_SIZE) >> PAGE_SHIFT), prot)); + + smp_wmb(); + + set_pud(pudp, pfn_pud(page_to_pfn(pmd_page), PAGE_TABLE)); + } + + ret = __split_linear_mapping_pmd(pudp, vaddr, next); + if (ret) + return ret; + } while (pudp++, vaddr = next, vaddr != end); + + return 0; +} + +static int __split_linear_mapping_p4d(pgd_t *pgdp, + unsigned long vaddr, unsigned long end) +{ + p4d_t *p4dp; + unsigned long next; + int ret; + + p4dp = p4d_offset(pgdp, vaddr); + + do { + next = p4d_addr_end(vaddr, end); + + /* + * If [vaddr; end] contains [vaddr & P4D_MASK; next], we don't + * need to split, we'll change the protections on the whole P4D. + */ + if (next - vaddr >= P4D_SIZE && + vaddr <= (vaddr & P4D_MASK) && end >= next) + continue; + + if (p4d_leaf(*p4dp)) { + struct page *pud_page; + unsigned long pfn = _p4d_pfn(*p4dp); + pgprot_t prot = __pgprot(p4d_val(*p4dp) & ~_PAGE_PFN_MASK); + pud_t *pudp_new; + int i; + + pud_page = alloc_page(GFP_KERNEL); + if (!pud_page) + return -ENOMEM; + + /* + * Fill the pud level with leaf puds that have the same + * protections as the leaf p4d. + */ + pudp_new = (pud_t *)page_address(pud_page); + for (i = 0; i < PTRS_PER_PUD; ++i, ++pudp_new) + set_pud(pudp_new, + pfn_pud(pfn + ((i * PUD_SIZE) >> PAGE_SHIFT), prot)); + + /* + * Make sure the pud filling is not reordered with the + * p4d store which could result in seeing a partially + * filled pud level. + */ + smp_wmb(); + + set_p4d(p4dp, pfn_p4d(page_to_pfn(pud_page), PAGE_TABLE)); + } + + ret = __split_linear_mapping_pud(p4dp, vaddr, next); + if (ret) + return ret; + } while (p4dp++, vaddr = next, vaddr != end); + + return 0; +} + +static int __split_linear_mapping_pgd(pgd_t *pgdp, + unsigned long vaddr, + unsigned long end) +{ + unsigned long next; + int ret; + + do { + next = pgd_addr_end(vaddr, end); + /* We never use PGD mappings for the linear mapping */ + ret = __split_linear_mapping_p4d(pgdp, vaddr, next); + if (ret) + return ret; + } while (pgdp++, vaddr = next, vaddr != end); + + return 0; +} + +static int split_linear_mapping(unsigned long start, unsigned long end) +{ + return __split_linear_mapping_pgd(pgd_offset_k(start), start, end); +} +#endif /* CONFIG_64BIT */ + static int __set_memory(unsigned long addr, int numpages, pgprot_t set_mask, pgprot_t clear_mask) { int ret; unsigned long start = addr; unsigned long end = start + PAGE_SIZE * numpages; + unsigned long __maybe_unused lm_start; + unsigned long __maybe_unused lm_end; struct pageattr_masks masks = { .set_mask = set_mask, .clear_mask = clear_mask @@ -119,11 +275,72 @@ static int __set_memory(unsigned long addr, int numpages, pgprot_t set_mask, return 0;
mmap_write_lock(&init_mm); + +#ifdef CONFIG_64BIT + /* + * We are about to change the permissions of a kernel mapping, we must + * apply the same changes to its linear mapping alias, which may imply + * splitting a huge mapping. + */ + + if (is_vmalloc_or_module_addr((void *)start)) { + struct vm_struct *area = NULL; + int i, page_start; + + area = find_vm_area((void *)start); + page_start = (start - (unsigned long)area->addr) >> PAGE_SHIFT; + + for (i = page_start; i < page_start + numpages; ++i) { + lm_start = (unsigned long)page_address(area->pages[i]); + lm_end = lm_start + PAGE_SIZE; + + ret = split_linear_mapping(lm_start, lm_end); + if (ret) + goto unlock; + + ret = walk_page_range_novma(&init_mm, lm_start, lm_end, + &pageattr_ops, NULL, &masks); + if (ret) + goto unlock; + } + } else if (is_kernel_mapping(start) || is_linear_mapping(start)) { + if (is_kernel_mapping(start)) { + lm_start = (unsigned long)lm_alias(start); + lm_end = (unsigned long)lm_alias(end); + } else { + lm_start = start; + lm_end = end; + } + + ret = split_linear_mapping(lm_start, lm_end); + if (ret) + goto unlock; + + ret = walk_page_range_novma(&init_mm, lm_start, lm_end, + &pageattr_ops, NULL, &masks); + if (ret) + goto unlock; + } + ret = walk_page_range_novma(&init_mm, start, end, &pageattr_ops, NULL, &masks); + +unlock: + mmap_write_unlock(&init_mm); + + /* + * We can't use flush_tlb_kernel_range() here as we may have split a + * hugepage that is larger than that, so let's flush everything. + */ + flush_tlb_all(); +#else + ret = walk_page_range_novma(&init_mm, start, end, &pageattr_ops, NULL, + &masks); + mmap_write_unlock(&init_mm);
flush_tlb_kernel_range(start, end); +#endif
return ret; } @@ -158,36 +375,14 @@ int set_memory_nx(unsigned long addr, int numpages)
int set_direct_map_invalid_noflush(struct page *page) { - int ret; - unsigned long start = (unsigned long)page_address(page); - unsigned long end = start + PAGE_SIZE; - struct pageattr_masks masks = { - .set_mask = __pgprot(0), - .clear_mask = __pgprot(_PAGE_PRESENT) - }; - - mmap_read_lock(&init_mm); - ret = walk_page_range(&init_mm, start, end, &pageattr_ops, &masks); - mmap_read_unlock(&init_mm); - - return ret; + return __set_memory((unsigned long)page_address(page), 1, + __pgprot(0), __pgprot(_PAGE_PRESENT)); }
int set_direct_map_default_noflush(struct page *page) { - int ret; - unsigned long start = (unsigned long)page_address(page); - unsigned long end = start + PAGE_SIZE; - struct pageattr_masks masks = { - .set_mask = PAGE_KERNEL, - .clear_mask = __pgprot(0) - }; - - mmap_read_lock(&init_mm); - ret = walk_page_range(&init_mm, start, end, &pageattr_ops, &masks); - mmap_read_unlock(&init_mm); - - return ret; + return __set_memory((unsigned long)page_address(page), 1, + PAGE_KERNEL, __pgprot(_PAGE_EXEC)); }
#ifdef CONFIG_DEBUG_PAGEALLOC diff --git a/arch/s390/include/asm/pci_io.h b/arch/s390/include/asm/pci_io.h index 287bb88f7698..2686bee800e3 100644 --- a/arch/s390/include/asm/pci_io.h +++ b/arch/s390/include/asm/pci_io.h @@ -11,6 +11,8 @@ /* I/O size constraints */ #define ZPCI_MAX_READ_SIZE 8 #define ZPCI_MAX_WRITE_SIZE 128 +#define ZPCI_BOUNDARY_SIZE (1 << 12) +#define ZPCI_BOUNDARY_MASK (ZPCI_BOUNDARY_SIZE - 1)
/* I/O Map */ #define ZPCI_IOMAP_SHIFT 48 @@ -125,16 +127,18 @@ static inline int zpci_read_single(void *dst, const volatile void __iomem *src, int zpci_write_block(volatile void __iomem *dst, const void *src, unsigned long len);
-static inline u8 zpci_get_max_write_size(u64 src, u64 dst, int len, int max) +static inline int zpci_get_max_io_size(u64 src, u64 dst, int len, int max) { - int count = len > max ? max : len, size = 1; + int offset = dst & ZPCI_BOUNDARY_MASK; + int size;
- while (!(src & 0x1) && !(dst & 0x1) && ((size << 1) <= count)) { - dst = dst >> 1; - src = src >> 1; - size = size << 1; - } - return size; + size = min3(len, ZPCI_BOUNDARY_SIZE - offset, max); + if (IS_ALIGNED(src, 8) && IS_ALIGNED(dst, 8) && IS_ALIGNED(size, 8)) + return size; + + if (size >= 8) + return 8; + return rounddown_pow_of_two(size); }
static inline int zpci_memcpy_fromio(void *dst, @@ -144,9 +148,9 @@ static inline int zpci_memcpy_fromio(void *dst, int size, rc = 0;
while (n > 0) { - size = zpci_get_max_write_size((u64 __force) src, - (u64) dst, n, - ZPCI_MAX_READ_SIZE); + size = zpci_get_max_io_size((u64 __force) src, + (u64) dst, n, + ZPCI_MAX_READ_SIZE); rc = zpci_read_single(dst, src, size); if (rc) break; @@ -166,9 +170,9 @@ static inline int zpci_memcpy_toio(volatile void __iomem *dst, return -EINVAL;
while (n > 0) { - size = zpci_get_max_write_size((u64 __force) dst, - (u64) src, n, - ZPCI_MAX_WRITE_SIZE); + size = zpci_get_max_io_size((u64 __force) dst, + (u64) src, n, + ZPCI_MAX_WRITE_SIZE); if (size > 8) /* main path */ rc = zpci_write_block(dst, src, size); else diff --git a/arch/s390/pci/pci_mmio.c b/arch/s390/pci/pci_mmio.c index 588089332931..a90499c087f0 100644 --- a/arch/s390/pci/pci_mmio.c +++ b/arch/s390/pci/pci_mmio.c @@ -97,9 +97,9 @@ static inline int __memcpy_toio_inuser(void __iomem *dst, return -EINVAL;
while (n > 0) { - size = zpci_get_max_write_size((u64 __force) dst, - (u64 __force) src, n, - ZPCI_MAX_WRITE_SIZE); + size = zpci_get_max_io_size((u64 __force) dst, + (u64 __force) src, n, + ZPCI_MAX_WRITE_SIZE); if (size > 8) /* main path */ rc = __pcistb_mio_inuser(dst, src, size, &status); else @@ -242,9 +242,9 @@ static inline int __memcpy_fromio_inuser(void __user *dst, u8 status;
while (n > 0) { - size = zpci_get_max_write_size((u64 __force) src, - (u64 __force) dst, n, - ZPCI_MAX_READ_SIZE); + size = zpci_get_max_io_size((u64 __force) src, + (u64 __force) dst, n, + ZPCI_MAX_READ_SIZE); rc = __pcilg_mio_inuser(dst, src, size, &status); if (rc) break; diff --git a/arch/x86/kernel/cpu/mce/inject.c b/arch/x86/kernel/cpu/mce/inject.c index 12cf2e7ca33c..87c15ab89651 100644 --- a/arch/x86/kernel/cpu/mce/inject.c +++ b/arch/x86/kernel/cpu/mce/inject.c @@ -747,6 +747,7 @@ static void check_hw_inj_possible(void)
wrmsrl_safe(mca_msr_reg(bank, MCA_STATUS), status); rdmsrl_safe(mca_msr_reg(bank, MCA_STATUS), &status); + wrmsrl_safe(mca_msr_reg(bank, MCA_STATUS), 0);
if (!status) { hw_injection_possible = false; diff --git a/arch/x86/kernel/kvmclock.c b/arch/x86/kernel/kvmclock.c index 16333ba1904b..c067887d42df 100644 --- a/arch/x86/kernel/kvmclock.c +++ b/arch/x86/kernel/kvmclock.c @@ -24,8 +24,8 @@
static int kvmclock __initdata = 1; static int kvmclock_vsyscall __initdata = 1; -static int msr_kvm_system_time __ro_after_init = MSR_KVM_SYSTEM_TIME; -static int msr_kvm_wall_clock __ro_after_init = MSR_KVM_WALL_CLOCK; +static int msr_kvm_system_time __ro_after_init; +static int msr_kvm_wall_clock __ro_after_init; static u64 kvm_sched_clock_offset __ro_after_init;
static int __init parse_no_kvmclock(char *arg) @@ -195,7 +195,8 @@ static void kvm_setup_secondary_clock(void)
void kvmclock_disable(void) { - native_write_msr(msr_kvm_system_time, 0, 0); + if (msr_kvm_system_time) + native_write_msr(msr_kvm_system_time, 0, 0); }
static void __init kvmclock_init_mem(void) @@ -294,7 +295,10 @@ void __init kvmclock_init(void) if (kvm_para_has_feature(KVM_FEATURE_CLOCKSOURCE2)) { msr_kvm_system_time = MSR_KVM_SYSTEM_TIME_NEW; msr_kvm_wall_clock = MSR_KVM_WALL_CLOCK_NEW; - } else if (!kvm_para_has_feature(KVM_FEATURE_CLOCKSOURCE)) { + } else if (kvm_para_has_feature(KVM_FEATURE_CLOCKSOURCE)) { + msr_kvm_system_time = MSR_KVM_SYSTEM_TIME; + msr_kvm_wall_clock = MSR_KVM_WALL_CLOCK; + } else { return; }
diff --git a/arch/x86/lib/misc.c b/arch/x86/lib/misc.c index a018ec4fba53..c97be9a1430a 100644 --- a/arch/x86/lib/misc.c +++ b/arch/x86/lib/misc.c @@ -6,7 +6,7 @@ */ int num_digits(int val) { - int m = 10; + long long m = 10; int d = 1;
if (val < 0) { diff --git a/block/bio.c b/block/bio.c index 9ec72a78f114..6c22dd7b6f27 100644 --- a/block/bio.c +++ b/block/bio.c @@ -1109,13 +1109,22 @@ bool bio_add_folio(struct bio *bio, struct folio *folio, size_t len,
void __bio_release_pages(struct bio *bio, bool mark_dirty) { - struct bvec_iter_all iter_all; - struct bio_vec *bvec; + struct folio_iter fi;
- bio_for_each_segment_all(bvec, bio, iter_all) { - if (mark_dirty && !PageCompound(bvec->bv_page)) - set_page_dirty_lock(bvec->bv_page); - put_page(bvec->bv_page); + bio_for_each_folio_all(fi, bio) { + struct page *page; + size_t done = 0; + + if (mark_dirty) { + folio_lock(fi.folio); + folio_mark_dirty(fi.folio); + folio_unlock(fi.folio); + } + page = folio_page(fi.folio, fi.offset / PAGE_SIZE); + do { + folio_put(fi.folio); + done += PAGE_SIZE; + } while (done < fi.length); } } EXPORT_SYMBOL_GPL(__bio_release_pages); @@ -1414,12 +1423,12 @@ EXPORT_SYMBOL(bio_free_pages); */ void bio_set_pages_dirty(struct bio *bio) { - struct bio_vec *bvec; - struct bvec_iter_all iter_all; + struct folio_iter fi;
- bio_for_each_segment_all(bvec, bio, iter_all) { - if (!PageCompound(bvec->bv_page)) - set_page_dirty_lock(bvec->bv_page); + bio_for_each_folio_all(fi, bio) { + folio_lock(fi.folio); + folio_mark_dirty(fi.folio); + folio_unlock(fi.folio); } }
@@ -1462,12 +1471,11 @@ static void bio_dirty_fn(struct work_struct *work)
void bio_check_pages_dirty(struct bio *bio) { - struct bio_vec *bvec; + struct folio_iter fi; unsigned long flags; - struct bvec_iter_all iter_all;
- bio_for_each_segment_all(bvec, bio, iter_all) { - if (!PageDirty(bvec->bv_page) && !PageCompound(bvec->bv_page)) + bio_for_each_folio_all(fi, bio) { + if (!folio_test_dirty(fi.folio)) goto defer; }
diff --git a/block/blk-mq.c b/block/blk-mq.c index 368f1947c895..b3f99dda4530 100644 --- a/block/blk-mq.c +++ b/block/blk-mq.c @@ -2946,12 +2946,6 @@ void blk_mq_submit_bio(struct bio *bio) blk_status_t ret;
bio = blk_queue_bounce(bio, q); - if (bio_may_exceed_limits(bio, &q->limits)) { - bio = __bio_split_to_limits(bio, &q->limits, &nr_segs); - if (!bio) - return; - } - bio_set_ioprio(bio);
if (plug) { @@ -2960,6 +2954,11 @@ void blk_mq_submit_bio(struct bio *bio) rq = NULL; } if (rq) { + if (unlikely(bio_may_exceed_limits(bio, &q->limits))) { + bio = __bio_split_to_limits(bio, &q->limits, &nr_segs); + if (!bio) + return; + } if (!bio_integrity_prep(bio)) return; if (blk_mq_attempt_bio_merge(q, bio, nr_segs)) @@ -2970,6 +2969,11 @@ void blk_mq_submit_bio(struct bio *bio) } else { if (unlikely(bio_queue_enter(bio))) return; + if (unlikely(bio_may_exceed_limits(bio, &q->limits))) { + bio = __bio_split_to_limits(bio, &q->limits, &nr_segs); + if (!bio) + goto fail; + } if (!bio_integrity_prep(bio)) goto fail; } diff --git a/block/blk-settings.c b/block/blk-settings.c index 86ff375c00ce..bbca4ce77a2d 100644 --- a/block/blk-settings.c +++ b/block/blk-settings.c @@ -135,7 +135,7 @@ void blk_queue_max_hw_sectors(struct request_queue *q, unsigned int max_hw_secto limits->max_hw_sectors = max_hw_sectors;
max_sectors = min_not_zero(max_hw_sectors, limits->max_dev_sectors); - max_sectors = min_t(unsigned int, max_sectors, BLK_DEF_MAX_SECTORS); + max_sectors = min(max_sectors, BLK_DEF_MAX_SECTORS); max_sectors = round_down(max_sectors, limits->logical_block_size >> SECTOR_SHIFT); limits->max_sectors = max_sectors; diff --git a/block/genhd.c b/block/genhd.c index afab646d12c8..ddb17c4adc8a 100644 --- a/block/genhd.c +++ b/block/genhd.c @@ -444,7 +444,9 @@ int __must_check device_add_disk(struct device *parent, struct gendisk *disk, DISK_MAX_PARTS); disk->minors = DISK_MAX_PARTS; } - if (disk->first_minor + disk->minors > MINORMASK + 1) + if (disk->first_minor > MINORMASK || + disk->minors > MINORMASK + 1 || + disk->first_minor + disk->minors > MINORMASK + 1) goto out_exit_elevator; } else { if (WARN_ON(disk->minors)) @@ -567,6 +569,7 @@ int __must_check device_add_disk(struct device *parent, struct gendisk *disk, out_del_block_link: if (!sysfs_deprecated) sysfs_remove_link(block_depr, dev_name(ddev)); + pm_runtime_set_memalloc_noio(ddev, false); out_device_del: device_del(ddev); out_free_ext_minor: diff --git a/block/ioctl.c b/block/ioctl.c index 3c475e4166e9..ebe4a2653622 100644 --- a/block/ioctl.c +++ b/block/ioctl.c @@ -18,7 +18,7 @@ static int blkpg_do_ioctl(struct block_device *bdev, { struct gendisk *disk = bdev->bd_disk; struct blkpg_partition p; - long long start, length; + sector_t start, length;
if (disk->flags & GENHD_FL_NO_PART) return -EINVAL; @@ -35,14 +35,17 @@ static int blkpg_do_ioctl(struct block_device *bdev, if (op == BLKPG_DEL_PARTITION) return bdev_del_partition(disk, p.pno);
+ if (p.start < 0 || p.length <= 0 || p.start + p.length < 0) + return -EINVAL; + /* Check that the partition is aligned to the block size */ + if (!IS_ALIGNED(p.start | p.length, bdev_logical_block_size(bdev))) + return -EINVAL; + start = p.start >> SECTOR_SHIFT; length = p.length >> SECTOR_SHIFT;
switch (op) { case BLKPG_ADD_PARTITION: - /* check if partition is aligned to blocksize */ - if (p.start & (bdev_logical_block_size(bdev) - 1)) - return -EINVAL; return bdev_add_partition(disk, p.pno, start, length); case BLKPG_RESIZE_PARTITION: return bdev_resize_partition(disk, p.pno, start, length); diff --git a/crypto/af_alg.c b/crypto/af_alg.c index e893c0f6c879..fef69d2a6b18 100644 --- a/crypto/af_alg.c +++ b/crypto/af_alg.c @@ -1045,9 +1045,13 @@ EXPORT_SYMBOL_GPL(af_alg_sendpage); void af_alg_free_resources(struct af_alg_async_req *areq) { struct sock *sk = areq->sk; + struct af_alg_ctx *ctx;
af_alg_free_areq_sgls(areq); sock_kfree_s(sk, areq, areq->areqlen); + + ctx = alg_sk(sk)->private; + ctx->inflight = false; } EXPORT_SYMBOL_GPL(af_alg_free_resources);
@@ -1117,11 +1121,19 @@ EXPORT_SYMBOL_GPL(af_alg_poll); struct af_alg_async_req *af_alg_alloc_areq(struct sock *sk, unsigned int areqlen) { - struct af_alg_async_req *areq = sock_kmalloc(sk, areqlen, GFP_KERNEL); + struct af_alg_ctx *ctx = alg_sk(sk)->private; + struct af_alg_async_req *areq; + + /* Only one AIO request can be in flight. */ + if (ctx->inflight) + return ERR_PTR(-EBUSY);
+ areq = sock_kmalloc(sk, areqlen, GFP_KERNEL); if (unlikely(!areq)) return ERR_PTR(-ENOMEM);
+ ctx->inflight = true; + areq->areqlen = areqlen; areq->sk = sk; areq->last_rsgl = NULL; diff --git a/crypto/scompress.c b/crypto/scompress.c index 738f4f8f0f41..4d6366a44400 100644 --- a/crypto/scompress.c +++ b/crypto/scompress.c @@ -124,6 +124,7 @@ static int scomp_acomp_comp_decomp(struct acomp_req *req, int dir) struct crypto_scomp *scomp = *tfm_ctx; void **ctx = acomp_request_ctx(req); struct scomp_scratch *scratch; + unsigned int dlen; int ret;
if (!req->src || !req->slen || req->slen > SCOMP_SCRATCH_SIZE) @@ -135,6 +136,8 @@ static int scomp_acomp_comp_decomp(struct acomp_req *req, int dir) if (!req->dlen || req->dlen > SCOMP_SCRATCH_SIZE) req->dlen = SCOMP_SCRATCH_SIZE;
+ dlen = req->dlen; + scratch = raw_cpu_ptr(&scomp_scratch); spin_lock(&scratch->lock);
@@ -152,6 +155,9 @@ static int scomp_acomp_comp_decomp(struct acomp_req *req, int dir) ret = -ENOMEM; goto out; } + } else if (req->dlen > dlen) { + ret = -ENOSPC; + goto out; } scatterwalk_map_and_copy(scratch->dst, req->dst, 0, req->dlen, 1); diff --git a/drivers/acpi/acpi_extlog.c b/drivers/acpi/acpi_extlog.c index e648158368a7..088db2356998 100644 --- a/drivers/acpi/acpi_extlog.c +++ b/drivers/acpi/acpi_extlog.c @@ -145,9 +145,14 @@ static int extlog_print(struct notifier_block *nb, unsigned long val, static u32 err_seq;
estatus = extlog_elog_entry_check(cpu, bank); - if (estatus == NULL || (mce->kflags & MCE_HANDLED_CEC)) + if (!estatus) return NOTIFY_DONE;
+ if (mce->kflags & MCE_HANDLED_CEC) { + estatus->block_status = 0; + return NOTIFY_DONE; + } + memcpy(elog_buf, (void *)estatus, ELOG_ENTRY_LEN); /* clear record status to enable BIOS to update it again */ estatus->block_status = 0; diff --git a/drivers/acpi/acpi_lpit.c b/drivers/acpi/acpi_lpit.c index 50540d4d4948..2c015ecf7185 100644 --- a/drivers/acpi/acpi_lpit.c +++ b/drivers/acpi/acpi_lpit.c @@ -98,7 +98,7 @@ static void lpit_update_residency(struct lpit_residency_info *info, struct acpi_lpit_native *lpit_native) { info->frequency = lpit_native->counter_frequency ? - lpit_native->counter_frequency : tsc_khz * 1000; + lpit_native->counter_frequency : mul_u32_u32(tsc_khz, 1000U); if (!info->frequency) info->frequency = 1;
diff --git a/drivers/acpi/acpi_lpss.c b/drivers/acpi/acpi_lpss.c index f08ffa75f4a7..8b44743945c8 100644 --- a/drivers/acpi/acpi_lpss.c +++ b/drivers/acpi/acpi_lpss.c @@ -450,8 +450,9 @@ static int register_device_clock(struct acpi_device *adev, if (!clk_name) return -ENOMEM; clk = clk_register_fractional_divider(NULL, clk_name, parent, + 0, prv_base, 1, 15, 16, 15, CLK_FRAC_DIVIDER_POWER_OF_TWO_PS, - prv_base, 1, 15, 16, 15, 0, NULL); + NULL); parent = clk_name;
clk_name = kasprintf(GFP_KERNEL, "%s-update", devname); diff --git a/drivers/acpi/acpi_video.c b/drivers/acpi/acpi_video.c index ed318485eb19..f7852fb75ab3 100644 --- a/drivers/acpi/acpi_video.c +++ b/drivers/acpi/acpi_video.c @@ -1726,12 +1726,12 @@ static void acpi_video_dev_register_backlight(struct acpi_video_device *device) return; count++;
- acpi_get_parent(device->dev->handle, &acpi_parent); - - pdev = acpi_get_pci_dev(acpi_parent); - if (pdev) { - parent = &pdev->dev; - pci_dev_put(pdev); + if (ACPI_SUCCESS(acpi_get_parent(device->dev->handle, &acpi_parent))) { + pdev = acpi_get_pci_dev(acpi_parent); + if (pdev) { + parent = &pdev->dev; + pci_dev_put(pdev); + } }
memset(&props, 0, sizeof(struct backlight_properties)); diff --git a/drivers/acpi/property.c b/drivers/acpi/property.c index 0565c18c2ee3..62aee900af3d 100644 --- a/drivers/acpi/property.c +++ b/drivers/acpi/property.c @@ -851,6 +851,7 @@ static int acpi_get_ref_args(struct fwnode_reference_args *args, * @index: Index of the reference to return * @num_args: Maximum number of arguments after each reference * @args: Location to store the returned reference with optional arguments + * (may be NULL) * * Find property with @name, verifify that it is a package containing at least * one object reference and if so, store the ACPI device object pointer to the @@ -907,6 +908,9 @@ int __acpi_node_get_property_reference(const struct fwnode_handle *fwnode, if (!device) return -EINVAL;
+ if (!args) + return 0; + args->fwnode = acpi_fwnode_handle(device); args->nargs = 0; return 0; diff --git a/drivers/android/binder_alloc.c b/drivers/android/binder_alloc.c index ed607850f87f..fcbb750b1ccc 100644 --- a/drivers/android/binder_alloc.c +++ b/drivers/android/binder_alloc.c @@ -271,7 +271,7 @@ static int binder_update_page_range(struct binder_alloc *alloc, int allocate, } if (mm) { mmap_write_unlock(mm); - mmput(mm); + mmput_async(mm); } return 0;
@@ -304,7 +304,7 @@ static int binder_update_page_range(struct binder_alloc *alloc, int allocate, err_no_vma: if (mm) { mmap_write_unlock(mm); - mmput(mm); + mmput_async(mm); } return vma ? -ENOMEM : -ESRCH; } @@ -344,8 +344,7 @@ static bool debug_low_async_space_locked(struct binder_alloc *alloc, int pid) continue; if (!buffer->async_transaction) continue; - total_alloc_size += binder_alloc_buffer_size(alloc, buffer) - + sizeof(struct binder_buffer); + total_alloc_size += binder_alloc_buffer_size(alloc, buffer); num_buffers++; }
@@ -407,17 +406,17 @@ static struct binder_buffer *binder_alloc_new_buf_locked( alloc->pid, extra_buffers_size); return ERR_PTR(-EINVAL); } - if (is_async && - alloc->free_async_space < size + sizeof(struct binder_buffer)) { + + /* Pad 0-size buffers so they get assigned unique addresses */ + size = max(size, sizeof(void *)); + + if (is_async && alloc->free_async_space < size) { binder_alloc_debug(BINDER_DEBUG_BUFFER_ALLOC, "%d: binder_alloc_buf size %zd failed, no async space left\n", alloc->pid, size); return ERR_PTR(-ENOSPC); }
- /* Pad 0-size buffers so they get assigned unique addresses */ - size = max(size, sizeof(void *)); - while (n) { buffer = rb_entry(n, struct binder_buffer, rb_node); BUG_ON(!buffer->free); @@ -519,7 +518,7 @@ static struct binder_buffer *binder_alloc_new_buf_locked( buffer->pid = pid; buffer->oneway_spam_suspect = false; if (is_async) { - alloc->free_async_space -= size + sizeof(struct binder_buffer); + alloc->free_async_space -= size; binder_alloc_debug(BINDER_DEBUG_BUFFER_ALLOC_ASYNC, "%d: binder_alloc_buf size %zd async free %zd\n", alloc->pid, size, alloc->free_async_space); @@ -657,8 +656,7 @@ static void binder_free_buf_locked(struct binder_alloc *alloc, BUG_ON(buffer->user_data > alloc->buffer + alloc->buffer_size);
if (buffer->async_transaction) { - alloc->free_async_space += buffer_size + sizeof(struct binder_buffer); - + alloc->free_async_space += buffer_size; binder_alloc_debug(BINDER_DEBUG_BUFFER_ALLOC_ASYNC, "%d: binder_free_buf size %zd async free %zd\n", alloc->pid, size, alloc->free_async_space); diff --git a/drivers/base/node.c b/drivers/base/node.c index faf3597a96da..a4141b57b147 100644 --- a/drivers/base/node.c +++ b/drivers/base/node.c @@ -859,11 +859,15 @@ int __register_one_node(int nid) { int error; int cpu; + struct node *node;
- node_devices[nid] = kzalloc(sizeof(struct node), GFP_KERNEL); - if (!node_devices[nid]) + node = kzalloc(sizeof(struct node), GFP_KERNEL); + if (!node) return -ENOMEM;
+ INIT_LIST_HEAD(&node->access_list); + node_devices[nid] = node; + error = register_node(node_devices[nid], nid);
/* link cpu under this node */ @@ -872,7 +876,6 @@ int __register_one_node(int nid) register_cpu_under_node(cpu, nid); }
- INIT_LIST_HEAD(&node_devices[nid]->access_list); node_init_caches(nid);
return error; diff --git a/drivers/base/swnode.c b/drivers/base/swnode.c index 0a482212c7e8..44153caa893a 100644 --- a/drivers/base/swnode.c +++ b/drivers/base/swnode.c @@ -541,6 +541,9 @@ software_node_get_reference_args(const struct fwnode_handle *fwnode, if (nargs > NR_FWNODE_REFERENCE_ARGS) return -EINVAL;
+ if (!args) + return 0; + args->fwnode = software_node_get(refnode); args->nargs = nargs;
diff --git a/drivers/block/loop.c b/drivers/block/loop.c index 127e3ceb5979..12ff6f58b8a9 100644 --- a/drivers/block/loop.c +++ b/drivers/block/loop.c @@ -165,39 +165,37 @@ static loff_t get_loop_size(struct loop_device *lo, struct file *file) return get_size(lo->lo_offset, lo->lo_sizelimit, file); }
+/* + * We support direct I/O only if lo_offset is aligned with the logical I/O size + * of backing device, and the logical block size of loop is bigger than that of + * the backing device. + */ +static bool lo_bdev_can_use_dio(struct loop_device *lo, + struct block_device *backing_bdev) +{ + unsigned short sb_bsize = bdev_logical_block_size(backing_bdev); + + if (queue_logical_block_size(lo->lo_queue) < sb_bsize) + return false; + if (lo->lo_offset & (sb_bsize - 1)) + return false; + return true; +} + static void __loop_update_dio(struct loop_device *lo, bool dio) { struct file *file = lo->lo_backing_file; - struct address_space *mapping = file->f_mapping; - struct inode *inode = mapping->host; - unsigned short sb_bsize = 0; - unsigned dio_align = 0; + struct inode *inode = file->f_mapping->host; + struct block_device *backing_bdev = NULL; bool use_dio;
- if (inode->i_sb->s_bdev) { - sb_bsize = bdev_logical_block_size(inode->i_sb->s_bdev); - dio_align = sb_bsize - 1; - } + if (S_ISBLK(inode->i_mode)) + backing_bdev = I_BDEV(inode); + else if (inode->i_sb->s_bdev) + backing_bdev = inode->i_sb->s_bdev;
- /* - * We support direct I/O only if lo_offset is aligned with the - * logical I/O size of backing device, and the logical block - * size of loop is bigger than the backing device's. - * - * TODO: the above condition may be loosed in the future, and - * direct I/O may be switched runtime at that time because most - * of requests in sane applications should be PAGE_SIZE aligned - */ - if (dio) { - if (queue_logical_block_size(lo->lo_queue) >= sb_bsize && - !(lo->lo_offset & dio_align) && - (file->f_mode & FMODE_CAN_ODIRECT)) - use_dio = true; - else - use_dio = false; - } else { - use_dio = false; - } + use_dio = dio && (file->f_mode & FMODE_CAN_ODIRECT) && + (!backing_bdev || lo_bdev_can_use_dio(lo, backing_bdev));
if (lo->use_dio == use_dio) return; diff --git a/drivers/block/null_blk/main.c b/drivers/block/null_blk/main.c index e9f38eba2f13..959952e8ede3 100644 --- a/drivers/block/null_blk/main.c +++ b/drivers/block/null_blk/main.c @@ -2114,11 +2114,8 @@ static int null_add_dev(struct nullb_device *dev)
blk_queue_logical_block_size(nullb->q, dev->blocksize); blk_queue_physical_block_size(nullb->q, dev->blocksize); - if (!dev->max_sectors) - dev->max_sectors = queue_max_hw_sectors(nullb->q); - dev->max_sectors = min_t(unsigned int, dev->max_sectors, - BLK_DEF_MAX_SECTORS); - blk_queue_max_hw_sectors(nullb->q, dev->max_sectors); + if (dev->max_sectors) + blk_queue_max_hw_sectors(nullb->q, dev->max_sectors);
if (dev->virt_boundary) blk_queue_virt_boundary(nullb->q, PAGE_SIZE - 1); @@ -2218,12 +2215,6 @@ static int __init null_init(void) g_bs = PAGE_SIZE; }
- if (g_max_sectors > BLK_DEF_MAX_SECTORS) { - pr_warn("invalid max sectors\n"); - pr_warn("defaults max sectors to %u\n", BLK_DEF_MAX_SECTORS); - g_max_sectors = BLK_DEF_MAX_SECTORS; - } - if (g_home_node != NUMA_NO_NODE && g_home_node >= nr_online_nodes) { pr_err("invalid home_node value\n"); g_home_node = NUMA_NO_NODE; diff --git a/drivers/bluetooth/btmtkuart.c b/drivers/bluetooth/btmtkuart.c index c98691cdbbd5..04b72394dda5 100644 --- a/drivers/bluetooth/btmtkuart.c +++ b/drivers/bluetooth/btmtkuart.c @@ -337,7 +337,7 @@ mtk_stp_split(struct btmtkuart_dev *bdev, const unsigned char *data, int count, return data; }
-static int btmtkuart_recv(struct hci_dev *hdev, const u8 *data, size_t count) +static void btmtkuart_recv(struct hci_dev *hdev, const u8 *data, size_t count) { struct btmtkuart_dev *bdev = hci_get_drvdata(hdev); const unsigned char *p_left = data, *p_h4; @@ -376,25 +376,20 @@ static int btmtkuart_recv(struct hci_dev *hdev, const u8 *data, size_t count) bt_dev_err(bdev->hdev, "Frame reassembly failed (%d)", err); bdev->rx_skb = NULL; - return err; + return; }
sz_left -= sz_h4; p_left += sz_h4; } - - return 0; }
static int btmtkuart_receive_buf(struct serdev_device *serdev, const u8 *data, size_t count) { struct btmtkuart_dev *bdev = serdev_device_get_drvdata(serdev); - int err;
- err = btmtkuart_recv(bdev->hdev, data, count); - if (err < 0) - return err; + btmtkuart_recv(bdev->hdev, data, count);
bdev->hdev->stat.byte_rx += count;
diff --git a/drivers/clk/clk-si5341.c b/drivers/clk/clk-si5341.c index c7d8cbd22bac..5acb35236c58 100644 --- a/drivers/clk/clk-si5341.c +++ b/drivers/clk/clk-si5341.c @@ -892,10 +892,8 @@ static int si5341_output_clk_set_rate(struct clk_hw *hw, unsigned long rate, r[0] = r_div ? (r_div & 0xff) : 1; r[1] = (r_div >> 8) & 0xff; r[2] = (r_div >> 16) & 0xff; - err = regmap_bulk_write(output->data->regmap, + return regmap_bulk_write(output->data->regmap, SI5341_OUT_R_REG(output), r, 3); - - return 0; }
static int si5341_output_reparent(struct clk_si5341_output *output, u8 index) diff --git a/drivers/clk/qcom/gpucc-sm8150.c b/drivers/clk/qcom/gpucc-sm8150.c index 8422fd047493..c89a5b59ddb7 100644 --- a/drivers/clk/qcom/gpucc-sm8150.c +++ b/drivers/clk/qcom/gpucc-sm8150.c @@ -37,8 +37,8 @@ static struct alpha_pll_config gpu_cc_pll1_config = { .config_ctl_hi_val = 0x00002267, .config_ctl_hi1_val = 0x00000024, .test_ctl_val = 0x00000000, - .test_ctl_hi_val = 0x00000002, - .test_ctl_hi1_val = 0x00000000, + .test_ctl_hi_val = 0x00000000, + .test_ctl_hi1_val = 0x00000020, .user_ctl_val = 0x00000000, .user_ctl_hi_val = 0x00000805, .user_ctl_hi1_val = 0x000000d0, diff --git a/drivers/clk/qcom/videocc-sm8150.c b/drivers/clk/qcom/videocc-sm8150.c index 1afdbe4a249d..52a9a453a143 100644 --- a/drivers/clk/qcom/videocc-sm8150.c +++ b/drivers/clk/qcom/videocc-sm8150.c @@ -33,6 +33,7 @@ static struct alpha_pll_config video_pll0_config = { .config_ctl_val = 0x20485699, .config_ctl_hi_val = 0x00002267, .config_ctl_hi1_val = 0x00000024, + .test_ctl_hi1_val = 0x00000020, .user_ctl_val = 0x00000000, .user_ctl_hi_val = 0x00000805, .user_ctl_hi1_val = 0x000000D0, @@ -214,6 +215,10 @@ static const struct regmap_config video_cc_sm8150_regmap_config = {
static const struct qcom_reset_map video_cc_sm8150_resets[] = { [VIDEO_CC_MVSC_CORE_CLK_BCR] = { 0x850, 2 }, + [VIDEO_CC_INTERFACE_BCR] = { 0x8f0 }, + [VIDEO_CC_MVS0_BCR] = { 0x870 }, + [VIDEO_CC_MVS1_BCR] = { 0x8b0 }, + [VIDEO_CC_MVSC_BCR] = { 0x810 }, };
static const struct qcom_cc_desc video_cc_sm8150_desc = { diff --git a/drivers/clk/renesas/rzg2l-cpg.c b/drivers/clk/renesas/rzg2l-cpg.c index 84767cfc1e73..473feb36a38f 100644 --- a/drivers/clk/renesas/rzg2l-cpg.c +++ b/drivers/clk/renesas/rzg2l-cpg.c @@ -1115,41 +1115,33 @@ rzg2l_cpg_register_mod_clk(const struct rzg2l_mod_clk *mod,
#define rcdev_to_priv(x) container_of(x, struct rzg2l_cpg_priv, rcdev)
-static int rzg2l_cpg_reset(struct reset_controller_dev *rcdev, - unsigned long id) -{ - struct rzg2l_cpg_priv *priv = rcdev_to_priv(rcdev); - const struct rzg2l_cpg_info *info = priv->info; - unsigned int reg = info->resets[id].off; - u32 dis = BIT(info->resets[id].bit); - u32 we = dis << 16; - - dev_dbg(rcdev->dev, "reset id:%ld offset:0x%x\n", id, CLK_RST_R(reg)); - - /* Reset module */ - writel(we, priv->base + CLK_RST_R(reg)); - - /* Wait for at least one cycle of the RCLK clock (@ ca. 32 kHz) */ - udelay(35); - - /* Release module from reset state */ - writel(we | dis, priv->base + CLK_RST_R(reg)); - - return 0; -} - static int rzg2l_cpg_assert(struct reset_controller_dev *rcdev, unsigned long id) { struct rzg2l_cpg_priv *priv = rcdev_to_priv(rcdev); const struct rzg2l_cpg_info *info = priv->info; unsigned int reg = info->resets[id].off; - u32 value = BIT(info->resets[id].bit) << 16; + u32 mask = BIT(info->resets[id].bit); + s8 monbit = info->resets[id].monbit; + u32 value = mask << 16;
dev_dbg(rcdev->dev, "assert id:%ld offset:0x%x\n", id, CLK_RST_R(reg));
writel(value, priv->base + CLK_RST_R(reg)); - return 0; + + if (info->has_clk_mon_regs) { + reg = CLK_MRST_R(reg); + } else if (monbit >= 0) { + reg = CPG_RST_MON; + mask = BIT(monbit); + } else { + /* Wait for at least one cycle of the RCLK clock (@ ca. 32 kHz) */ + udelay(35); + return 0; + } + + return readl_poll_timeout_atomic(priv->base + reg, value, + value & mask, 10, 200); }
static int rzg2l_cpg_deassert(struct reset_controller_dev *rcdev, @@ -1158,14 +1150,40 @@ static int rzg2l_cpg_deassert(struct reset_controller_dev *rcdev, struct rzg2l_cpg_priv *priv = rcdev_to_priv(rcdev); const struct rzg2l_cpg_info *info = priv->info; unsigned int reg = info->resets[id].off; - u32 dis = BIT(info->resets[id].bit); - u32 value = (dis << 16) | dis; + u32 mask = BIT(info->resets[id].bit); + s8 monbit = info->resets[id].monbit; + u32 value = (mask << 16) | mask;
dev_dbg(rcdev->dev, "deassert id:%ld offset:0x%x\n", id, CLK_RST_R(reg));
writel(value, priv->base + CLK_RST_R(reg)); - return 0; + + if (info->has_clk_mon_regs) { + reg = CLK_MRST_R(reg); + } else if (monbit >= 0) { + reg = CPG_RST_MON; + mask = BIT(monbit); + } else { + /* Wait for at least one cycle of the RCLK clock (@ ca. 32 kHz) */ + udelay(35); + return 0; + } + + return readl_poll_timeout_atomic(priv->base + reg, value, + !(value & mask), 10, 200); +} + +static int rzg2l_cpg_reset(struct reset_controller_dev *rcdev, + unsigned long id) +{ + int ret; + + ret = rzg2l_cpg_assert(rcdev, id); + if (ret) + return ret; + + return rzg2l_cpg_deassert(rcdev, id); }
static int rzg2l_cpg_status(struct reset_controller_dev *rcdev, @@ -1173,18 +1191,21 @@ static int rzg2l_cpg_status(struct reset_controller_dev *rcdev, { struct rzg2l_cpg_priv *priv = rcdev_to_priv(rcdev); const struct rzg2l_cpg_info *info = priv->info; - unsigned int reg = info->resets[id].off; - u32 bitmask = BIT(info->resets[id].bit); s8 monbit = info->resets[id].monbit; + unsigned int reg; + u32 bitmask;
if (info->has_clk_mon_regs) { - return !!(readl(priv->base + CLK_MRST_R(reg)) & bitmask); + reg = CLK_MRST_R(info->resets[id].off); + bitmask = BIT(info->resets[id].bit); } else if (monbit >= 0) { - u32 monbitmask = BIT(monbit); - - return !!(readl(priv->base + CPG_RST_MON) & monbitmask); + reg = CPG_RST_MON; + bitmask = BIT(monbit); + } else { + return -ENOTSUPP; } - return -ENOTSUPP; + + return !!(readl(priv->base + reg) & bitmask); }
static const struct reset_control_ops rzg2l_cpg_reset_ops = { diff --git a/drivers/clk/zynqmp/clk-mux-zynqmp.c b/drivers/clk/zynqmp/clk-mux-zynqmp.c index 60359333f26d..9b5d3050b742 100644 --- a/drivers/clk/zynqmp/clk-mux-zynqmp.c +++ b/drivers/clk/zynqmp/clk-mux-zynqmp.c @@ -89,7 +89,7 @@ static int zynqmp_clk_mux_set_parent(struct clk_hw *hw, u8 index) static const struct clk_ops zynqmp_clk_mux_ops = { .get_parent = zynqmp_clk_mux_get_parent, .set_parent = zynqmp_clk_mux_set_parent, - .determine_rate = __clk_mux_determine_rate, + .determine_rate = __clk_mux_determine_rate_closest, };
static const struct clk_ops zynqmp_clk_mux_ro_ops = { diff --git a/drivers/clk/zynqmp/divider.c b/drivers/clk/zynqmp/divider.c index 33a3b2a22659..5a00487ae408 100644 --- a/drivers/clk/zynqmp/divider.c +++ b/drivers/clk/zynqmp/divider.c @@ -110,52 +110,6 @@ static unsigned long zynqmp_clk_divider_recalc_rate(struct clk_hw *hw, return DIV_ROUND_UP_ULL(parent_rate, value); }
-static void zynqmp_get_divider2_val(struct clk_hw *hw, - unsigned long rate, - struct zynqmp_clk_divider *divider, - u32 *bestdiv) -{ - int div1; - int div2; - long error = LONG_MAX; - unsigned long div1_prate; - struct clk_hw *div1_parent_hw; - struct zynqmp_clk_divider *pdivider; - struct clk_hw *div2_parent_hw = clk_hw_get_parent(hw); - - if (!div2_parent_hw) - return; - - pdivider = to_zynqmp_clk_divider(div2_parent_hw); - if (!pdivider) - return; - - div1_parent_hw = clk_hw_get_parent(div2_parent_hw); - if (!div1_parent_hw) - return; - - div1_prate = clk_hw_get_rate(div1_parent_hw); - *bestdiv = 1; - for (div1 = 1; div1 <= pdivider->max_div;) { - for (div2 = 1; div2 <= divider->max_div;) { - long new_error = ((div1_prate / div1) / div2) - rate; - - if (abs(new_error) < abs(error)) { - *bestdiv = div2; - error = new_error; - } - if (divider->flags & CLK_DIVIDER_POWER_OF_TWO) - div2 = div2 << 1; - else - div2++; - } - if (pdivider->flags & CLK_DIVIDER_POWER_OF_TWO) - div1 = div1 << 1; - else - div1++; - } -} - /** * zynqmp_clk_divider_round_rate() - Round rate of divider clock * @hw: handle between common and hardware-specific interfaces @@ -174,6 +128,7 @@ static long zynqmp_clk_divider_round_rate(struct clk_hw *hw, u32 div_type = divider->div_type; u32 bestdiv; int ret; + u8 width;
/* if read only, just return current value */ if (divider->flags & CLK_DIVIDER_READ_ONLY) { @@ -193,23 +148,12 @@ static long zynqmp_clk_divider_round_rate(struct clk_hw *hw, return DIV_ROUND_UP_ULL((u64)*prate, bestdiv); }
- bestdiv = zynqmp_divider_get_val(*prate, rate, divider->flags); - - /* - * In case of two divisors, compute best divider values and return - * divider2 value based on compute value. div1 will be automatically - * set to optimum based on required total divider value. - */ - if (div_type == TYPE_DIV2 && - (clk_hw_get_flags(hw) & CLK_SET_RATE_PARENT)) { - zynqmp_get_divider2_val(hw, rate, divider, &bestdiv); - } + width = fls(divider->max_div);
- if ((clk_hw_get_flags(hw) & CLK_SET_RATE_PARENT) && divider->is_frac) - bestdiv = rate % *prate ? 1 : bestdiv; + rate = divider_round_rate(hw, rate, prate, NULL, width, divider->flags);
- bestdiv = min_t(u32, bestdiv, divider->max_div); - *prate = rate * bestdiv; + if (divider->is_frac && (clk_hw_get_flags(hw) & CLK_SET_RATE_PARENT) && (rate % *prate)) + *prate = rate;
return rate; } diff --git a/drivers/clocksource/timer-ti-dm.c b/drivers/clocksource/timer-ti-dm.c index ec86aecb748f..7f9c1f58a947 100644 --- a/drivers/clocksource/timer-ti-dm.c +++ b/drivers/clocksource/timer-ti-dm.c @@ -184,7 +184,7 @@ static inline u32 dmtimer_read(struct dmtimer *timer, u32 reg) * dmtimer_write - write timer registers in posted and non-posted mode * @timer: timer pointer over which write operation is to perform * @reg: lowest byte holds the register offset - * @value: data to write into the register + * @val: data to write into the register * * The posted mode bit is encoded in reg. Note that in posted mode, the write * pending bit must be checked. Otherwise a write on a register which has a @@ -937,7 +937,7 @@ static int omap_dm_timer_set_int_enable(struct omap_dm_timer *cookie,
/** * omap_dm_timer_set_int_disable - disable timer interrupts - * @timer: pointer to timer handle + * @cookie: pointer to timer cookie * @mask: bit mask of interrupts to be disabled * * Disables the specified timer interrupts for a timer. diff --git a/drivers/cpufreq/cpufreq-dt-platdev.c b/drivers/cpufreq/cpufreq-dt-platdev.c index 69a8742c0a7a..8514bb62dd10 100644 --- a/drivers/cpufreq/cpufreq-dt-platdev.c +++ b/drivers/cpufreq/cpufreq-dt-platdev.c @@ -176,7 +176,7 @@ static bool __init cpu0_node_has_opp_v2_prop(void) struct device_node *np = of_cpu_device_node_get(0); bool ret = false;
- if (of_get_property(np, "operating-points-v2", NULL)) + if (of_property_present(np, "operating-points-v2")) ret = true;
of_node_put(np); diff --git a/drivers/cpufreq/imx-cpufreq-dt.c b/drivers/cpufreq/imx-cpufreq-dt.c index 76e553af2071..535867a7dfdd 100644 --- a/drivers/cpufreq/imx-cpufreq-dt.c +++ b/drivers/cpufreq/imx-cpufreq-dt.c @@ -89,7 +89,7 @@ static int imx_cpufreq_dt_probe(struct platform_device *pdev)
cpu_dev = get_cpu_device(0);
- if (!of_find_property(cpu_dev->of_node, "cpu-supply", NULL)) + if (!of_property_present(cpu_dev->of_node, "cpu-supply")) return -ENODEV;
if (of_machine_is_compatible("fsl,imx7ulp")) { diff --git a/drivers/cpufreq/imx6q-cpufreq.c b/drivers/cpufreq/imx6q-cpufreq.c index 925fc17eaacb..39b0362a3b9a 100644 --- a/drivers/cpufreq/imx6q-cpufreq.c +++ b/drivers/cpufreq/imx6q-cpufreq.c @@ -230,7 +230,7 @@ static int imx6q_opp_check_speed_grading(struct device *dev) u32 val; int ret;
- if (of_find_property(dev->of_node, "nvmem-cells", NULL)) { + if (of_property_present(dev->of_node, "nvmem-cells")) { ret = nvmem_cell_read_u32(dev, "speed_grade", &val); if (ret) return ret; @@ -285,7 +285,7 @@ static int imx6ul_opp_check_speed_grading(struct device *dev) u32 val; int ret = 0;
- if (of_find_property(dev->of_node, "nvmem-cells", NULL)) { + if (of_property_present(dev->of_node, "nvmem-cells")) { ret = nvmem_cell_read_u32(dev, "speed_grade", &val); if (ret) return ret; diff --git a/drivers/cpufreq/scmi-cpufreq.c b/drivers/cpufreq/scmi-cpufreq.c index 513a071845c2..028df8a5f537 100644 --- a/drivers/cpufreq/scmi-cpufreq.c +++ b/drivers/cpufreq/scmi-cpufreq.c @@ -310,8 +310,11 @@ static int scmi_cpufreq_probe(struct scmi_device *sdev)
#ifdef CONFIG_COMMON_CLK /* dummy clock provider as needed by OPP if clocks property is used */ - if (of_find_property(dev->of_node, "#clock-cells", NULL)) - devm_of_clk_add_hw_provider(dev, of_clk_hw_simple_get, NULL); + if (of_property_present(dev->of_node, "#clock-cells")) { + ret = devm_of_clk_add_hw_provider(dev, of_clk_hw_simple_get, NULL); + if (ret) + return dev_err_probe(dev, ret, "%s: registering clock provider failed\n", __func__); + } #endif
ret = cpufreq_register_driver(&scmi_cpufreq_driver); diff --git a/drivers/cpufreq/tegra20-cpufreq.c b/drivers/cpufreq/tegra20-cpufreq.c index ab7ac7df9e62..dfd2de4f8e07 100644 --- a/drivers/cpufreq/tegra20-cpufreq.c +++ b/drivers/cpufreq/tegra20-cpufreq.c @@ -25,7 +25,7 @@ static bool cpu0_node_has_opp_v2_prop(void) struct device_node *np = of_cpu_device_node_get(0); bool ret = false;
- if (of_get_property(np, "operating-points-v2", NULL)) + if (of_property_present(np, "operating-points-v2")) ret = true;
of_node_put(np); diff --git a/drivers/crypto/ccp/ccp-ops.c b/drivers/crypto/ccp/ccp-ops.c index aa4e1a500691..cb8e99936abb 100644 --- a/drivers/crypto/ccp/ccp-ops.c +++ b/drivers/crypto/ccp/ccp-ops.c @@ -179,8 +179,11 @@ static int ccp_init_dm_workarea(struct ccp_dm_workarea *wa,
wa->dma.address = dma_map_single(wa->dev, wa->address, len, dir); - if (dma_mapping_error(wa->dev, wa->dma.address)) + if (dma_mapping_error(wa->dev, wa->dma.address)) { + kfree(wa->address); + wa->address = NULL; return -ENOMEM; + }
wa->dma.length = len; } diff --git a/drivers/crypto/hisilicon/hpre/hpre_main.c b/drivers/crypto/hisilicon/hpre/hpre_main.c index ff8a5f20a5df..269df4ec148b 100644 --- a/drivers/crypto/hisilicon/hpre/hpre_main.c +++ b/drivers/crypto/hisilicon/hpre/hpre_main.c @@ -118,8 +118,6 @@ #define HPRE_DFX_COMMON2_LEN 0xE #define HPRE_DFX_CORE_LEN 0x43
-#define HPRE_DEV_ALG_MAX_LEN 256 - static const char hpre_name[] = "hisi_hpre"; static struct dentry *hpre_debugfs_root; static const struct pci_device_id hpre_dev_ids[] = { @@ -135,12 +133,7 @@ struct hpre_hw_error { const char *msg; };
-struct hpre_dev_alg { - u32 alg_msk; - const char *alg; -}; - -static const struct hpre_dev_alg hpre_dev_algs[] = { +static const struct qm_dev_alg hpre_dev_algs[] = { { .alg_msk = BIT(0), .alg = "rsa\n" @@ -233,6 +226,20 @@ static const struct hisi_qm_cap_info hpre_basic_info[] = { {HPRE_CORE10_ALG_BITMAP_CAP, 0x3170, 0, GENMASK(31, 0), 0x0, 0x10, 0x10} };
+enum hpre_pre_store_cap_idx { + HPRE_CLUSTER_NUM_CAP_IDX = 0x0, + HPRE_CORE_ENABLE_BITMAP_CAP_IDX, + HPRE_DRV_ALG_BITMAP_CAP_IDX, + HPRE_DEV_ALG_BITMAP_CAP_IDX, +}; + +static const u32 hpre_pre_store_caps[] = { + HPRE_CLUSTER_NUM_CAP, + HPRE_CORE_ENABLE_BITMAP_CAP, + HPRE_DRV_ALG_BITMAP_CAP, + HPRE_DEV_ALG_BITMAP_CAP, +}; + static const struct hpre_hw_error hpre_hw_errors[] = { { .int_msk = BIT(0), @@ -352,42 +359,13 @@ bool hpre_check_alg_support(struct hisi_qm *qm, u32 alg) { u32 cap_val;
- cap_val = hisi_qm_get_hw_info(qm, hpre_basic_info, HPRE_DRV_ALG_BITMAP_CAP, qm->cap_ver); + cap_val = qm->cap_tables.dev_cap_table[HPRE_DRV_ALG_BITMAP_CAP_IDX].cap_val; if (alg & cap_val) return true;
return false; }
-static int hpre_set_qm_algs(struct hisi_qm *qm) -{ - struct device *dev = &qm->pdev->dev; - char *algs, *ptr; - u32 alg_msk; - int i; - - if (!qm->use_sva) - return 0; - - algs = devm_kzalloc(dev, HPRE_DEV_ALG_MAX_LEN * sizeof(char), GFP_KERNEL); - if (!algs) - return -ENOMEM; - - alg_msk = hisi_qm_get_hw_info(qm, hpre_basic_info, HPRE_DEV_ALG_BITMAP_CAP, qm->cap_ver); - - for (i = 0; i < ARRAY_SIZE(hpre_dev_algs); i++) - if (alg_msk & hpre_dev_algs[i].alg_msk) - strcat(algs, hpre_dev_algs[i].alg); - - ptr = strrchr(algs, '\n'); - if (ptr) - *ptr = '\0'; - - qm->uacce->algs = algs; - - return 0; -} - static int hpre_diff_regs_show(struct seq_file *s, void *unused) { struct hisi_qm *qm = s->private; @@ -457,16 +435,6 @@ static u32 vfs_num; module_param_cb(vfs_num, &vfs_num_ops, &vfs_num, 0444); MODULE_PARM_DESC(vfs_num, "Number of VFs to enable(1-63), 0(default)");
-static inline int hpre_cluster_num(struct hisi_qm *qm) -{ - return hisi_qm_get_hw_info(qm, hpre_basic_info, HPRE_CLUSTER_NUM_CAP, qm->cap_ver); -} - -static inline int hpre_cluster_core_mask(struct hisi_qm *qm) -{ - return hisi_qm_get_hw_info(qm, hpre_basic_info, HPRE_CORE_ENABLE_BITMAP_CAP, qm->cap_ver); -} - struct hisi_qp *hpre_create_qp(u8 type) { int node = cpu_to_node(smp_processor_id()); @@ -533,13 +501,15 @@ static int hpre_cfg_by_dsm(struct hisi_qm *qm)
static int hpre_set_cluster(struct hisi_qm *qm) { - u32 cluster_core_mask = hpre_cluster_core_mask(qm); - u8 clusters_num = hpre_cluster_num(qm); struct device *dev = &qm->pdev->dev; unsigned long offset; + u32 cluster_core_mask; + u8 clusters_num; u32 val = 0; int ret, i;
+ cluster_core_mask = qm->cap_tables.dev_cap_table[HPRE_CORE_ENABLE_BITMAP_CAP_IDX].cap_val; + clusters_num = qm->cap_tables.dev_cap_table[HPRE_CLUSTER_NUM_CAP_IDX].cap_val; for (i = 0; i < clusters_num; i++) { offset = i * HPRE_CLSTR_ADDR_INTRVL;
@@ -734,11 +704,12 @@ static int hpre_set_user_domain_and_cache(struct hisi_qm *qm)
static void hpre_cnt_regs_clear(struct hisi_qm *qm) { - u8 clusters_num = hpre_cluster_num(qm); unsigned long offset; + u8 clusters_num; int i;
/* clear clusterX/cluster_ctrl */ + clusters_num = qm->cap_tables.dev_cap_table[HPRE_CLUSTER_NUM_CAP_IDX].cap_val; for (i = 0; i < clusters_num; i++) { offset = HPRE_CLSTR_BASE + i * HPRE_CLSTR_ADDR_INTRVL; writel(0x0, qm->io_base + offset + HPRE_CLUSTER_INQURY); @@ -1025,13 +996,14 @@ static int hpre_pf_comm_regs_debugfs_init(struct hisi_qm *qm)
static int hpre_cluster_debugfs_init(struct hisi_qm *qm) { - u8 clusters_num = hpre_cluster_num(qm); struct device *dev = &qm->pdev->dev; char buf[HPRE_DBGFS_VAL_MAX_LEN]; struct debugfs_regset32 *regset; struct dentry *tmp_d; + u8 clusters_num; int i, ret;
+ clusters_num = qm->cap_tables.dev_cap_table[HPRE_CLUSTER_NUM_CAP_IDX].cap_val; for (i = 0; i < clusters_num; i++) { ret = snprintf(buf, HPRE_DBGFS_VAL_MAX_LEN, "cluster%d", i); if (ret >= HPRE_DBGFS_VAL_MAX_LEN) @@ -1136,8 +1108,37 @@ static void hpre_debugfs_exit(struct hisi_qm *qm) debugfs_remove_recursive(qm->debug.debug_root); }
+static int hpre_pre_store_cap_reg(struct hisi_qm *qm) +{ + struct hisi_qm_cap_record *hpre_cap; + struct device *dev = &qm->pdev->dev; + size_t i, size; + + size = ARRAY_SIZE(hpre_pre_store_caps); + hpre_cap = devm_kzalloc(dev, sizeof(*hpre_cap) * size, GFP_KERNEL); + if (!hpre_cap) + return -ENOMEM; + + for (i = 0; i < size; i++) { + hpre_cap[i].type = hpre_pre_store_caps[i]; + hpre_cap[i].cap_val = hisi_qm_get_hw_info(qm, hpre_basic_info, + hpre_pre_store_caps[i], qm->cap_ver); + } + + if (hpre_cap[HPRE_CLUSTER_NUM_CAP_IDX].cap_val > HPRE_CLUSTERS_NUM_MAX) { + dev_err(dev, "Device cluster num %u is out of range for driver supports %d!\n", + hpre_cap[HPRE_CLUSTER_NUM_CAP_IDX].cap_val, HPRE_CLUSTERS_NUM_MAX); + return -EINVAL; + } + + qm->cap_tables.dev_cap_table = hpre_cap; + + return 0; +} + static int hpre_qm_init(struct hisi_qm *qm, struct pci_dev *pdev) { + u64 alg_msk; int ret;
if (pdev->revision == QM_HW_V1) { @@ -1168,7 +1169,16 @@ static int hpre_qm_init(struct hisi_qm *qm, struct pci_dev *pdev) return ret; }
- ret = hpre_set_qm_algs(qm); + /* Fetch and save the value of capability registers */ + ret = hpre_pre_store_cap_reg(qm); + if (ret) { + pci_err(pdev, "Failed to pre-store capability registers!\n"); + hisi_qm_uninit(qm); + return ret; + } + + alg_msk = qm->cap_tables.dev_cap_table[HPRE_DEV_ALG_BITMAP_CAP_IDX].cap_val; + ret = hisi_qm_set_algs(qm, alg_msk, hpre_dev_algs, ARRAY_SIZE(hpre_dev_algs)); if (ret) { pci_err(pdev, "Failed to set hpre algs!\n"); hisi_qm_uninit(qm); @@ -1181,11 +1191,12 @@ static int hpre_show_last_regs_init(struct hisi_qm *qm) { int cluster_dfx_regs_num = ARRAY_SIZE(hpre_cluster_dfx_regs); int com_dfx_regs_num = ARRAY_SIZE(hpre_com_dfx_regs); - u8 clusters_num = hpre_cluster_num(qm); struct qm_debug *debug = &qm->debug; void __iomem *io_base; + u8 clusters_num; int i, j, idx;
+ clusters_num = qm->cap_tables.dev_cap_table[HPRE_CLUSTER_NUM_CAP_IDX].cap_val; debug->last_words = kcalloc(cluster_dfx_regs_num * clusters_num + com_dfx_regs_num, sizeof(unsigned int), GFP_KERNEL); if (!debug->last_words) @@ -1222,10 +1233,10 @@ static void hpre_show_last_dfx_regs(struct hisi_qm *qm) { int cluster_dfx_regs_num = ARRAY_SIZE(hpre_cluster_dfx_regs); int com_dfx_regs_num = ARRAY_SIZE(hpre_com_dfx_regs); - u8 clusters_num = hpre_cluster_num(qm); struct qm_debug *debug = &qm->debug; struct pci_dev *pdev = qm->pdev; void __iomem *io_base; + u8 clusters_num; int i, j, idx; u32 val;
@@ -1240,6 +1251,7 @@ static void hpre_show_last_dfx_regs(struct hisi_qm *qm) hpre_com_dfx_regs[i].name, debug->last_words[i], val); }
+ clusters_num = qm->cap_tables.dev_cap_table[HPRE_CLUSTER_NUM_CAP_IDX].cap_val; for (i = 0; i < clusters_num; i++) { io_base = qm->io_base + hpre_cluster_offsets[i]; for (j = 0; j < cluster_dfx_regs_num; j++) { diff --git a/drivers/crypto/hisilicon/qm.c b/drivers/crypto/hisilicon/qm.c index f9acf7ecc41b..5539be1bfb40 100644 --- a/drivers/crypto/hisilicon/qm.c +++ b/drivers/crypto/hisilicon/qm.c @@ -237,6 +237,8 @@ #define QM_QOS_MAX_CIR_S 11 #define QM_AUTOSUSPEND_DELAY 3000
+#define QM_DEV_ALG_MAX_LEN 256 + #define QM_MK_CQC_DW3_V1(hop_num, pg_sz, buf_sz, cqe_sz) \ (((hop_num) << QM_CQ_HOP_NUM_SHIFT) | \ ((pg_sz) << QM_CQ_PAGE_SIZE_SHIFT) | \ @@ -315,6 +317,13 @@ enum qm_basic_type { QM_VF_IRQ_NUM_CAP, };
+enum qm_pre_store_cap_idx { + QM_EQ_IRQ_TYPE_CAP_IDX = 0x0, + QM_AEQ_IRQ_TYPE_CAP_IDX, + QM_ABN_IRQ_TYPE_CAP_IDX, + QM_PF2VF_IRQ_TYPE_CAP_IDX, +}; + static const struct hisi_qm_cap_info qm_cap_info_comm[] = { {QM_SUPPORT_DB_ISOLATION, 0x30, 0, BIT(0), 0x0, 0x0, 0x0}, {QM_SUPPORT_FUNC_QOS, 0x3100, 0, BIT(8), 0x0, 0x0, 0x1}, @@ -344,6 +353,13 @@ static const struct hisi_qm_cap_info qm_basic_info[] = { {QM_VF_IRQ_NUM_CAP, 0x311c, 0, GENMASK(15, 0), 0x1, 0x2, 0x3}, };
+static const u32 qm_pre_store_caps[] = { + QM_EQ_IRQ_TYPE_CAP, + QM_AEQ_IRQ_TYPE_CAP, + QM_ABN_IRQ_TYPE_CAP, + QM_PF2VF_IRQ_TYPE_CAP, +}; + struct qm_mailbox { __le16 w0; __le16 queue_num; @@ -781,6 +797,40 @@ static void qm_get_xqc_depth(struct hisi_qm *qm, u16 *low_bits, *high_bits = (depth >> QM_XQ_DEPTH_SHIFT) & QM_XQ_DEPTH_MASK; }
+int hisi_qm_set_algs(struct hisi_qm *qm, u64 alg_msk, const struct qm_dev_alg *dev_algs, + u32 dev_algs_size) +{ + struct device *dev = &qm->pdev->dev; + char *algs, *ptr; + int i; + + if (!qm->uacce) + return 0; + + if (dev_algs_size >= QM_DEV_ALG_MAX_LEN) { + dev_err(dev, "algs size %u is equal or larger than %d.\n", + dev_algs_size, QM_DEV_ALG_MAX_LEN); + return -EINVAL; + } + + algs = devm_kzalloc(dev, QM_DEV_ALG_MAX_LEN * sizeof(char), GFP_KERNEL); + if (!algs) + return -ENOMEM; + + for (i = 0; i < dev_algs_size; i++) + if (alg_msk & dev_algs[i].alg_msk) + strcat(algs, dev_algs[i].alg); + + ptr = strrchr(algs, '\n'); + if (ptr) { + *ptr = '\0'; + qm->uacce->algs = algs; + } + + return 0; +} +EXPORT_SYMBOL_GPL(hisi_qm_set_algs); + static u32 qm_get_irq_num(struct hisi_qm *qm) { if (qm->fun_type == QM_HW_PF) @@ -4804,7 +4854,7 @@ static void qm_unregister_abnormal_irq(struct hisi_qm *qm) if (qm->fun_type == QM_HW_VF) return;
- val = hisi_qm_get_hw_info(qm, qm_basic_info, QM_ABN_IRQ_TYPE_CAP, qm->cap_ver); + val = qm->cap_tables.qm_cap_table[QM_ABN_IRQ_TYPE_CAP_IDX].cap_val; if (!((val >> QM_IRQ_TYPE_SHIFT) & QM_ABN_IRQ_TYPE_MASK)) return;
@@ -4821,7 +4871,7 @@ static int qm_register_abnormal_irq(struct hisi_qm *qm) if (qm->fun_type == QM_HW_VF) return 0;
- val = hisi_qm_get_hw_info(qm, qm_basic_info, QM_ABN_IRQ_TYPE_CAP, qm->cap_ver); + val = qm->cap_tables.qm_cap_table[QM_ABN_IRQ_TYPE_CAP_IDX].cap_val; if (!((val >> QM_IRQ_TYPE_SHIFT) & QM_ABN_IRQ_TYPE_MASK)) return 0;
@@ -4838,7 +4888,7 @@ static void qm_unregister_mb_cmd_irq(struct hisi_qm *qm) struct pci_dev *pdev = qm->pdev; u32 irq_vector, val;
- val = hisi_qm_get_hw_info(qm, qm_basic_info, QM_PF2VF_IRQ_TYPE_CAP, qm->cap_ver); + val = qm->cap_tables.qm_cap_table[QM_PF2VF_IRQ_TYPE_CAP_IDX].cap_val; if (!((val >> QM_IRQ_TYPE_SHIFT) & QM_IRQ_TYPE_MASK)) return;
@@ -4852,7 +4902,7 @@ static int qm_register_mb_cmd_irq(struct hisi_qm *qm) u32 irq_vector, val; int ret;
- val = hisi_qm_get_hw_info(qm, qm_basic_info, QM_PF2VF_IRQ_TYPE_CAP, qm->cap_ver); + val = qm->cap_tables.qm_cap_table[QM_PF2VF_IRQ_TYPE_CAP_IDX].cap_val; if (!((val >> QM_IRQ_TYPE_SHIFT) & QM_IRQ_TYPE_MASK)) return 0;
@@ -4869,7 +4919,7 @@ static void qm_unregister_aeq_irq(struct hisi_qm *qm) struct pci_dev *pdev = qm->pdev; u32 irq_vector, val;
- val = hisi_qm_get_hw_info(qm, qm_basic_info, QM_AEQ_IRQ_TYPE_CAP, qm->cap_ver); + val = qm->cap_tables.qm_cap_table[QM_AEQ_IRQ_TYPE_CAP_IDX].cap_val; if (!((val >> QM_IRQ_TYPE_SHIFT) & QM_IRQ_TYPE_MASK)) return;
@@ -4883,7 +4933,7 @@ static int qm_register_aeq_irq(struct hisi_qm *qm) u32 irq_vector, val; int ret;
- val = hisi_qm_get_hw_info(qm, qm_basic_info, QM_AEQ_IRQ_TYPE_CAP, qm->cap_ver); + val = qm->cap_tables.qm_cap_table[QM_AEQ_IRQ_TYPE_CAP_IDX].cap_val; if (!((val >> QM_IRQ_TYPE_SHIFT) & QM_IRQ_TYPE_MASK)) return 0;
@@ -4901,7 +4951,7 @@ static void qm_unregister_eq_irq(struct hisi_qm *qm) struct pci_dev *pdev = qm->pdev; u32 irq_vector, val;
- val = hisi_qm_get_hw_info(qm, qm_basic_info, QM_EQ_IRQ_TYPE_CAP, qm->cap_ver); + val = qm->cap_tables.qm_cap_table[QM_EQ_IRQ_TYPE_CAP_IDX].cap_val; if (!((val >> QM_IRQ_TYPE_SHIFT) & QM_IRQ_TYPE_MASK)) return;
@@ -4915,7 +4965,7 @@ static int qm_register_eq_irq(struct hisi_qm *qm) u32 irq_vector, val; int ret;
- val = hisi_qm_get_hw_info(qm, qm_basic_info, QM_EQ_IRQ_TYPE_CAP, qm->cap_ver); + val = qm->cap_tables.qm_cap_table[QM_EQ_IRQ_TYPE_CAP_IDX].cap_val; if (!((val >> QM_IRQ_TYPE_SHIFT) & QM_IRQ_TYPE_MASK)) return 0;
@@ -5003,7 +5053,29 @@ static int qm_get_qp_num(struct hisi_qm *qm) return 0; }
-static void qm_get_hw_caps(struct hisi_qm *qm) +static int qm_pre_store_irq_type_caps(struct hisi_qm *qm) +{ + struct hisi_qm_cap_record *qm_cap; + struct pci_dev *pdev = qm->pdev; + size_t i, size; + + size = ARRAY_SIZE(qm_pre_store_caps); + qm_cap = devm_kzalloc(&pdev->dev, sizeof(*qm_cap) * size, GFP_KERNEL); + if (!qm_cap) + return -ENOMEM; + + for (i = 0; i < size; i++) { + qm_cap[i].type = qm_pre_store_caps[i]; + qm_cap[i].cap_val = hisi_qm_get_hw_info(qm, qm_basic_info, + qm_pre_store_caps[i], qm->cap_ver); + } + + qm->cap_tables.qm_cap_table = qm_cap; + + return 0; +} + +static int qm_get_hw_caps(struct hisi_qm *qm) { const struct hisi_qm_cap_info *cap_info = qm->fun_type == QM_HW_PF ? qm_cap_info_pf : qm_cap_info_vf; @@ -5034,6 +5106,9 @@ static void qm_get_hw_caps(struct hisi_qm *qm) if (val) set_bit(cap_info[i].type, &qm->caps); } + + /* Fetch and save the value of irq type related capability registers */ + return qm_pre_store_irq_type_caps(qm); }
static int qm_get_pci_res(struct hisi_qm *qm) @@ -5055,7 +5130,10 @@ static int qm_get_pci_res(struct hisi_qm *qm) goto err_request_mem_regions; }
- qm_get_hw_caps(qm); + ret = qm_get_hw_caps(qm); + if (ret) + goto err_ioremap; + if (test_bit(QM_SUPPORT_DB_ISOLATION, &qm->caps)) { qm->db_interval = QM_QP_DB_INTERVAL; qm->db_phys_base = pci_resource_start(pdev, PCI_BAR_4); diff --git a/drivers/crypto/hisilicon/sec2/sec.h b/drivers/crypto/hisilicon/sec2/sec.h index 3e57fc04b377..410c83712e28 100644 --- a/drivers/crypto/hisilicon/sec2/sec.h +++ b/drivers/crypto/hisilicon/sec2/sec.h @@ -220,6 +220,13 @@ enum sec_cap_type { SEC_CORE4_ALG_BITMAP_HIGH, };
+enum sec_cap_reg_record_idx { + SEC_DRV_ALG_BITMAP_LOW_IDX = 0x0, + SEC_DRV_ALG_BITMAP_HIGH_IDX, + SEC_DEV_ALG_BITMAP_LOW_IDX, + SEC_DEV_ALG_BITMAP_HIGH_IDX, +}; + void sec_destroy_qps(struct hisi_qp **qps, int qp_num); struct hisi_qp **sec_create_qps(void); int sec_register_to_crypto(struct hisi_qm *qm); diff --git a/drivers/crypto/hisilicon/sec2/sec_crypto.c b/drivers/crypto/hisilicon/sec2/sec_crypto.c index 84ae8ddd1a13..cae7c414bdaf 100644 --- a/drivers/crypto/hisilicon/sec2/sec_crypto.c +++ b/drivers/crypto/hisilicon/sec2/sec_crypto.c @@ -2546,8 +2546,12 @@ static int sec_register_aead(u64 alg_mask)
int sec_register_to_crypto(struct hisi_qm *qm) { - u64 alg_mask = sec_get_alg_bitmap(qm, SEC_DRV_ALG_BITMAP_HIGH, SEC_DRV_ALG_BITMAP_LOW); - int ret; + u64 alg_mask; + int ret = 0; + + alg_mask = sec_get_alg_bitmap(qm, SEC_DRV_ALG_BITMAP_HIGH_IDX, + SEC_DRV_ALG_BITMAP_LOW_IDX); +
ret = sec_register_skcipher(alg_mask); if (ret) @@ -2562,7 +2566,10 @@ int sec_register_to_crypto(struct hisi_qm *qm)
void sec_unregister_from_crypto(struct hisi_qm *qm) { - u64 alg_mask = sec_get_alg_bitmap(qm, SEC_DRV_ALG_BITMAP_HIGH, SEC_DRV_ALG_BITMAP_LOW); + u64 alg_mask; + + alg_mask = sec_get_alg_bitmap(qm, SEC_DRV_ALG_BITMAP_HIGH_IDX, + SEC_DRV_ALG_BITMAP_LOW_IDX);
sec_unregister_aead(alg_mask, ARRAY_SIZE(sec_aeads)); sec_unregister_skcipher(alg_mask, ARRAY_SIZE(sec_skciphers)); diff --git a/drivers/crypto/hisilicon/sec2/sec_main.c b/drivers/crypto/hisilicon/sec2/sec_main.c index e384988bda91..4bab5000a13e 100644 --- a/drivers/crypto/hisilicon/sec2/sec_main.c +++ b/drivers/crypto/hisilicon/sec2/sec_main.c @@ -121,7 +121,6 @@ GENMASK_ULL(42, 25)) #define SEC_AEAD_BITMAP (GENMASK_ULL(7, 6) | GENMASK_ULL(18, 17) | \ GENMASK_ULL(45, 43)) -#define SEC_DEV_ALG_MAX_LEN 256
struct sec_hw_error { u32 int_msk; @@ -133,11 +132,6 @@ struct sec_dfx_item { u32 offset; };
-struct sec_dev_alg { - u64 alg_msk; - const char *algs; -}; - static const char sec_name[] = "hisi_sec2"; static struct dentry *sec_debugfs_root;
@@ -174,15 +168,22 @@ static const struct hisi_qm_cap_info sec_basic_info[] = { {SEC_CORE4_ALG_BITMAP_HIGH, 0x3170, 0, GENMASK(31, 0), 0x3FFF, 0x3FFF, 0x3FFF}, };
-static const struct sec_dev_alg sec_dev_algs[] = { { +static const u32 sec_pre_store_caps[] = { + SEC_DRV_ALG_BITMAP_LOW, + SEC_DRV_ALG_BITMAP_HIGH, + SEC_DEV_ALG_BITMAP_LOW, + SEC_DEV_ALG_BITMAP_HIGH, +}; + +static const struct qm_dev_alg sec_dev_algs[] = { { .alg_msk = SEC_CIPHER_BITMAP, - .algs = "cipher\n", + .alg = "cipher\n", }, { .alg_msk = SEC_DIGEST_BITMAP, - .algs = "digest\n", + .alg = "digest\n", }, { .alg_msk = SEC_AEAD_BITMAP, - .algs = "aead\n", + .alg = "aead\n", }, };
@@ -395,8 +396,8 @@ u64 sec_get_alg_bitmap(struct hisi_qm *qm, u32 high, u32 low) { u32 cap_val_h, cap_val_l;
- cap_val_h = hisi_qm_get_hw_info(qm, sec_basic_info, high, qm->cap_ver); - cap_val_l = hisi_qm_get_hw_info(qm, sec_basic_info, low, qm->cap_ver); + cap_val_h = qm->cap_tables.dev_cap_table[high].cap_val; + cap_val_l = qm->cap_tables.dev_cap_table[low].cap_val;
return ((u64)cap_val_h << SEC_ALG_BITMAP_SHIFT) | (u64)cap_val_l; } @@ -1079,37 +1080,31 @@ static int sec_pf_probe_init(struct sec_dev *sec) return ret; }
-static int sec_set_qm_algs(struct hisi_qm *qm) +static int sec_pre_store_cap_reg(struct hisi_qm *qm) { - struct device *dev = &qm->pdev->dev; - char *algs, *ptr; - u64 alg_mask; - int i; - - if (!qm->use_sva) - return 0; + struct hisi_qm_cap_record *sec_cap; + struct pci_dev *pdev = qm->pdev; + size_t i, size;
- algs = devm_kzalloc(dev, SEC_DEV_ALG_MAX_LEN * sizeof(char), GFP_KERNEL); - if (!algs) + size = ARRAY_SIZE(sec_pre_store_caps); + sec_cap = devm_kzalloc(&pdev->dev, sizeof(*sec_cap) * size, GFP_KERNEL); + if (!sec_cap) return -ENOMEM;
- alg_mask = sec_get_alg_bitmap(qm, SEC_DEV_ALG_BITMAP_HIGH, SEC_DEV_ALG_BITMAP_LOW); - - for (i = 0; i < ARRAY_SIZE(sec_dev_algs); i++) - if (alg_mask & sec_dev_algs[i].alg_msk) - strcat(algs, sec_dev_algs[i].algs); - - ptr = strrchr(algs, '\n'); - if (ptr) - *ptr = '\0'; + for (i = 0; i < size; i++) { + sec_cap[i].type = sec_pre_store_caps[i]; + sec_cap[i].cap_val = hisi_qm_get_hw_info(qm, sec_basic_info, + sec_pre_store_caps[i], qm->cap_ver); + }
- qm->uacce->algs = algs; + qm->cap_tables.dev_cap_table = sec_cap;
return 0; }
static int sec_qm_init(struct hisi_qm *qm, struct pci_dev *pdev) { + u64 alg_msk; int ret;
qm->pdev = pdev; @@ -1144,7 +1139,16 @@ static int sec_qm_init(struct hisi_qm *qm, struct pci_dev *pdev) return ret; }
- ret = sec_set_qm_algs(qm); + /* Fetch and save the value of capability registers */ + ret = sec_pre_store_cap_reg(qm); + if (ret) { + pci_err(qm->pdev, "Failed to pre-store capability registers!\n"); + hisi_qm_uninit(qm); + return ret; + } + + alg_msk = sec_get_alg_bitmap(qm, SEC_DEV_ALG_BITMAP_HIGH_IDX, SEC_DEV_ALG_BITMAP_LOW_IDX); + ret = hisi_qm_set_algs(qm, alg_msk, sec_dev_algs, ARRAY_SIZE(sec_dev_algs)); if (ret) { pci_err(qm->pdev, "Failed to set sec algs!\n"); hisi_qm_uninit(qm); diff --git a/drivers/crypto/hisilicon/zip/zip_main.c b/drivers/crypto/hisilicon/zip/zip_main.c index 190b4fecfc74..9e3f5bca27de 100644 --- a/drivers/crypto/hisilicon/zip/zip_main.c +++ b/drivers/crypto/hisilicon/zip/zip_main.c @@ -74,7 +74,6 @@ #define HZIP_AXI_SHUTDOWN_ENABLE BIT(14) #define HZIP_WR_PORT BIT(11)
-#define HZIP_DEV_ALG_MAX_LEN 256 #define HZIP_ALG_ZLIB_BIT GENMASK(1, 0) #define HZIP_ALG_GZIP_BIT GENMASK(3, 2) #define HZIP_ALG_DEFLATE_BIT GENMASK(5, 4) @@ -107,6 +106,14 @@ #define HZIP_CLOCK_GATED_EN (HZIP_CORE_GATED_EN | \ HZIP_CORE_GATED_OOO_EN)
+/* zip comp high performance */ +#define HZIP_HIGH_PERF_OFFSET 0x301208 + +enum { + HZIP_HIGH_COMP_RATE, + HZIP_HIGH_COMP_PERF, +}; + static const char hisi_zip_name[] = "hisi_zip"; static struct dentry *hzip_debugfs_root;
@@ -120,23 +127,18 @@ struct zip_dfx_item { u32 offset; };
-struct zip_dev_alg { - u32 alg_msk; - const char *algs; -}; - -static const struct zip_dev_alg zip_dev_algs[] = { { +static const struct qm_dev_alg zip_dev_algs[] = { { .alg_msk = HZIP_ALG_ZLIB_BIT, - .algs = "zlib\n", + .alg = "zlib\n", }, { .alg_msk = HZIP_ALG_GZIP_BIT, - .algs = "gzip\n", + .alg = "gzip\n", }, { .alg_msk = HZIP_ALG_DEFLATE_BIT, - .algs = "deflate\n", + .alg = "deflate\n", }, { .alg_msk = HZIP_ALG_LZ77_BIT, - .algs = "lz77_zstd\n", + .alg = "lz77_zstd\n", }, };
@@ -247,6 +249,26 @@ static struct hisi_qm_cap_info zip_basic_cap_info[] = { {ZIP_CAP_MAX, 0x317c, 0, GENMASK(0, 0), 0x0, 0x0, 0x0} };
+enum zip_pre_store_cap_idx { + ZIP_CORE_NUM_CAP_IDX = 0x0, + ZIP_CLUSTER_COMP_NUM_CAP_IDX, + ZIP_CLUSTER_DECOMP_NUM_CAP_IDX, + ZIP_DECOMP_ENABLE_BITMAP_IDX, + ZIP_COMP_ENABLE_BITMAP_IDX, + ZIP_DRV_ALG_BITMAP_IDX, + ZIP_DEV_ALG_BITMAP_IDX, +}; + +static const u32 zip_pre_store_caps[] = { + ZIP_CORE_NUM_CAP, + ZIP_CLUSTER_COMP_NUM_CAP, + ZIP_CLUSTER_DECOMP_NUM_CAP, + ZIP_DECOMP_ENABLE_BITMAP, + ZIP_COMP_ENABLE_BITMAP, + ZIP_DRV_ALG_BITMAP, + ZIP_DEV_ALG_BITMAP, +}; + enum { HZIP_COMP_CORE0, HZIP_COMP_CORE1, @@ -352,6 +374,37 @@ static int hzip_diff_regs_show(struct seq_file *s, void *unused) return 0; } DEFINE_SHOW_ATTRIBUTE(hzip_diff_regs); + +static int perf_mode_set(const char *val, const struct kernel_param *kp) +{ + int ret; + u32 n; + + if (!val) + return -EINVAL; + + ret = kstrtou32(val, 10, &n); + if (ret != 0 || (n != HZIP_HIGH_COMP_PERF && + n != HZIP_HIGH_COMP_RATE)) + return -EINVAL; + + return param_set_int(val, kp); +} + +static const struct kernel_param_ops zip_com_perf_ops = { + .set = perf_mode_set, + .get = param_get_int, +}; + +/* + * perf_mode = 0 means enable high compression rate mode, + * perf_mode = 1 means enable high compression performance mode. + * These two modes only apply to the compression direction. + */ +static u32 perf_mode = HZIP_HIGH_COMP_RATE; +module_param_cb(perf_mode, &zip_com_perf_ops, &perf_mode, 0444); +MODULE_PARM_DESC(perf_mode, "ZIP high perf mode 0(default), 1(enable)"); + static const struct kernel_param_ops zip_uacce_mode_ops = { .set = uacce_mode_set, .get = param_get_int, @@ -410,40 +463,33 @@ bool hisi_zip_alg_support(struct hisi_qm *qm, u32 alg) { u32 cap_val;
- cap_val = hisi_qm_get_hw_info(qm, zip_basic_cap_info, ZIP_DRV_ALG_BITMAP, qm->cap_ver); + cap_val = qm->cap_tables.dev_cap_table[ZIP_DRV_ALG_BITMAP_IDX].cap_val; if ((alg & cap_val) == alg) return true;
return false; }
-static int hisi_zip_set_qm_algs(struct hisi_qm *qm) +static int hisi_zip_set_high_perf(struct hisi_qm *qm) { - struct device *dev = &qm->pdev->dev; - char *algs, *ptr; - u32 alg_mask; - int i; - - if (!qm->use_sva) - return 0; - - algs = devm_kzalloc(dev, HZIP_DEV_ALG_MAX_LEN * sizeof(char), GFP_KERNEL); - if (!algs) - return -ENOMEM; - - alg_mask = hisi_qm_get_hw_info(qm, zip_basic_cap_info, ZIP_DEV_ALG_BITMAP, qm->cap_ver); - - for (i = 0; i < ARRAY_SIZE(zip_dev_algs); i++) - if (alg_mask & zip_dev_algs[i].alg_msk) - strcat(algs, zip_dev_algs[i].algs); - - ptr = strrchr(algs, '\n'); - if (ptr) - *ptr = '\0'; + u32 val; + int ret;
- qm->uacce->algs = algs; + val = readl_relaxed(qm->io_base + HZIP_HIGH_PERF_OFFSET); + if (perf_mode == HZIP_HIGH_COMP_PERF) + val |= HZIP_HIGH_COMP_PERF; + else + val &= ~HZIP_HIGH_COMP_PERF; + + /* Set perf mode */ + writel(val, qm->io_base + HZIP_HIGH_PERF_OFFSET); + ret = readl_relaxed_poll_timeout(qm->io_base + HZIP_HIGH_PERF_OFFSET, + val, val == perf_mode, HZIP_DELAY_1_US, + HZIP_POLL_TIMEOUT_US); + if (ret) + pci_err(qm->pdev, "failed to set perf mode\n");
- return 0; + return ret; }
static void hisi_zip_open_sva_prefetch(struct hisi_qm *qm) @@ -542,10 +588,8 @@ static int hisi_zip_set_user_domain_and_cache(struct hisi_qm *qm) }
/* let's open all compression/decompression cores */ - dcomp_bm = hisi_qm_get_hw_info(qm, zip_basic_cap_info, - ZIP_DECOMP_ENABLE_BITMAP, qm->cap_ver); - comp_bm = hisi_qm_get_hw_info(qm, zip_basic_cap_info, - ZIP_COMP_ENABLE_BITMAP, qm->cap_ver); + dcomp_bm = qm->cap_tables.dev_cap_table[ZIP_DECOMP_ENABLE_BITMAP_IDX].cap_val; + comp_bm = qm->cap_tables.dev_cap_table[ZIP_COMP_ENABLE_BITMAP_IDX].cap_val; writel(HZIP_DECOMP_CHECK_ENABLE | dcomp_bm | comp_bm, base + HZIP_CLOCK_GATE_CTRL);
/* enable sqc,cqc writeback */ @@ -772,9 +816,8 @@ static int hisi_zip_core_debug_init(struct hisi_qm *qm) char buf[HZIP_BUF_SIZE]; int i;
- zip_core_num = hisi_qm_get_hw_info(qm, zip_basic_cap_info, ZIP_CORE_NUM_CAP, qm->cap_ver); - zip_comp_core_num = hisi_qm_get_hw_info(qm, zip_basic_cap_info, ZIP_CLUSTER_COMP_NUM_CAP, - qm->cap_ver); + zip_core_num = qm->cap_tables.dev_cap_table[ZIP_CORE_NUM_CAP_IDX].cap_val; + zip_comp_core_num = qm->cap_tables.dev_cap_table[ZIP_CLUSTER_COMP_NUM_CAP_IDX].cap_val;
for (i = 0; i < zip_core_num; i++) { if (i < zip_comp_core_num) @@ -916,7 +959,7 @@ static int hisi_zip_show_last_regs_init(struct hisi_qm *qm) u32 zip_core_num; int i, j, idx;
- zip_core_num = hisi_qm_get_hw_info(qm, zip_basic_cap_info, ZIP_CORE_NUM_CAP, qm->cap_ver); + zip_core_num = qm->cap_tables.dev_cap_table[ZIP_CORE_NUM_CAP_IDX].cap_val;
debug->last_words = kcalloc(core_dfx_regs_num * zip_core_num + com_dfx_regs_num, sizeof(unsigned int), GFP_KERNEL); @@ -972,9 +1015,9 @@ static void hisi_zip_show_last_dfx_regs(struct hisi_qm *qm) hzip_com_dfx_regs[i].name, debug->last_words[i], val); }
- zip_core_num = hisi_qm_get_hw_info(qm, zip_basic_cap_info, ZIP_CORE_NUM_CAP, qm->cap_ver); - zip_comp_core_num = hisi_qm_get_hw_info(qm, zip_basic_cap_info, ZIP_CLUSTER_COMP_NUM_CAP, - qm->cap_ver); + zip_core_num = qm->cap_tables.dev_cap_table[ZIP_CORE_NUM_CAP_IDX].cap_val; + zip_comp_core_num = qm->cap_tables.dev_cap_table[ZIP_CLUSTER_COMP_NUM_CAP_IDX].cap_val; + for (i = 0; i < zip_core_num; i++) { if (i < zip_comp_core_num) scnprintf(buf, sizeof(buf), "Comp_core-%d", i); @@ -1115,6 +1158,10 @@ static int hisi_zip_pf_probe_init(struct hisi_zip *hisi_zip) if (ret) return ret;
+ ret = hisi_zip_set_high_perf(qm); + if (ret) + return ret; + hisi_zip_open_sva_prefetch(qm); hisi_qm_dev_err_init(qm); hisi_zip_debug_regs_clear(qm); @@ -1126,8 +1173,31 @@ static int hisi_zip_pf_probe_init(struct hisi_zip *hisi_zip) return ret; }
+static int zip_pre_store_cap_reg(struct hisi_qm *qm) +{ + struct hisi_qm_cap_record *zip_cap; + struct pci_dev *pdev = qm->pdev; + size_t i, size; + + size = ARRAY_SIZE(zip_pre_store_caps); + zip_cap = devm_kzalloc(&pdev->dev, sizeof(*zip_cap) * size, GFP_KERNEL); + if (!zip_cap) + return -ENOMEM; + + for (i = 0; i < size; i++) { + zip_cap[i].type = zip_pre_store_caps[i]; + zip_cap[i].cap_val = hisi_qm_get_hw_info(qm, zip_basic_cap_info, + zip_pre_store_caps[i], qm->cap_ver); + } + + qm->cap_tables.dev_cap_table = zip_cap; + + return 0; +} + static int hisi_zip_qm_init(struct hisi_qm *qm, struct pci_dev *pdev) { + u64 alg_msk; int ret;
qm->pdev = pdev; @@ -1163,7 +1233,16 @@ static int hisi_zip_qm_init(struct hisi_qm *qm, struct pci_dev *pdev) return ret; }
- ret = hisi_zip_set_qm_algs(qm); + /* Fetch and save the value of capability registers */ + ret = zip_pre_store_cap_reg(qm); + if (ret) { + pci_err(qm->pdev, "Failed to pre-store capability registers!\n"); + hisi_qm_uninit(qm); + return ret; + } + + alg_msk = qm->cap_tables.dev_cap_table[ZIP_DEV_ALG_BITMAP_IDX].cap_val; + ret = hisi_qm_set_algs(qm, alg_msk, zip_dev_algs, ARRAY_SIZE(zip_dev_algs)); if (ret) { pci_err(qm->pdev, "Failed to set zip algs!\n"); hisi_qm_uninit(qm); diff --git a/drivers/crypto/inside-secure/safexcel_cipher.c b/drivers/crypto/inside-secure/safexcel_cipher.c index 32a37e3850c5..f59e32115268 100644 --- a/drivers/crypto/inside-secure/safexcel_cipher.c +++ b/drivers/crypto/inside-secure/safexcel_cipher.c @@ -742,9 +742,9 @@ static int safexcel_send_req(struct crypto_async_request *base, int ring, max(totlen_src, totlen_dst)); return -EINVAL; } - if (sreq->nr_src > 0) - dma_map_sg(priv->dev, src, sreq->nr_src, - DMA_BIDIRECTIONAL); + if (sreq->nr_src > 0 && + !dma_map_sg(priv->dev, src, sreq->nr_src, DMA_BIDIRECTIONAL)) + return -EIO; } else { if (unlikely(totlen_src && (sreq->nr_src <= 0))) { dev_err(priv->dev, "Source buffer not large enough (need %d bytes)!", @@ -752,8 +752,9 @@ static int safexcel_send_req(struct crypto_async_request *base, int ring, return -EINVAL; }
- if (sreq->nr_src > 0) - dma_map_sg(priv->dev, src, sreq->nr_src, DMA_TO_DEVICE); + if (sreq->nr_src > 0 && + !dma_map_sg(priv->dev, src, sreq->nr_src, DMA_TO_DEVICE)) + return -EIO;
if (unlikely(totlen_dst && (sreq->nr_dst <= 0))) { dev_err(priv->dev, "Dest buffer not large enough (need %d bytes)!", @@ -762,9 +763,11 @@ static int safexcel_send_req(struct crypto_async_request *base, int ring, goto unmap; }
- if (sreq->nr_dst > 0) - dma_map_sg(priv->dev, dst, sreq->nr_dst, - DMA_FROM_DEVICE); + if (sreq->nr_dst > 0 && + !dma_map_sg(priv->dev, dst, sreq->nr_dst, DMA_FROM_DEVICE)) { + ret = -EIO; + goto unmap; + } }
memcpy(ctx->base.ctxr->data, ctx->key, ctx->key_len); diff --git a/drivers/crypto/sa2ul.c b/drivers/crypto/sa2ul.c index f4bc06c24ad8..e7efebf8127f 100644 --- a/drivers/crypto/sa2ul.c +++ b/drivers/crypto/sa2ul.c @@ -1868,9 +1868,8 @@ static int sa_aead_setkey(struct crypto_aead *authenc, crypto_aead_set_flags(ctx->fallback.aead, crypto_aead_get_flags(authenc) & CRYPTO_TFM_REQ_MASK); - crypto_aead_setkey(ctx->fallback.aead, key, keylen);
- return 0; + return crypto_aead_setkey(ctx->fallback.aead, key, keylen); }
static int sa_aead_setauthsize(struct crypto_aead *tfm, unsigned int authsize) diff --git a/drivers/crypto/sahara.c b/drivers/crypto/sahara.c index 7ab20fb95166..3b946f1313ed 100644 --- a/drivers/crypto/sahara.c +++ b/drivers/crypto/sahara.c @@ -44,7 +44,6 @@ #define FLAGS_MODE_MASK 0x000f #define FLAGS_ENCRYPT BIT(0) #define FLAGS_CBC BIT(1) -#define FLAGS_NEW_KEY BIT(3)
#define SAHARA_HDR_BASE 0x00800000 #define SAHARA_HDR_SKHA_ALG_AES 0 @@ -142,8 +141,6 @@ struct sahara_hw_link { };
struct sahara_ctx { - unsigned long flags; - /* AES-specific context */ int keylen; u8 key[AES_KEYSIZE_128]; @@ -152,6 +149,7 @@ struct sahara_ctx {
struct sahara_aes_reqctx { unsigned long mode; + u8 iv_out[AES_BLOCK_SIZE]; struct skcipher_request fallback_req; // keep at the end };
@@ -447,27 +445,24 @@ static int sahara_hw_descriptor_create(struct sahara_dev *dev) int ret; int i, j; int idx = 0; + u32 len;
- /* Copy new key if necessary */ - if (ctx->flags & FLAGS_NEW_KEY) { - memcpy(dev->key_base, ctx->key, ctx->keylen); - ctx->flags &= ~FLAGS_NEW_KEY; + memcpy(dev->key_base, ctx->key, ctx->keylen);
- if (dev->flags & FLAGS_CBC) { - dev->hw_desc[idx]->len1 = AES_BLOCK_SIZE; - dev->hw_desc[idx]->p1 = dev->iv_phys_base; - } else { - dev->hw_desc[idx]->len1 = 0; - dev->hw_desc[idx]->p1 = 0; - } - dev->hw_desc[idx]->len2 = ctx->keylen; - dev->hw_desc[idx]->p2 = dev->key_phys_base; - dev->hw_desc[idx]->next = dev->hw_phys_desc[1]; + if (dev->flags & FLAGS_CBC) { + dev->hw_desc[idx]->len1 = AES_BLOCK_SIZE; + dev->hw_desc[idx]->p1 = dev->iv_phys_base; + } else { + dev->hw_desc[idx]->len1 = 0; + dev->hw_desc[idx]->p1 = 0; + } + dev->hw_desc[idx]->len2 = ctx->keylen; + dev->hw_desc[idx]->p2 = dev->key_phys_base; + dev->hw_desc[idx]->next = dev->hw_phys_desc[1]; + dev->hw_desc[idx]->hdr = sahara_aes_key_hdr(dev);
- dev->hw_desc[idx]->hdr = sahara_aes_key_hdr(dev); + idx++;
- idx++; - }
dev->nb_in_sg = sg_nents_for_len(dev->in_sg, dev->total); if (dev->nb_in_sg < 0) { @@ -489,24 +484,27 @@ static int sahara_hw_descriptor_create(struct sahara_dev *dev) DMA_TO_DEVICE); if (!ret) { dev_err(dev->device, "couldn't map in sg\n"); - goto unmap_in; + return -EINVAL; } + ret = dma_map_sg(dev->device, dev->out_sg, dev->nb_out_sg, DMA_FROM_DEVICE); if (!ret) { dev_err(dev->device, "couldn't map out sg\n"); - goto unmap_out; + goto unmap_in; }
/* Create input links */ dev->hw_desc[idx]->p1 = dev->hw_phys_link[0]; sg = dev->in_sg; + len = dev->total; for (i = 0; i < dev->nb_in_sg; i++) { - dev->hw_link[i]->len = sg->length; + dev->hw_link[i]->len = min(len, sg->length); dev->hw_link[i]->p = sg->dma_address; if (i == (dev->nb_in_sg - 1)) { dev->hw_link[i]->next = 0; } else { + len -= min(len, sg->length); dev->hw_link[i]->next = dev->hw_phys_link[i + 1]; sg = sg_next(sg); } @@ -515,12 +513,14 @@ static int sahara_hw_descriptor_create(struct sahara_dev *dev) /* Create output links */ dev->hw_desc[idx]->p2 = dev->hw_phys_link[i]; sg = dev->out_sg; + len = dev->total; for (j = i; j < dev->nb_out_sg + i; j++) { - dev->hw_link[j]->len = sg->length; + dev->hw_link[j]->len = min(len, sg->length); dev->hw_link[j]->p = sg->dma_address; if (j == (dev->nb_out_sg + i - 1)) { dev->hw_link[j]->next = 0; } else { + len -= min(len, sg->length); dev->hw_link[j]->next = dev->hw_phys_link[j + 1]; sg = sg_next(sg); } @@ -539,9 +539,6 @@ static int sahara_hw_descriptor_create(struct sahara_dev *dev)
return 0;
-unmap_out: - dma_unmap_sg(dev->device, dev->out_sg, dev->nb_out_sg, - DMA_FROM_DEVICE); unmap_in: dma_unmap_sg(dev->device, dev->in_sg, dev->nb_in_sg, DMA_TO_DEVICE); @@ -549,8 +546,24 @@ static int sahara_hw_descriptor_create(struct sahara_dev *dev) return -EINVAL; }
+static void sahara_aes_cbc_update_iv(struct skcipher_request *req) +{ + struct crypto_skcipher *skcipher = crypto_skcipher_reqtfm(req); + struct sahara_aes_reqctx *rctx = skcipher_request_ctx(req); + unsigned int ivsize = crypto_skcipher_ivsize(skcipher); + + /* Update IV buffer to contain the last ciphertext block */ + if (rctx->mode & FLAGS_ENCRYPT) { + sg_pcopy_to_buffer(req->dst, sg_nents(req->dst), req->iv, + ivsize, req->cryptlen - ivsize); + } else { + memcpy(req->iv, rctx->iv_out, ivsize); + } +} + static int sahara_aes_process(struct skcipher_request *req) { + struct crypto_skcipher *skcipher = crypto_skcipher_reqtfm(req); struct sahara_dev *dev = dev_ptr; struct sahara_ctx *ctx; struct sahara_aes_reqctx *rctx; @@ -572,8 +585,17 @@ static int sahara_aes_process(struct skcipher_request *req) rctx->mode &= FLAGS_MODE_MASK; dev->flags = (dev->flags & ~FLAGS_MODE_MASK) | rctx->mode;
- if ((dev->flags & FLAGS_CBC) && req->iv) - memcpy(dev->iv_base, req->iv, AES_KEYSIZE_128); + if ((dev->flags & FLAGS_CBC) && req->iv) { + unsigned int ivsize = crypto_skcipher_ivsize(skcipher); + + memcpy(dev->iv_base, req->iv, ivsize); + + if (!(dev->flags & FLAGS_ENCRYPT)) { + sg_pcopy_to_buffer(req->src, sg_nents(req->src), + rctx->iv_out, ivsize, + req->cryptlen - ivsize); + } + }
/* assign new context to device */ dev->ctx = ctx; @@ -586,16 +608,20 @@ static int sahara_aes_process(struct skcipher_request *req)
timeout = wait_for_completion_timeout(&dev->dma_completion, msecs_to_jiffies(SAHARA_TIMEOUT_MS)); - if (!timeout) { - dev_err(dev->device, "AES timeout\n"); - return -ETIMEDOUT; - }
dma_unmap_sg(dev->device, dev->out_sg, dev->nb_out_sg, DMA_FROM_DEVICE); dma_unmap_sg(dev->device, dev->in_sg, dev->nb_in_sg, DMA_TO_DEVICE);
+ if (!timeout) { + dev_err(dev->device, "AES timeout\n"); + return -ETIMEDOUT; + } + + if ((dev->flags & FLAGS_CBC) && req->iv) + sahara_aes_cbc_update_iv(req); + return 0; }
@@ -609,7 +635,6 @@ static int sahara_aes_setkey(struct crypto_skcipher *tfm, const u8 *key, /* SAHARA only supports 128bit keys */ if (keylen == AES_KEYSIZE_128) { memcpy(ctx->key, key, keylen); - ctx->flags |= FLAGS_NEW_KEY; return 0; }
@@ -625,12 +650,40 @@ static int sahara_aes_setkey(struct crypto_skcipher *tfm, const u8 *key, return crypto_skcipher_setkey(ctx->fallback, key, keylen); }
+static int sahara_aes_fallback(struct skcipher_request *req, unsigned long mode) +{ + struct sahara_aes_reqctx *rctx = skcipher_request_ctx(req); + struct sahara_ctx *ctx = crypto_skcipher_ctx( + crypto_skcipher_reqtfm(req)); + + skcipher_request_set_tfm(&rctx->fallback_req, ctx->fallback); + skcipher_request_set_callback(&rctx->fallback_req, + req->base.flags, + req->base.complete, + req->base.data); + skcipher_request_set_crypt(&rctx->fallback_req, req->src, + req->dst, req->cryptlen, req->iv); + + if (mode & FLAGS_ENCRYPT) + return crypto_skcipher_encrypt(&rctx->fallback_req); + + return crypto_skcipher_decrypt(&rctx->fallback_req); +} + static int sahara_aes_crypt(struct skcipher_request *req, unsigned long mode) { struct sahara_aes_reqctx *rctx = skcipher_request_ctx(req); + struct sahara_ctx *ctx = crypto_skcipher_ctx( + crypto_skcipher_reqtfm(req)); struct sahara_dev *dev = dev_ptr; int err = 0;
+ if (!req->cryptlen) + return 0; + + if (unlikely(ctx->keylen != AES_KEYSIZE_128)) + return sahara_aes_fallback(req, mode); + dev_dbg(dev->device, "nbytes: %d, enc: %d, cbc: %d\n", req->cryptlen, !!(mode & FLAGS_ENCRYPT), !!(mode & FLAGS_CBC));
@@ -653,81 +706,21 @@ static int sahara_aes_crypt(struct skcipher_request *req, unsigned long mode)
static int sahara_aes_ecb_encrypt(struct skcipher_request *req) { - struct sahara_aes_reqctx *rctx = skcipher_request_ctx(req); - struct sahara_ctx *ctx = crypto_skcipher_ctx( - crypto_skcipher_reqtfm(req)); - - if (unlikely(ctx->keylen != AES_KEYSIZE_128)) { - skcipher_request_set_tfm(&rctx->fallback_req, ctx->fallback); - skcipher_request_set_callback(&rctx->fallback_req, - req->base.flags, - req->base.complete, - req->base.data); - skcipher_request_set_crypt(&rctx->fallback_req, req->src, - req->dst, req->cryptlen, req->iv); - return crypto_skcipher_encrypt(&rctx->fallback_req); - } - return sahara_aes_crypt(req, FLAGS_ENCRYPT); }
static int sahara_aes_ecb_decrypt(struct skcipher_request *req) { - struct sahara_aes_reqctx *rctx = skcipher_request_ctx(req); - struct sahara_ctx *ctx = crypto_skcipher_ctx( - crypto_skcipher_reqtfm(req)); - - if (unlikely(ctx->keylen != AES_KEYSIZE_128)) { - skcipher_request_set_tfm(&rctx->fallback_req, ctx->fallback); - skcipher_request_set_callback(&rctx->fallback_req, - req->base.flags, - req->base.complete, - req->base.data); - skcipher_request_set_crypt(&rctx->fallback_req, req->src, - req->dst, req->cryptlen, req->iv); - return crypto_skcipher_decrypt(&rctx->fallback_req); - } - return sahara_aes_crypt(req, 0); }
static int sahara_aes_cbc_encrypt(struct skcipher_request *req) { - struct sahara_aes_reqctx *rctx = skcipher_request_ctx(req); - struct sahara_ctx *ctx = crypto_skcipher_ctx( - crypto_skcipher_reqtfm(req)); - - if (unlikely(ctx->keylen != AES_KEYSIZE_128)) { - skcipher_request_set_tfm(&rctx->fallback_req, ctx->fallback); - skcipher_request_set_callback(&rctx->fallback_req, - req->base.flags, - req->base.complete, - req->base.data); - skcipher_request_set_crypt(&rctx->fallback_req, req->src, - req->dst, req->cryptlen, req->iv); - return crypto_skcipher_encrypt(&rctx->fallback_req); - } - return sahara_aes_crypt(req, FLAGS_ENCRYPT | FLAGS_CBC); }
static int sahara_aes_cbc_decrypt(struct skcipher_request *req) { - struct sahara_aes_reqctx *rctx = skcipher_request_ctx(req); - struct sahara_ctx *ctx = crypto_skcipher_ctx( - crypto_skcipher_reqtfm(req)); - - if (unlikely(ctx->keylen != AES_KEYSIZE_128)) { - skcipher_request_set_tfm(&rctx->fallback_req, ctx->fallback); - skcipher_request_set_callback(&rctx->fallback_req, - req->base.flags, - req->base.complete, - req->base.data); - skcipher_request_set_crypt(&rctx->fallback_req, req->src, - req->dst, req->cryptlen, req->iv); - return crypto_skcipher_decrypt(&rctx->fallback_req); - } - return sahara_aes_crypt(req, FLAGS_CBC); }
@@ -784,6 +777,7 @@ static int sahara_sha_hw_links_create(struct sahara_dev *dev, int start) { struct scatterlist *sg; + unsigned int len; unsigned int i; int ret;
@@ -805,12 +799,14 @@ static int sahara_sha_hw_links_create(struct sahara_dev *dev, if (!ret) return -EFAULT;
+ len = rctx->total; for (i = start; i < dev->nb_in_sg + start; i++) { - dev->hw_link[i]->len = sg->length; + dev->hw_link[i]->len = min(len, sg->length); dev->hw_link[i]->p = sg->dma_address; if (i == (dev->nb_in_sg + start - 1)) { dev->hw_link[i]->next = 0; } else { + len -= min(len, sg->length); dev->hw_link[i]->next = dev->hw_phys_link[i + 1]; sg = sg_next(sg); } @@ -891,24 +887,6 @@ static int sahara_sha_hw_context_descriptor_create(struct sahara_dev *dev, return 0; }
-static int sahara_walk_and_recalc(struct scatterlist *sg, unsigned int nbytes) -{ - if (!sg || !sg->length) - return nbytes; - - while (nbytes && sg) { - if (nbytes <= sg->length) { - sg->length = nbytes; - sg_mark_end(sg); - break; - } - nbytes -= sg->length; - sg = sg_next(sg); - } - - return nbytes; -} - static int sahara_sha_prepare_request(struct ahash_request *req) { struct crypto_ahash *tfm = crypto_ahash_reqtfm(req); @@ -945,36 +923,20 @@ static int sahara_sha_prepare_request(struct ahash_request *req) hash_later, 0); }
- /* nbytes should now be multiple of blocksize */ - req->nbytes = req->nbytes - hash_later; - - sahara_walk_and_recalc(req->src, req->nbytes); - + rctx->total = len - hash_later; /* have data from previous operation and current */ if (rctx->buf_cnt && req->nbytes) { sg_init_table(rctx->in_sg_chain, 2); sg_set_buf(rctx->in_sg_chain, rctx->rembuf, rctx->buf_cnt); - sg_chain(rctx->in_sg_chain, 2, req->src); - - rctx->total = req->nbytes + rctx->buf_cnt; rctx->in_sg = rctx->in_sg_chain; - - req->src = rctx->in_sg_chain; /* only data from previous operation */ } else if (rctx->buf_cnt) { - if (req->src) - rctx->in_sg = req->src; - else - rctx->in_sg = rctx->in_sg_chain; - /* buf was copied into rembuf above */ + rctx->in_sg = rctx->in_sg_chain; sg_init_one(rctx->in_sg, rctx->rembuf, rctx->buf_cnt); - rctx->total = rctx->buf_cnt; /* no data from previous operation */ } else { rctx->in_sg = req->src; - rctx->total = req->nbytes; - req->src = rctx->in_sg; }
/* on next call, we only have the remaining data in the buffer */ @@ -995,7 +957,10 @@ static int sahara_sha_process(struct ahash_request *req) return ret;
if (rctx->first) { - sahara_sha_hw_data_descriptor_create(dev, rctx, req, 0); + ret = sahara_sha_hw_data_descriptor_create(dev, rctx, req, 0); + if (ret) + return ret; + dev->hw_desc[0]->next = 0; rctx->first = 0; } else { @@ -1003,7 +968,10 @@ static int sahara_sha_process(struct ahash_request *req)
sahara_sha_hw_context_descriptor_create(dev, rctx, req, 0); dev->hw_desc[0]->next = dev->hw_phys_desc[1]; - sahara_sha_hw_data_descriptor_create(dev, rctx, req, 1); + ret = sahara_sha_hw_data_descriptor_create(dev, rctx, req, 1); + if (ret) + return ret; + dev->hw_desc[1]->next = 0; }
@@ -1016,18 +984,19 @@ static int sahara_sha_process(struct ahash_request *req)
timeout = wait_for_completion_timeout(&dev->dma_completion, msecs_to_jiffies(SAHARA_TIMEOUT_MS)); - if (!timeout) { - dev_err(dev->device, "SHA timeout\n"); - return -ETIMEDOUT; - }
if (rctx->sg_in_idx) dma_unmap_sg(dev->device, dev->in_sg, dev->nb_in_sg, DMA_TO_DEVICE);
+ if (!timeout) { + dev_err(dev->device, "SHA timeout\n"); + return -ETIMEDOUT; + } + memcpy(rctx->context, dev->context_base, rctx->context_size);
- if (req->result) + if (req->result && rctx->last) memcpy(req->result, rctx->context, rctx->digest_size);
return 0; @@ -1171,8 +1140,7 @@ static int sahara_sha_import(struct ahash_request *req, const void *in) static int sahara_sha_cra_init(struct crypto_tfm *tfm) { crypto_ahash_set_reqsize(__crypto_ahash_cast(tfm), - sizeof(struct sahara_sha_reqctx) + - SHA_BUFFER_LEN + SHA256_BLOCK_SIZE); + sizeof(struct sahara_sha_reqctx));
return 0; } diff --git a/drivers/crypto/virtio/virtio_crypto_common.h b/drivers/crypto/virtio/virtio_crypto_common.h index 154590e1f764..7059bbe5a2eb 100644 --- a/drivers/crypto/virtio/virtio_crypto_common.h +++ b/drivers/crypto/virtio/virtio_crypto_common.h @@ -10,6 +10,7 @@ #include <linux/virtio.h> #include <linux/crypto.h> #include <linux/spinlock.h> +#include <linux/interrupt.h> #include <crypto/aead.h> #include <crypto/aes.h> #include <crypto/engine.h> @@ -28,6 +29,7 @@ struct data_queue { char name[32];
struct crypto_engine *engine; + struct tasklet_struct done_task; };
struct virtio_crypto { diff --git a/drivers/crypto/virtio/virtio_crypto_core.c b/drivers/crypto/virtio/virtio_crypto_core.c index 3842915ea743..56dc0935c774 100644 --- a/drivers/crypto/virtio/virtio_crypto_core.c +++ b/drivers/crypto/virtio/virtio_crypto_core.c @@ -72,27 +72,28 @@ int virtio_crypto_ctrl_vq_request(struct virtio_crypto *vcrypto, struct scatterl return 0; }
-static void virtcrypto_dataq_callback(struct virtqueue *vq) +static void virtcrypto_done_task(unsigned long data) { - struct virtio_crypto *vcrypto = vq->vdev->priv; + struct data_queue *data_vq = (struct data_queue *)data; + struct virtqueue *vq = data_vq->vq; struct virtio_crypto_request *vc_req; - unsigned long flags; unsigned int len; - unsigned int qid = vq->index;
- spin_lock_irqsave(&vcrypto->data_vq[qid].lock, flags); do { virtqueue_disable_cb(vq); while ((vc_req = virtqueue_get_buf(vq, &len)) != NULL) { - spin_unlock_irqrestore( - &vcrypto->data_vq[qid].lock, flags); if (vc_req->alg_cb) vc_req->alg_cb(vc_req, len); - spin_lock_irqsave( - &vcrypto->data_vq[qid].lock, flags); } } while (!virtqueue_enable_cb(vq)); - spin_unlock_irqrestore(&vcrypto->data_vq[qid].lock, flags); +} + +static void virtcrypto_dataq_callback(struct virtqueue *vq) +{ + struct virtio_crypto *vcrypto = vq->vdev->priv; + struct data_queue *dq = &vcrypto->data_vq[vq->index]; + + tasklet_schedule(&dq->done_task); }
static int virtcrypto_find_vqs(struct virtio_crypto *vi) @@ -150,6 +151,8 @@ static int virtcrypto_find_vqs(struct virtio_crypto *vi) ret = -ENOMEM; goto err_engine; } + tasklet_init(&vi->data_vq[i].done_task, virtcrypto_done_task, + (unsigned long)&vi->data_vq[i]); }
kfree(names); @@ -496,12 +499,15 @@ static void virtcrypto_free_unused_reqs(struct virtio_crypto *vcrypto) static void virtcrypto_remove(struct virtio_device *vdev) { struct virtio_crypto *vcrypto = vdev->priv; + int i;
dev_info(&vdev->dev, "Start virtcrypto_remove.\n");
flush_work(&vcrypto->config_work); if (virtcrypto_dev_started(vcrypto)) virtcrypto_dev_stop(vcrypto); + for (i = 0; i < vcrypto->max_data_queues; i++) + tasklet_kill(&vcrypto->data_vq[i].done_task); virtio_reset_device(vdev); virtcrypto_free_unused_reqs(vcrypto); virtcrypto_clear_crypto_engines(vcrypto); diff --git a/drivers/cxl/core/port.c b/drivers/cxl/core/port.c index bd4142431980..1f1483a9e525 100644 --- a/drivers/cxl/core/port.c +++ b/drivers/cxl/core/port.c @@ -1403,7 +1403,7 @@ static int decoder_populate_targets(struct cxl_switch_decoder *cxlsd, return -EINVAL;
write_seqlock(&cxlsd->target_lock); - for (i = 0; i < cxlsd->nr_targets; i++) { + for (i = 0; i < cxlsd->cxld.interleave_ways; i++) { struct cxl_dport *dport = find_dport(port, target_map[i]);
if (!dport) { diff --git a/drivers/cxl/core/region.c b/drivers/cxl/core/region.c index ebc1b028555c..2f7187dbfa2d 100644 --- a/drivers/cxl/core/region.c +++ b/drivers/cxl/core/region.c @@ -331,7 +331,7 @@ static ssize_t interleave_ways_store(struct device *dev, return rc;
/* - * Even for x3, x9, and x12 interleaves the region interleave must be a + * Even for x3, x6, and x12 interleaves the region interleave must be a * power of 2 multiple of the host bridge interleave. */ if (!is_power_of_2(val / cxld->interleave_ways) || diff --git a/drivers/edac/thunderx_edac.c b/drivers/edac/thunderx_edac.c index f13674081cb6..4dca21b39bf7 100644 --- a/drivers/edac/thunderx_edac.c +++ b/drivers/edac/thunderx_edac.c @@ -1133,7 +1133,7 @@ static irqreturn_t thunderx_ocx_com_threaded_isr(int irq, void *irq_id) decode_register(other, OCX_OTHER_SIZE, ocx_com_errors, ctx->reg_com_int);
- strncat(msg, other, OCX_MESSAGE_SIZE); + strlcat(msg, other, OCX_MESSAGE_SIZE);
for (lane = 0; lane < OCX_RX_LANES; lane++) if (ctx->reg_com_int & BIT(lane)) { @@ -1142,12 +1142,12 @@ static irqreturn_t thunderx_ocx_com_threaded_isr(int irq, void *irq_id) lane, ctx->reg_lane_int[lane], lane, ctx->reg_lane_stat11[lane]);
- strncat(msg, other, OCX_MESSAGE_SIZE); + strlcat(msg, other, OCX_MESSAGE_SIZE);
decode_register(other, OCX_OTHER_SIZE, ocx_lane_errors, ctx->reg_lane_int[lane]); - strncat(msg, other, OCX_MESSAGE_SIZE); + strlcat(msg, other, OCX_MESSAGE_SIZE); }
if (ctx->reg_com_int & OCX_COM_INT_CE) @@ -1217,7 +1217,7 @@ static irqreturn_t thunderx_ocx_lnk_threaded_isr(int irq, void *irq_id) decode_register(other, OCX_OTHER_SIZE, ocx_com_link_errors, ctx->reg_com_link_int);
- strncat(msg, other, OCX_MESSAGE_SIZE); + strlcat(msg, other, OCX_MESSAGE_SIZE);
if (ctx->reg_com_link_int & OCX_COM_LINK_INT_UE) edac_device_handle_ue(ocx->edac_dev, 0, 0, msg); @@ -1896,7 +1896,7 @@ static irqreturn_t thunderx_l2c_threaded_isr(int irq, void *irq_id)
decode_register(other, L2C_OTHER_SIZE, l2_errors, ctx->reg_int);
- strncat(msg, other, L2C_MESSAGE_SIZE); + strlcat(msg, other, L2C_MESSAGE_SIZE);
if (ctx->reg_int & mask_ue) edac_device_handle_ue(l2c->edac_dev, 0, 0, msg); diff --git a/drivers/firmware/meson/meson_sm.c b/drivers/firmware/meson/meson_sm.c index d081a6312627..bf19dd66c213 100644 --- a/drivers/firmware/meson/meson_sm.c +++ b/drivers/firmware/meson/meson_sm.c @@ -313,11 +313,14 @@ static int __init meson_sm_probe(struct platform_device *pdev)
platform_set_drvdata(pdev, fw);
- pr_info("secure-monitor enabled\n"); + if (devm_of_platform_populate(dev)) + goto out_in_base;
if (sysfs_create_group(&pdev->dev.kobj, &meson_sm_sysfs_attr_group)) goto out_in_base;
+ pr_info("secure-monitor enabled\n"); + return 0;
out_in_base: diff --git a/drivers/firmware/ti_sci.c b/drivers/firmware/ti_sci.c index 597d1a367d96..6231c98ba291 100644 --- a/drivers/firmware/ti_sci.c +++ b/drivers/firmware/ti_sci.c @@ -161,7 +161,7 @@ static int ti_sci_debugfs_create(struct platform_device *pdev, { struct device *dev = &pdev->dev; struct resource *res; - char debug_name[50] = "ti_sci_debug@"; + char debug_name[50];
/* Debug region is optional */ res = platform_get_resource_byname(pdev, IORESOURCE_MEM, @@ -178,10 +178,10 @@ static int ti_sci_debugfs_create(struct platform_device *pdev, /* Setup NULL termination */ info->debug_buffer[info->debug_region_size] = 0;
- info->d = debugfs_create_file(strncat(debug_name, dev_name(dev), - sizeof(debug_name) - - sizeof("ti_sci_debug@")), - 0444, NULL, info, &ti_sci_debug_fops); + snprintf(debug_name, sizeof(debug_name), "ti_sci_debug@%s", + dev_name(dev)); + info->d = debugfs_create_file(debug_name, 0444, NULL, info, + &ti_sci_debug_fops); if (IS_ERR(info->d)) return PTR_ERR(info->d);
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_debugfs.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_debugfs.c index 8123feb1a116..06ab6066da61 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_debugfs.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_debugfs.c @@ -596,7 +596,7 @@ static ssize_t amdgpu_debugfs_regs_smc_read(struct file *f, char __user *buf, int r;
if (!adev->smc_rreg) - return -EPERM; + return -EOPNOTSUPP;
if (size & 0x3 || *pos & 0x3) return -EINVAL; @@ -655,7 +655,7 @@ static ssize_t amdgpu_debugfs_regs_smc_write(struct file *f, const char __user * int r;
if (!adev->smc_wreg) - return -EPERM; + return -EOPNOTSUPP;
if (size & 0x3 || *pos & 0x3) return -EINVAL; diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c index b9983ca99eb7..a8e1f2cfe12d 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c @@ -2202,6 +2202,8 @@ static int amdgpu_pci_probe(struct pci_dev *pdev,
pci_wake_from_d3(pdev, TRUE);
+ pci_wake_from_d3(pdev, TRUE); + /* * For runpm implemented via BACO, PMFW will handle the * timing for BACO in and out: diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_migrate.c b/drivers/gpu/drm/amd/amdkfd/kfd_migrate.c index 88bf6221d4be..8a7705db0b9a 100644 --- a/drivers/gpu/drm/amd/amdkfd/kfd_migrate.c +++ b/drivers/gpu/drm/amd/amdkfd/kfd_migrate.c @@ -1019,7 +1019,7 @@ int svm_migrate_init(struct amdgpu_device *adev) } else { res = devm_request_free_mem_region(adev->dev, &iomem_resource, size); if (IS_ERR(res)) - return -ENOMEM; + return PTR_ERR(res); pgmap->range.start = res->start; pgmap->range.end = res->end; pgmap->type = MEMORY_DEVICE_PRIVATE; @@ -1035,11 +1035,10 @@ int svm_migrate_init(struct amdgpu_device *adev) r = devm_memremap_pages(adev->dev, pgmap); if (IS_ERR(r)) { pr_err("failed to register HMM device memory\n"); + if (pgmap->type == MEMORY_DEVICE_PRIVATE) + devm_release_mem_region(adev->dev, res->start, resource_size(res)); /* Disable SVM support capability */ pgmap->type = 0; - if (pgmap->type == MEMORY_DEVICE_PRIVATE) - devm_release_mem_region(adev->dev, res->start, - res->end - res->start + 1); return PTR_ERR(r); }
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_topology.c b/drivers/gpu/drm/amd/amdkfd/kfd_topology.c index 713f893d2530..705d9e91b5aa 100644 --- a/drivers/gpu/drm/amd/amdkfd/kfd_topology.c +++ b/drivers/gpu/drm/amd/amdkfd/kfd_topology.c @@ -1403,10 +1403,11 @@ static int kfd_create_indirect_link_prop(struct kfd_topology_device *kdev, int g num_cpu++; }
+ if (list_empty(&kdev->io_link_props)) + return -ENODATA; + gpu_link = list_first_entry(&kdev->io_link_props, - struct kfd_iolink_properties, list); - if (!gpu_link) - return -ENOMEM; + struct kfd_iolink_properties, list);
for (i = 0; i < num_cpu; i++) { /* CPU <--> GPU */ @@ -1484,15 +1485,17 @@ static int kfd_add_peer_prop(struct kfd_topology_device *kdev, peer->gpu->adev)) return ret;
+ if (list_empty(&kdev->io_link_props)) + return -ENODATA; + iolink1 = list_first_entry(&kdev->io_link_props, - struct kfd_iolink_properties, list); - if (!iolink1) - return -ENOMEM; + struct kfd_iolink_properties, list); + + if (list_empty(&peer->io_link_props)) + return -ENODATA;
iolink2 = list_first_entry(&peer->io_link_props, - struct kfd_iolink_properties, list); - if (!iolink2) - return -ENOMEM; + struct kfd_iolink_properties, list);
props = kfd_alloc_struct(props); if (!props) diff --git a/drivers/gpu/drm/amd/pm/legacy-dpm/kv_dpm.c b/drivers/gpu/drm/amd/pm/legacy-dpm/kv_dpm.c index f5e08b60f66e..d17bfa111aa7 100644 --- a/drivers/gpu/drm/amd/pm/legacy-dpm/kv_dpm.c +++ b/drivers/gpu/drm/amd/pm/legacy-dpm/kv_dpm.c @@ -2748,10 +2748,8 @@ static int kv_parse_power_table(struct amdgpu_device *adev) non_clock_info = (struct _ATOM_PPLIB_NONCLOCK_INFO *) &non_clock_info_array->nonClockInfo[non_clock_array_index]; ps = kzalloc(sizeof(struct kv_ps), GFP_KERNEL); - if (ps == NULL) { - kfree(adev->pm.dpm.ps); + if (ps == NULL) return -ENOMEM; - } adev->pm.dpm.ps[i].ps_priv = ps; k = 0; idx = (u8 *)&power_state->v2.clockInfoIndex[0]; diff --git a/drivers/gpu/drm/amd/pm/legacy-dpm/legacy_dpm.c b/drivers/gpu/drm/amd/pm/legacy-dpm/legacy_dpm.c index d3fe149d8476..291223ea7ba7 100644 --- a/drivers/gpu/drm/amd/pm/legacy-dpm/legacy_dpm.c +++ b/drivers/gpu/drm/amd/pm/legacy-dpm/legacy_dpm.c @@ -272,10 +272,8 @@ int amdgpu_parse_extended_power_table(struct amdgpu_device *adev) le16_to_cpu(power_info->pplib4.usVddcDependencyOnSCLKOffset)); ret = amdgpu_parse_clk_voltage_dep_table(&adev->pm.dpm.dyn_state.vddc_dependency_on_sclk, dep_table); - if (ret) { - amdgpu_free_extended_power_table(adev); + if (ret) return ret; - } } if (power_info->pplib4.usVddciDependencyOnMCLKOffset) { dep_table = (ATOM_PPLIB_Clock_Voltage_Dependency_Table *) @@ -283,10 +281,8 @@ int amdgpu_parse_extended_power_table(struct amdgpu_device *adev) le16_to_cpu(power_info->pplib4.usVddciDependencyOnMCLKOffset)); ret = amdgpu_parse_clk_voltage_dep_table(&adev->pm.dpm.dyn_state.vddci_dependency_on_mclk, dep_table); - if (ret) { - amdgpu_free_extended_power_table(adev); + if (ret) return ret; - } } if (power_info->pplib4.usVddcDependencyOnMCLKOffset) { dep_table = (ATOM_PPLIB_Clock_Voltage_Dependency_Table *) @@ -294,10 +290,8 @@ int amdgpu_parse_extended_power_table(struct amdgpu_device *adev) le16_to_cpu(power_info->pplib4.usVddcDependencyOnMCLKOffset)); ret = amdgpu_parse_clk_voltage_dep_table(&adev->pm.dpm.dyn_state.vddc_dependency_on_mclk, dep_table); - if (ret) { - amdgpu_free_extended_power_table(adev); + if (ret) return ret; - } } if (power_info->pplib4.usMvddDependencyOnMCLKOffset) { dep_table = (ATOM_PPLIB_Clock_Voltage_Dependency_Table *) @@ -305,10 +299,8 @@ int amdgpu_parse_extended_power_table(struct amdgpu_device *adev) le16_to_cpu(power_info->pplib4.usMvddDependencyOnMCLKOffset)); ret = amdgpu_parse_clk_voltage_dep_table(&adev->pm.dpm.dyn_state.mvdd_dependency_on_mclk, dep_table); - if (ret) { - amdgpu_free_extended_power_table(adev); + if (ret) return ret; - } } if (power_info->pplib4.usMaxClockVoltageOnDCOffset) { ATOM_PPLIB_Clock_Voltage_Limit_Table *clk_v = @@ -339,10 +331,8 @@ int amdgpu_parse_extended_power_table(struct amdgpu_device *adev) kcalloc(psl->ucNumEntries, sizeof(struct amdgpu_phase_shedding_limits_entry), GFP_KERNEL); - if (!adev->pm.dpm.dyn_state.phase_shedding_limits_table.entries) { - amdgpu_free_extended_power_table(adev); + if (!adev->pm.dpm.dyn_state.phase_shedding_limits_table.entries) return -ENOMEM; - }
entry = &psl->entries[0]; for (i = 0; i < psl->ucNumEntries; i++) { @@ -383,10 +373,8 @@ int amdgpu_parse_extended_power_table(struct amdgpu_device *adev) ATOM_PPLIB_CAC_Leakage_Record *entry; u32 size = cac_table->ucNumEntries * sizeof(struct amdgpu_cac_leakage_table); adev->pm.dpm.dyn_state.cac_leakage_table.entries = kzalloc(size, GFP_KERNEL); - if (!adev->pm.dpm.dyn_state.cac_leakage_table.entries) { - amdgpu_free_extended_power_table(adev); + if (!adev->pm.dpm.dyn_state.cac_leakage_table.entries) return -ENOMEM; - } entry = &cac_table->entries[0]; for (i = 0; i < cac_table->ucNumEntries; i++) { if (adev->pm.dpm.platform_caps & ATOM_PP_PLATFORM_CAP_EVV) { @@ -438,10 +426,8 @@ int amdgpu_parse_extended_power_table(struct amdgpu_device *adev) sizeof(struct amdgpu_vce_clock_voltage_dependency_entry); adev->pm.dpm.dyn_state.vce_clock_voltage_dependency_table.entries = kzalloc(size, GFP_KERNEL); - if (!adev->pm.dpm.dyn_state.vce_clock_voltage_dependency_table.entries) { - amdgpu_free_extended_power_table(adev); + if (!adev->pm.dpm.dyn_state.vce_clock_voltage_dependency_table.entries) return -ENOMEM; - } adev->pm.dpm.dyn_state.vce_clock_voltage_dependency_table.count = limits->numEntries; entry = &limits->entries[0]; @@ -493,10 +479,8 @@ int amdgpu_parse_extended_power_table(struct amdgpu_device *adev) sizeof(struct amdgpu_uvd_clock_voltage_dependency_entry); adev->pm.dpm.dyn_state.uvd_clock_voltage_dependency_table.entries = kzalloc(size, GFP_KERNEL); - if (!adev->pm.dpm.dyn_state.uvd_clock_voltage_dependency_table.entries) { - amdgpu_free_extended_power_table(adev); + if (!adev->pm.dpm.dyn_state.uvd_clock_voltage_dependency_table.entries) return -ENOMEM; - } adev->pm.dpm.dyn_state.uvd_clock_voltage_dependency_table.count = limits->numEntries; entry = &limits->entries[0]; @@ -525,10 +509,8 @@ int amdgpu_parse_extended_power_table(struct amdgpu_device *adev) sizeof(struct amdgpu_clock_voltage_dependency_entry); adev->pm.dpm.dyn_state.samu_clock_voltage_dependency_table.entries = kzalloc(size, GFP_KERNEL); - if (!adev->pm.dpm.dyn_state.samu_clock_voltage_dependency_table.entries) { - amdgpu_free_extended_power_table(adev); + if (!adev->pm.dpm.dyn_state.samu_clock_voltage_dependency_table.entries) return -ENOMEM; - } adev->pm.dpm.dyn_state.samu_clock_voltage_dependency_table.count = limits->numEntries; entry = &limits->entries[0]; @@ -548,10 +530,8 @@ int amdgpu_parse_extended_power_table(struct amdgpu_device *adev) le16_to_cpu(ext_hdr->usPPMTableOffset)); adev->pm.dpm.dyn_state.ppm_table = kzalloc(sizeof(struct amdgpu_ppm_table), GFP_KERNEL); - if (!adev->pm.dpm.dyn_state.ppm_table) { - amdgpu_free_extended_power_table(adev); + if (!adev->pm.dpm.dyn_state.ppm_table) return -ENOMEM; - } adev->pm.dpm.dyn_state.ppm_table->ppm_design = ppm->ucPpmDesign; adev->pm.dpm.dyn_state.ppm_table->cpu_core_number = le16_to_cpu(ppm->usCpuCoreNumber); @@ -583,10 +563,8 @@ int amdgpu_parse_extended_power_table(struct amdgpu_device *adev) sizeof(struct amdgpu_clock_voltage_dependency_entry); adev->pm.dpm.dyn_state.acp_clock_voltage_dependency_table.entries = kzalloc(size, GFP_KERNEL); - if (!adev->pm.dpm.dyn_state.acp_clock_voltage_dependency_table.entries) { - amdgpu_free_extended_power_table(adev); + if (!adev->pm.dpm.dyn_state.acp_clock_voltage_dependency_table.entries) return -ENOMEM; - } adev->pm.dpm.dyn_state.acp_clock_voltage_dependency_table.count = limits->numEntries; entry = &limits->entries[0]; @@ -606,10 +584,8 @@ int amdgpu_parse_extended_power_table(struct amdgpu_device *adev) ATOM_PowerTune_Table *pt; adev->pm.dpm.dyn_state.cac_tdp_table = kzalloc(sizeof(struct amdgpu_cac_tdp_table), GFP_KERNEL); - if (!adev->pm.dpm.dyn_state.cac_tdp_table) { - amdgpu_free_extended_power_table(adev); + if (!adev->pm.dpm.dyn_state.cac_tdp_table) return -ENOMEM; - } if (rev > 0) { ATOM_PPLIB_POWERTUNE_Table_V1 *ppt = (ATOM_PPLIB_POWERTUNE_Table_V1 *) (mode_info->atom_context->bios + data_offset + @@ -645,10 +621,8 @@ int amdgpu_parse_extended_power_table(struct amdgpu_device *adev) ret = amdgpu_parse_clk_voltage_dep_table( &adev->pm.dpm.dyn_state.vddgfx_dependency_on_sclk, dep_table); - if (ret) { - kfree(adev->pm.dpm.dyn_state.vddgfx_dependency_on_sclk.entries); + if (ret) return ret; - } } }
diff --git a/drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c b/drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c index c89cfef7cafa..dc0a6fba7050 100644 --- a/drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c +++ b/drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c @@ -7379,10 +7379,9 @@ static int si_dpm_init(struct amdgpu_device *adev) kcalloc(4, sizeof(struct amdgpu_clock_voltage_dependency_entry), GFP_KERNEL); - if (!adev->pm.dpm.dyn_state.vddc_dependency_on_dispclk.entries) { - amdgpu_free_extended_power_table(adev); + if (!adev->pm.dpm.dyn_state.vddc_dependency_on_dispclk.entries) return -ENOMEM; - } + adev->pm.dpm.dyn_state.vddc_dependency_on_dispclk.count = 4; adev->pm.dpm.dyn_state.vddc_dependency_on_dispclk.entries[0].clk = 0; adev->pm.dpm.dyn_state.vddc_dependency_on_dispclk.entries[0].v = 0; diff --git a/drivers/gpu/drm/amd/pm/powerplay/hwmgr/smu7_hwmgr.c b/drivers/gpu/drm/amd/pm/powerplay/hwmgr/smu7_hwmgr.c index a31a62a1ce0b..5e9410117712 100644 --- a/drivers/gpu/drm/amd/pm/powerplay/hwmgr/smu7_hwmgr.c +++ b/drivers/gpu/drm/amd/pm/powerplay/hwmgr/smu7_hwmgr.c @@ -2987,6 +2987,8 @@ static int smu7_hwmgr_backend_init(struct pp_hwmgr *hwmgr) result = smu7_get_evv_voltages(hwmgr); if (result) { pr_info("Get EVV Voltage Failed. Abort Driver loading!\n"); + kfree(hwmgr->backend); + hwmgr->backend = NULL; return -EINVAL; } } else { @@ -3032,8 +3034,10 @@ static int smu7_hwmgr_backend_init(struct pp_hwmgr *hwmgr) }
result = smu7_update_edc_leakage_table(hwmgr); - if (result) + if (result) { + smu7_hwmgr_backend_fini(hwmgr); return result; + }
return 0; } diff --git a/drivers/gpu/drm/bridge/cadence/cdns-mhdp8546-hdcp.c b/drivers/gpu/drm/bridge/cadence/cdns-mhdp8546-hdcp.c index 946212a95598..5e3b8edcf794 100644 --- a/drivers/gpu/drm/bridge/cadence/cdns-mhdp8546-hdcp.c +++ b/drivers/gpu/drm/bridge/cadence/cdns-mhdp8546-hdcp.c @@ -403,7 +403,8 @@ static int _cdns_mhdp_hdcp_disable(struct cdns_mhdp_device *mhdp)
static int _cdns_mhdp_hdcp_enable(struct cdns_mhdp_device *mhdp, u8 content_type) { - int ret, tries = 3; + int ret = -EINVAL; + int tries = 3; u32 i;
for (i = 0; i < tries; i++) { diff --git a/drivers/gpu/drm/bridge/tc358767.c b/drivers/gpu/drm/bridge/tc358767.c index 7ef78283e3d3..926ab5c3c31a 100644 --- a/drivers/gpu/drm/bridge/tc358767.c +++ b/drivers/gpu/drm/bridge/tc358767.c @@ -2097,7 +2097,7 @@ static int tc_probe(struct i2c_client *client, const struct i2c_device_id *id) } else { if (tc->hpd_pin < 0 || tc->hpd_pin > 1) { dev_err(dev, "failed to parse HPD number\n"); - return ret; + return -EINVAL; } }
diff --git a/drivers/gpu/drm/bridge/ti-tpd12s015.c b/drivers/gpu/drm/bridge/ti-tpd12s015.c index e0e015243a60..b588fea12502 100644 --- a/drivers/gpu/drm/bridge/ti-tpd12s015.c +++ b/drivers/gpu/drm/bridge/ti-tpd12s015.c @@ -179,7 +179,7 @@ static int tpd12s015_probe(struct platform_device *pdev) return 0; }
-static int __exit tpd12s015_remove(struct platform_device *pdev) +static int tpd12s015_remove(struct platform_device *pdev) { struct tpd12s015_device *tpd = platform_get_drvdata(pdev);
@@ -197,7 +197,7 @@ MODULE_DEVICE_TABLE(of, tpd12s015_of_match);
static struct platform_driver tpd12s015_driver = { .probe = tpd12s015_probe, - .remove = __exit_p(tpd12s015_remove), + .remove = tpd12s015_remove, .driver = { .name = "tpd12s015", .of_match_table = tpd12s015_of_match, diff --git a/drivers/gpu/drm/drm_drv.c b/drivers/gpu/drm/drm_drv.c index 203bf8d6c34c..d41a5eaa3e89 100644 --- a/drivers/gpu/drm/drm_drv.c +++ b/drivers/gpu/drm/drm_drv.c @@ -895,8 +895,11 @@ int drm_dev_register(struct drm_device *dev, unsigned long flags) goto err_minors; }
- if (drm_core_check_feature(dev, DRIVER_MODESET)) - drm_modeset_register_all(dev); + if (drm_core_check_feature(dev, DRIVER_MODESET)) { + ret = drm_modeset_register_all(dev); + if (ret) + goto err_unload; + }
DRM_INFO("Initialized %s %d.%d.%d %s for %s on minor %d\n", driver->name, driver->major, driver->minor, @@ -906,6 +909,9 @@ int drm_dev_register(struct drm_device *dev, unsigned long flags)
goto out_unlock;
+err_unload: + if (dev->driver->unload) + dev->driver->unload(dev); err_minors: remove_compat_control_link(dev); drm_minor_unregister(dev, DRM_MINOR_PRIMARY); diff --git a/drivers/gpu/drm/mediatek/mtk_disp_merge.c b/drivers/gpu/drm/mediatek/mtk_disp_merge.c index 6428b6203ffe..211140e87568 100644 --- a/drivers/gpu/drm/mediatek/mtk_disp_merge.c +++ b/drivers/gpu/drm/mediatek/mtk_disp_merge.c @@ -104,7 +104,7 @@ void mtk_merge_stop_cmdq(struct device *dev, struct cmdq_pkt *cmdq_pkt) mtk_ddp_write(cmdq_pkt, 0, &priv->cmdq_reg, priv->regs, DISP_REG_MERGE_CTRL);
- if (priv->async_clk) + if (!cmdq_pkt && priv->async_clk) reset_control_reset(priv->reset_ctl); }
diff --git a/drivers/gpu/drm/mediatek/mtk_dp.c b/drivers/gpu/drm/mediatek/mtk_dp.c index 2c850b6d945b..519e23a2a017 100644 --- a/drivers/gpu/drm/mediatek/mtk_dp.c +++ b/drivers/gpu/drm/mediatek/mtk_dp.c @@ -2669,3 +2669,4 @@ MODULE_AUTHOR("Markus Schneider-Pargmann msp@baylibre.com"); MODULE_AUTHOR("Bo-Chen Chen rex-bc.chen@mediatek.com"); MODULE_DESCRIPTION("MediaTek DisplayPort Driver"); MODULE_LICENSE("GPL"); +MODULE_SOFTDEP("pre: phy_mtk_dp"); diff --git a/drivers/gpu/drm/mediatek/mtk_mdp_rdma.c b/drivers/gpu/drm/mediatek/mtk_mdp_rdma.c index eecfa98ff52e..b288bb6eeecc 100644 --- a/drivers/gpu/drm/mediatek/mtk_mdp_rdma.c +++ b/drivers/gpu/drm/mediatek/mtk_mdp_rdma.c @@ -223,8 +223,7 @@ int mtk_mdp_rdma_clk_enable(struct device *dev) { struct mtk_mdp_rdma *rdma = dev_get_drvdata(dev);
- clk_prepare_enable(rdma->clk); - return 0; + return clk_prepare_enable(rdma->clk); }
void mtk_mdp_rdma_clk_disable(struct device *dev) diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c b/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c index 6c0ffe8e4adb..5a5821e59dc1 100644 --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c @@ -1,6 +1,6 @@ // SPDX-License-Identifier: GPL-2.0-only /* - * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved. + * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved. * Copyright (c) 2014-2021 The Linux Foundation. All rights reserved. * Copyright (C) 2013 Red Hat * Author: Rob Clark robdclark@gmail.com @@ -124,7 +124,7 @@ static void dpu_crtc_setup_lm_misr(struct dpu_crtc_state *crtc_state) continue;
/* Calculate MISR over 1 frame */ - m->hw_lm->ops.setup_misr(m->hw_lm, true, 1); + m->hw_lm->ops.setup_misr(m->hw_lm); } }
diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c index 547f9f2b9fcb..b0eb881f8af1 100644 --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_encoder.c @@ -2,7 +2,7 @@ /* * Copyright (C) 2013 Red Hat * Copyright (c) 2014-2018, 2020-2021 The Linux Foundation. All rights reserved. - * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved. + * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved. * * Author: Rob Clark robdclark@gmail.com */ @@ -257,7 +257,7 @@ void dpu_encoder_setup_misr(const struct drm_encoder *drm_enc) if (!phys->hw_intf || !phys->hw_intf->ops.setup_misr) continue;
- phys->hw_intf->ops.setup_misr(phys->hw_intf, true, 1); + phys->hw_intf->ops.setup_misr(phys->hw_intf); } }
diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.c b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.c index b9dddf576c02..384558d2f960 100644 --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.c +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.c @@ -1,6 +1,6 @@ // SPDX-License-Identifier: GPL-2.0-only /* - * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved. + * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved. * Copyright (c) 2015-2018, The Linux Foundation. All rights reserved. */
@@ -322,9 +322,9 @@ static u32 dpu_hw_intf_get_line_count(struct dpu_hw_intf *intf) return DPU_REG_READ(c, INTF_LINE_COUNT); }
-static void dpu_hw_intf_setup_misr(struct dpu_hw_intf *intf, bool enable, u32 frame_count) +static void dpu_hw_intf_setup_misr(struct dpu_hw_intf *intf) { - dpu_hw_setup_misr(&intf->hw, INTF_MISR_CTRL, enable, frame_count); + dpu_hw_setup_misr(&intf->hw, INTF_MISR_CTRL, 0x1); }
static int dpu_hw_intf_collect_misr(struct dpu_hw_intf *intf, u32 *misr_value) diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.h b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.h index 643dd10bc030..e75339b96a1d 100644 --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.h +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_intf.h @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0-only */ /* - * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved. + * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved. * Copyright (c) 2015-2018, The Linux Foundation. All rights reserved. */
@@ -80,7 +80,7 @@ struct dpu_hw_intf_ops { void (*bind_pingpong_blk)(struct dpu_hw_intf *intf, bool enable, const enum dpu_pingpong pp); - void (*setup_misr)(struct dpu_hw_intf *intf, bool enable, u32 frame_count); + void (*setup_misr)(struct dpu_hw_intf *intf); int (*collect_misr)(struct dpu_hw_intf *intf, u32 *misr_value); };
diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_lm.c b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_lm.c index f5120ea91ede..cc04fb979fb5 100644 --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_lm.c +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_lm.c @@ -1,6 +1,6 @@ // SPDX-License-Identifier: GPL-2.0-only /* - * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved. + * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved. * Copyright (c) 2015-2021, The Linux Foundation. All rights reserved. */
@@ -99,9 +99,9 @@ static void dpu_hw_lm_setup_border_color(struct dpu_hw_mixer *ctx, } }
-static void dpu_hw_lm_setup_misr(struct dpu_hw_mixer *ctx, bool enable, u32 frame_count) +static void dpu_hw_lm_setup_misr(struct dpu_hw_mixer *ctx) { - dpu_hw_setup_misr(&ctx->hw, LM_MISR_CTRL, enable, frame_count); + dpu_hw_setup_misr(&ctx->hw, LM_MISR_CTRL, 0x0); }
static int dpu_hw_lm_collect_misr(struct dpu_hw_mixer *ctx, u32 *misr_value) diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_lm.h b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_lm.h index 652ddfdedec3..0a050eb247b9 100644 --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_lm.h +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_lm.h @@ -1,5 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0-only */ /* + * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved. * Copyright (c) 2015-2021, The Linux Foundation. All rights reserved. */
@@ -57,7 +58,7 @@ struct dpu_hw_lm_ops { /** * setup_misr: Enable/disable MISR */ - void (*setup_misr)(struct dpu_hw_mixer *ctx, bool enable, u32 frame_count); + void (*setup_misr)(struct dpu_hw_mixer *ctx);
/** * collect_misr: Read MISR signature diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.c b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.c index 8062228eada6..1b7439ae686a 100644 --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.c +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.c @@ -1,6 +1,6 @@ // SPDX-License-Identifier: GPL-2.0-only /* - * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved. + * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved. * Copyright (c) 2015-2018, The Linux Foundation. All rights reserved. */ #define pr_fmt(fmt) "[drm:%s:%d] " fmt, __func__, __LINE__ @@ -450,9 +450,11 @@ u64 _dpu_hw_get_qos_lut(const struct dpu_qos_lut_tbl *tbl, return 0; }
+/* + * note: Aside from encoders, input_sel should be set to 0x0 by default + */ void dpu_hw_setup_misr(struct dpu_hw_blk_reg_map *c, - u32 misr_ctrl_offset, - bool enable, u32 frame_count) + u32 misr_ctrl_offset, u8 input_sel) { u32 config = 0;
@@ -461,15 +463,9 @@ void dpu_hw_setup_misr(struct dpu_hw_blk_reg_map *c, /* Clear old MISR value (in case it's read before a new value is calculated)*/ wmb();
- if (enable) { - config = (frame_count & MISR_FRAME_COUNT_MASK) | - MISR_CTRL_ENABLE | MISR_CTRL_FREE_RUN_MASK; - - DPU_REG_WRITE(c, misr_ctrl_offset, config); - } else { - DPU_REG_WRITE(c, misr_ctrl_offset, 0); - } - + config = MISR_FRAME_COUNT | MISR_CTRL_ENABLE | MISR_CTRL_FREE_RUN_MASK | + ((input_sel & 0xF) << 24); + DPU_REG_WRITE(c, misr_ctrl_offset, config); }
int dpu_hw_collect_misr(struct dpu_hw_blk_reg_map *c, diff --git a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.h b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.h index 27f4c39e35ab..4ae2a434372c 100644 --- a/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.h +++ b/drivers/gpu/drm/msm/disp/dpu1/dpu_hw_util.h @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0-only */ /* - * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved. + * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved. * Copyright (c) 2015-2021, The Linux Foundation. All rights reserved. */
@@ -13,7 +13,7 @@ #include "dpu_hw_catalog.h"
#define REG_MASK(n) ((BIT(n)) - 1) -#define MISR_FRAME_COUNT_MASK 0xFF +#define MISR_FRAME_COUNT 0x1 #define MISR_CTRL_ENABLE BIT(8) #define MISR_CTRL_STATUS BIT(9) #define MISR_CTRL_STATUS_CLEAR BIT(10) @@ -350,9 +350,7 @@ u64 _dpu_hw_get_qos_lut(const struct dpu_qos_lut_tbl *tbl, u32 total_fl);
void dpu_hw_setup_misr(struct dpu_hw_blk_reg_map *c, - u32 misr_ctrl_offset, - bool enable, - u32 frame_count); + u32 misr_ctrl_offset, u8 input_sel);
int dpu_hw_collect_misr(struct dpu_hw_blk_reg_map *c, u32 misr_ctrl_offset, diff --git a/drivers/gpu/drm/msm/disp/mdp4/mdp4_crtc.c b/drivers/gpu/drm/msm/disp/mdp4/mdp4_crtc.c index 169f9de4a12a..3100957225a7 100644 --- a/drivers/gpu/drm/msm/disp/mdp4/mdp4_crtc.c +++ b/drivers/gpu/drm/msm/disp/mdp4/mdp4_crtc.c @@ -269,6 +269,7 @@ static void mdp4_crtc_atomic_disable(struct drm_crtc *crtc, { struct mdp4_crtc *mdp4_crtc = to_mdp4_crtc(crtc); struct mdp4_kms *mdp4_kms = get_kms(crtc); + unsigned long flags;
DBG("%s", mdp4_crtc->name);
@@ -281,6 +282,14 @@ static void mdp4_crtc_atomic_disable(struct drm_crtc *crtc, mdp_irq_unregister(&mdp4_kms->base, &mdp4_crtc->err); mdp4_disable(mdp4_kms);
+ if (crtc->state->event && !crtc->state->active) { + WARN_ON(mdp4_crtc->event); + spin_lock_irqsave(&mdp4_kms->dev->event_lock, flags); + drm_crtc_send_vblank_event(crtc, crtc->state->event); + crtc->state->event = NULL; + spin_unlock_irqrestore(&mdp4_kms->dev->event_lock, flags); + } + mdp4_crtc->enabled = false; }
diff --git a/drivers/gpu/drm/msm/dsi/phy/dsi_phy.c b/drivers/gpu/drm/msm/dsi/phy/dsi_phy.c index 7fc0975cb869..62bc3756f2e2 100644 --- a/drivers/gpu/drm/msm/dsi/phy/dsi_phy.c +++ b/drivers/gpu/drm/msm/dsi/phy/dsi_phy.c @@ -512,7 +512,9 @@ static int dsi_phy_enable_resource(struct msm_dsi_phy *phy) struct device *dev = &phy->pdev->dev; int ret;
- pm_runtime_get_sync(dev); + ret = pm_runtime_resume_and_get(dev); + if (ret) + return ret;
ret = clk_prepare_enable(phy->ahb_clk); if (ret) { diff --git a/drivers/gpu/drm/nouveau/nv04_fence.c b/drivers/gpu/drm/nouveau/nv04_fence.c index 5b71a5a5cd85..cdbc75e3d1f6 100644 --- a/drivers/gpu/drm/nouveau/nv04_fence.c +++ b/drivers/gpu/drm/nouveau/nv04_fence.c @@ -39,7 +39,7 @@ struct nv04_fence_priv { static int nv04_fence_emit(struct nouveau_fence *fence) { - struct nvif_push *push = fence->channel->chan.push; + struct nvif_push *push = unrcu_pointer(fence->channel)->chan.push; int ret = PUSH_WAIT(push, 2); if (ret == 0) { PUSH_NVSQ(push, NV_SW, 0x0150, fence->base.seqno); diff --git a/drivers/gpu/drm/omapdrm/omap_drv.c b/drivers/gpu/drm/omapdrm/omap_drv.c index eaf67b9e5f12..5b6d1668f405 100644 --- a/drivers/gpu/drm/omapdrm/omap_drv.c +++ b/drivers/gpu/drm/omapdrm/omap_drv.c @@ -68,7 +68,6 @@ static void omap_atomic_commit_tail(struct drm_atomic_state *old_state) { struct drm_device *dev = old_state->dev; struct omap_drm_private *priv = dev->dev_private; - bool fence_cookie = dma_fence_begin_signalling();
dispc_runtime_get(priv->dispc);
@@ -91,6 +90,8 @@ static void omap_atomic_commit_tail(struct drm_atomic_state *old_state) omap_atomic_wait_for_completion(dev, old_state);
drm_atomic_helper_commit_planes(dev, old_state, 0); + + drm_atomic_helper_commit_hw_done(old_state); } else { /* * OMAP3 DSS seems to have issues with the work-around above, @@ -100,11 +101,9 @@ static void omap_atomic_commit_tail(struct drm_atomic_state *old_state) drm_atomic_helper_commit_planes(dev, old_state, 0);
drm_atomic_helper_commit_modeset_enables(dev, old_state); - }
- drm_atomic_helper_commit_hw_done(old_state); - - dma_fence_end_signalling(fence_cookie); + drm_atomic_helper_commit_hw_done(old_state); + }
/* * Wait for completion of the page flips to ensure that old buffers diff --git a/drivers/gpu/drm/panel/panel-elida-kd35t133.c b/drivers/gpu/drm/panel/panel-elida-kd35t133.c index eee714cf3f49..3a7fc3ca6a6f 100644 --- a/drivers/gpu/drm/panel/panel-elida-kd35t133.c +++ b/drivers/gpu/drm/panel/panel-elida-kd35t133.c @@ -112,6 +112,8 @@ static int kd35t133_unprepare(struct drm_panel *panel) return ret; }
+ gpiod_set_value_cansleep(ctx->reset_gpio, 1); + regulator_disable(ctx->iovcc); regulator_disable(ctx->vdd);
diff --git a/drivers/gpu/drm/panel/panel-sitronix-st7701.c b/drivers/gpu/drm/panel/panel-sitronix-st7701.c index 225b9884f61a..54b28992db5d 100644 --- a/drivers/gpu/drm/panel/panel-sitronix-st7701.c +++ b/drivers/gpu/drm/panel/panel-sitronix-st7701.c @@ -288,7 +288,7 @@ static void st7701_init_sequence(struct st7701 *st7701) FIELD_PREP(DSI_CMD2_BK1_PWRCTRL2_AVDD_MASK, DIV_ROUND_CLOSEST(desc->avdd_mv - 6200, 200)) | FIELD_PREP(DSI_CMD2_BK1_PWRCTRL2_AVCL_MASK, - DIV_ROUND_CLOSEST(-4400 + desc->avcl_mv, 200))); + DIV_ROUND_CLOSEST(-4400 - desc->avcl_mv, 200)));
/* T2D = 0.2us * T2D[3:0] */ ST7701_DSI(st7701, DSI_CMD2_BK1_SPD1, diff --git a/drivers/gpu/drm/panfrost/panfrost_gpu.c b/drivers/gpu/drm/panfrost/panfrost_gpu.c index 6452e4e900dd..55d243048516 100644 --- a/drivers/gpu/drm/panfrost/panfrost_gpu.c +++ b/drivers/gpu/drm/panfrost/panfrost_gpu.c @@ -71,7 +71,12 @@ int panfrost_gpu_soft_reset(struct panfrost_device *pfdev) }
gpu_write(pfdev, GPU_INT_CLEAR, GPU_IRQ_MASK_ALL); - gpu_write(pfdev, GPU_INT_MASK, GPU_IRQ_MASK_ALL); + + /* Only enable the interrupts we care about */ + gpu_write(pfdev, GPU_INT_MASK, + GPU_IRQ_MASK_ERROR | + GPU_IRQ_PERFCNT_SAMPLE_COMPLETED | + GPU_IRQ_CLEAN_CACHES_COMPLETED);
return 0; } @@ -313,28 +318,38 @@ static void panfrost_gpu_init_features(struct panfrost_device *pfdev) pfdev->features.shader_present, pfdev->features.l2_present); }
+static u64 panfrost_get_core_mask(struct panfrost_device *pfdev) +{ + u64 core_mask; + + if (pfdev->features.l2_present == 1) + return U64_MAX; + + /* + * Only support one core group now. + * ~(l2_present - 1) unsets all bits in l2_present except + * the bottom bit. (l2_present - 2) has all the bits in + * the first core group set. AND them together to generate + * a mask of cores in the first core group. + */ + core_mask = ~(pfdev->features.l2_present - 1) & + (pfdev->features.l2_present - 2); + dev_info_once(pfdev->dev, "using only 1st core group (%lu cores from %lu)\n", + hweight64(core_mask), + hweight64(pfdev->features.shader_present)); + + return core_mask; +} + void panfrost_gpu_power_on(struct panfrost_device *pfdev) { int ret; u32 val; - u64 core_mask = U64_MAX; + u64 core_mask;
panfrost_gpu_init_quirks(pfdev); + core_mask = panfrost_get_core_mask(pfdev);
- if (pfdev->features.l2_present != 1) { - /* - * Only support one core group now. - * ~(l2_present - 1) unsets all bits in l2_present except - * the bottom bit. (l2_present - 2) has all the bits in - * the first core group set. AND them together to generate - * a mask of cores in the first core group. - */ - core_mask = ~(pfdev->features.l2_present - 1) & - (pfdev->features.l2_present - 2); - dev_info_once(pfdev->dev, "using only 1st core group (%lu cores from %lu)\n", - hweight64(core_mask), - hweight64(pfdev->features.shader_present)); - } gpu_write(pfdev, L2_PWRON_LO, pfdev->features.l2_present & core_mask); ret = readl_relaxed_poll_timeout(pfdev->iomem + L2_READY_LO, val, val == (pfdev->features.l2_present & core_mask), @@ -359,9 +374,26 @@ void panfrost_gpu_power_on(struct panfrost_device *pfdev)
void panfrost_gpu_power_off(struct panfrost_device *pfdev) { - gpu_write(pfdev, TILER_PWROFF_LO, 0); - gpu_write(pfdev, SHADER_PWROFF_LO, 0); - gpu_write(pfdev, L2_PWROFF_LO, 0); + int ret; + u32 val; + + gpu_write(pfdev, SHADER_PWROFF_LO, pfdev->features.shader_present); + ret = readl_relaxed_poll_timeout(pfdev->iomem + SHADER_PWRTRANS_LO, + val, !val, 1, 1000); + if (ret) + dev_err(pfdev->dev, "shader power transition timeout"); + + gpu_write(pfdev, TILER_PWROFF_LO, pfdev->features.tiler_present); + ret = readl_relaxed_poll_timeout(pfdev->iomem + TILER_PWRTRANS_LO, + val, !val, 1, 1000); + if (ret) + dev_err(pfdev->dev, "tiler power transition timeout"); + + gpu_write(pfdev, L2_PWROFF_LO, pfdev->features.l2_present); + ret = readl_poll_timeout(pfdev->iomem + L2_PWRTRANS_LO, + val, !val, 0, 1000); + if (ret) + dev_err(pfdev->dev, "l2 power transition timeout"); }
int panfrost_gpu_init(struct panfrost_device *pfdev) diff --git a/drivers/gpu/drm/radeon/r100.c b/drivers/gpu/drm/radeon/r100.c index d4f09ecc3d22..f336b5b3b11f 100644 --- a/drivers/gpu/drm/radeon/r100.c +++ b/drivers/gpu/drm/radeon/r100.c @@ -2321,7 +2321,7 @@ int r100_cs_track_check(struct radeon_device *rdev, struct r100_cs_track *track) switch (prim_walk) { case 1: for (i = 0; i < track->num_arrays; i++) { - size = track->arrays[i].esize * track->max_indx * 4; + size = track->arrays[i].esize * track->max_indx * 4UL; if (track->arrays[i].robj == NULL) { DRM_ERROR("(PW %u) Vertex array %u no buffer " "bound\n", prim_walk, i); @@ -2340,7 +2340,7 @@ int r100_cs_track_check(struct radeon_device *rdev, struct r100_cs_track *track) break; case 2: for (i = 0; i < track->num_arrays; i++) { - size = track->arrays[i].esize * (nverts - 1) * 4; + size = track->arrays[i].esize * (nverts - 1) * 4UL; if (track->arrays[i].robj == NULL) { DRM_ERROR("(PW %u) Vertex array %u no buffer " "bound\n", prim_walk, i); diff --git a/drivers/gpu/drm/radeon/r600_cs.c b/drivers/gpu/drm/radeon/r600_cs.c index 638f861af80f..6cf54a747749 100644 --- a/drivers/gpu/drm/radeon/r600_cs.c +++ b/drivers/gpu/drm/radeon/r600_cs.c @@ -1275,7 +1275,7 @@ static int r600_cs_check_reg(struct radeon_cs_parser *p, u32 reg, u32 idx) return -EINVAL; } tmp = (reg - CB_COLOR0_BASE) / 4; - track->cb_color_bo_offset[tmp] = radeon_get_ib_value(p, idx) << 8; + track->cb_color_bo_offset[tmp] = (u64)radeon_get_ib_value(p, idx) << 8; ib[idx] += (u32)((reloc->gpu_offset >> 8) & 0xffffffff); track->cb_color_base_last[tmp] = ib[idx]; track->cb_color_bo[tmp] = reloc->robj; @@ -1302,7 +1302,7 @@ static int r600_cs_check_reg(struct radeon_cs_parser *p, u32 reg, u32 idx) "0x%04X\n", reg); return -EINVAL; } - track->htile_offset = radeon_get_ib_value(p, idx) << 8; + track->htile_offset = (u64)radeon_get_ib_value(p, idx) << 8; ib[idx] += (u32)((reloc->gpu_offset >> 8) & 0xffffffff); track->htile_bo = reloc->robj; track->db_dirty = true; diff --git a/drivers/gpu/drm/radeon/radeon_display.c b/drivers/gpu/drm/radeon/radeon_display.c index ca5598ae8bfc..1814bb8e14f1 100644 --- a/drivers/gpu/drm/radeon/radeon_display.c +++ b/drivers/gpu/drm/radeon/radeon_display.c @@ -687,11 +687,16 @@ static void radeon_crtc_init(struct drm_device *dev, int index) if (radeon_crtc == NULL) return;
+ radeon_crtc->flip_queue = alloc_workqueue("radeon-crtc", WQ_HIGHPRI, 0); + if (!radeon_crtc->flip_queue) { + kfree(radeon_crtc); + return; + } + drm_crtc_init(dev, &radeon_crtc->base, &radeon_crtc_funcs);
drm_mode_crtc_set_gamma_size(&radeon_crtc->base, 256); radeon_crtc->crtc_id = index; - radeon_crtc->flip_queue = alloc_workqueue("radeon-crtc", WQ_HIGHPRI, 0); rdev->mode_info.crtcs[index] = radeon_crtc;
if (rdev->family >= CHIP_BONAIRE) { diff --git a/drivers/gpu/drm/radeon/radeon_vm.c b/drivers/gpu/drm/radeon/radeon_vm.c index 987cabbf1318..c38b4d5d6a14 100644 --- a/drivers/gpu/drm/radeon/radeon_vm.c +++ b/drivers/gpu/drm/radeon/radeon_vm.c @@ -1204,13 +1204,17 @@ int radeon_vm_init(struct radeon_device *rdev, struct radeon_vm *vm) r = radeon_bo_create(rdev, pd_size, align, true, RADEON_GEM_DOMAIN_VRAM, 0, NULL, NULL, &vm->page_directory); - if (r) + if (r) { + kfree(vm->page_tables); + vm->page_tables = NULL; return r; - + } r = radeon_vm_clear_bo(rdev, vm->page_directory); if (r) { radeon_bo_unref(&vm->page_directory); vm->page_directory = NULL; + kfree(vm->page_tables); + vm->page_tables = NULL; return r; }
diff --git a/drivers/gpu/drm/radeon/si.c b/drivers/gpu/drm/radeon/si.c index a91012447b56..85e9cba49cec 100644 --- a/drivers/gpu/drm/radeon/si.c +++ b/drivers/gpu/drm/radeon/si.c @@ -3611,6 +3611,10 @@ static int si_cp_start(struct radeon_device *rdev) for (i = RADEON_RING_TYPE_GFX_INDEX; i <= CAYMAN_RING_TYPE_CP2_INDEX; ++i) { ring = &rdev->ring[i]; r = radeon_ring_lock(rdev, ring, 2); + if (r) { + DRM_ERROR("radeon: cp failed to lock ring (%d).\n", r); + return r; + }
/* clear the compute context state */ radeon_ring_write(ring, PACKET3_COMPUTE(PACKET3_CLEAR_STATE, 0)); diff --git a/drivers/gpu/drm/radeon/sumo_dpm.c b/drivers/gpu/drm/radeon/sumo_dpm.c index f74f381af05f..d49c145db437 100644 --- a/drivers/gpu/drm/radeon/sumo_dpm.c +++ b/drivers/gpu/drm/radeon/sumo_dpm.c @@ -1493,8 +1493,10 @@ static int sumo_parse_power_table(struct radeon_device *rdev) non_clock_array_index = power_state->v2.nonClockInfoIndex; non_clock_info = (struct _ATOM_PPLIB_NONCLOCK_INFO *) &non_clock_info_array->nonClockInfo[non_clock_array_index]; - if (!rdev->pm.power_state[i].clock_info) + if (!rdev->pm.power_state[i].clock_info) { + kfree(rdev->pm.dpm.ps); return -EINVAL; + } ps = kzalloc(sizeof(struct sumo_ps), GFP_KERNEL); if (ps == NULL) { kfree(rdev->pm.dpm.ps); diff --git a/drivers/gpu/drm/radeon/trinity_dpm.c b/drivers/gpu/drm/radeon/trinity_dpm.c index 08ea1c864cb2..ef1cc7bad20a 100644 --- a/drivers/gpu/drm/radeon/trinity_dpm.c +++ b/drivers/gpu/drm/radeon/trinity_dpm.c @@ -1726,8 +1726,10 @@ static int trinity_parse_power_table(struct radeon_device *rdev) non_clock_array_index = power_state->v2.nonClockInfoIndex; non_clock_info = (struct _ATOM_PPLIB_NONCLOCK_INFO *) &non_clock_info_array->nonClockInfo[non_clock_array_index]; - if (!rdev->pm.power_state[i].clock_info) + if (!rdev->pm.power_state[i].clock_info) { + kfree(rdev->pm.dpm.ps); return -EINVAL; + } ps = kzalloc(sizeof(struct sumo_ps), GFP_KERNEL); if (ps == NULL) { kfree(rdev->pm.dpm.ps); diff --git a/drivers/gpu/drm/tidss/tidss_dispc.c b/drivers/gpu/drm/tidss/tidss_dispc.c index 16301bdfead1..95b75236fe5e 100644 --- a/drivers/gpu/drm/tidss/tidss_dispc.c +++ b/drivers/gpu/drm/tidss/tidss_dispc.c @@ -2653,18 +2653,69 @@ static void dispc_init_errata(struct dispc_device *dispc) } }
-static void dispc_softreset(struct dispc_device *dispc) +static int dispc_softreset(struct dispc_device *dispc) { u32 val; int ret = 0;
+ /* K2G display controller does not support soft reset */ + if (dispc->feat->subrev == DISPC_K2G) + return 0; + /* Soft reset */ REG_FLD_MOD(dispc, DSS_SYSCONFIG, 1, 1, 1); /* Wait for reset to complete */ ret = readl_poll_timeout(dispc->base_common + DSS_SYSSTATUS, val, val & 1, 100, 5000); + if (ret) { + dev_err(dispc->dev, "failed to reset dispc\n"); + return ret; + } + + return 0; +} + +static int dispc_init_hw(struct dispc_device *dispc) +{ + struct device *dev = dispc->dev; + int ret; + + ret = pm_runtime_set_active(dev); + if (ret) { + dev_err(dev, "Failed to set DSS PM to active\n"); + return ret; + } + + ret = clk_prepare_enable(dispc->fclk); + if (ret) { + dev_err(dev, "Failed to enable DSS fclk\n"); + goto err_runtime_suspend; + } + + ret = dispc_softreset(dispc); if (ret) - dev_warn(dispc->dev, "failed to reset dispc\n"); + goto err_clk_disable; + + clk_disable_unprepare(dispc->fclk); + ret = pm_runtime_set_suspended(dev); + if (ret) { + dev_err(dev, "Failed to set DSS PM to suspended\n"); + return ret; + } + + return 0; + +err_clk_disable: + clk_disable_unprepare(dispc->fclk); + +err_runtime_suspend: + ret = pm_runtime_set_suspended(dev); + if (ret) { + dev_err(dev, "Failed to set DSS PM to suspended\n"); + return ret; + } + + return ret; }
int dispc_init(struct tidss_device *tidss) @@ -2726,10 +2777,6 @@ int dispc_init(struct tidss_device *tidss) return r; }
- /* K2G display controller does not support soft reset */ - if (feat->subrev != DISPC_K2G) - dispc_softreset(dispc); - for (i = 0; i < dispc->feat->num_vps; i++) { u32 gamma_size = dispc->feat->vp_feat.color.gamma_size; u32 *gamma_table; @@ -2778,6 +2825,10 @@ int dispc_init(struct tidss_device *tidss) of_property_read_u32(dispc->dev->of_node, "max-memory-bandwidth", &dispc->memory_bandwidth_limit);
+ r = dispc_init_hw(dispc); + if (r) + return r; + tidss->dispc = dispc;
return 0; diff --git a/drivers/gpu/drm/tidss/tidss_kms.c b/drivers/gpu/drm/tidss/tidss_kms.c index afb2879980c6..995bac488392 100644 --- a/drivers/gpu/drm/tidss/tidss_kms.c +++ b/drivers/gpu/drm/tidss/tidss_kms.c @@ -4,8 +4,6 @@ * Author: Tomi Valkeinen tomi.valkeinen@ti.com */
-#include <linux/dma-fence.h> - #include <drm/drm_atomic.h> #include <drm/drm_atomic_helper.h> #include <drm/drm_bridge.h> @@ -27,7 +25,6 @@ static void tidss_atomic_commit_tail(struct drm_atomic_state *old_state) { struct drm_device *ddev = old_state->dev; struct tidss_device *tidss = to_tidss(ddev); - bool fence_cookie = dma_fence_begin_signalling();
dev_dbg(ddev->dev, "%s\n", __func__);
@@ -38,7 +35,6 @@ static void tidss_atomic_commit_tail(struct drm_atomic_state *old_state) drm_atomic_helper_commit_modeset_enables(ddev, old_state);
drm_atomic_helper_commit_hw_done(old_state); - dma_fence_end_signalling(fence_cookie); drm_atomic_helper_wait_for_flip_done(ddev, old_state);
drm_atomic_helper_cleanup_planes(ddev, old_state); diff --git a/drivers/gpu/drm/tilcdc/tilcdc_drv.c b/drivers/gpu/drm/tilcdc/tilcdc_drv.c index f72755b8ea14..86d34b77b37d 100644 --- a/drivers/gpu/drm/tilcdc/tilcdc_drv.c +++ b/drivers/gpu/drm/tilcdc/tilcdc_drv.c @@ -138,7 +138,7 @@ static int tilcdc_irq_install(struct drm_device *dev, unsigned int irq) if (ret) return ret;
- priv->irq_enabled = false; + priv->irq_enabled = true;
return 0; } diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_bo.c b/drivers/gpu/drm/vmwgfx/vmwgfx_bo.c index ae01d22b8f84..c46f380d9149 100644 --- a/drivers/gpu/drm/vmwgfx/vmwgfx_bo.c +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_bo.c @@ -595,10 +595,9 @@ static int vmw_user_bo_synccpu_release(struct drm_file *filp, if (!(flags & drm_vmw_synccpu_allow_cs)) { atomic_dec(&vmw_bo->cpu_writers); } - ttm_bo_put(&vmw_bo->base); + vmw_user_bo_unref(&vmw_bo); }
- drm_gem_object_put(&vmw_bo->base.base); return ret; }
@@ -638,8 +637,7 @@ int vmw_user_bo_synccpu_ioctl(struct drm_device *dev, void *data, return ret;
ret = vmw_user_bo_synccpu_grab(vbo, arg->flags); - vmw_bo_unreference(&vbo); - drm_gem_object_put(&vbo->base.base); + vmw_user_bo_unref(&vbo); if (unlikely(ret != 0)) { if (ret == -ERESTARTSYS || ret == -EBUSY) return -EBUSY; @@ -713,7 +711,6 @@ int vmw_user_bo_lookup(struct drm_file *filp, }
*out = gem_to_vmw_bo(gobj); - ttm_bo_get(&(*out)->base);
return 0; } diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_cotable.c b/drivers/gpu/drm/vmwgfx/vmwgfx_cotable.c index 79b30dc9d825..97e56a94eaf8 100644 --- a/drivers/gpu/drm/vmwgfx/vmwgfx_cotable.c +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_cotable.c @@ -407,8 +407,8 @@ static int vmw_cotable_resize(struct vmw_resource *res, size_t new_size) * for the new COTable. Initially pin the buffer object to make sure * we can use tryreserve without failure. */ - ret = vmw_bo_create(dev_priv, new_size, &vmw_mob_placement, - true, true, vmw_bo_bo_free, &buf); + ret = vmw_gem_object_create(dev_priv, new_size, &vmw_mob_placement, + true, true, vmw_bo_bo_free, &buf); if (ret) { DRM_ERROR("Failed initializing new cotable MOB.\n"); return ret; @@ -475,7 +475,7 @@ static int vmw_cotable_resize(struct vmw_resource *res, size_t new_size)
vmw_resource_mob_attach(res); /* Let go of the old mob. */ - vmw_bo_unreference(&old_buf); + vmw_user_bo_unref(&old_buf); res->id = vcotbl->type;
ret = dma_resv_reserve_fences(bo->base.resv, 1); @@ -492,7 +492,7 @@ static int vmw_cotable_resize(struct vmw_resource *res, size_t new_size) out_wait: ttm_bo_unpin(bo); ttm_bo_unreserve(bo); - vmw_bo_unreference(&buf); + vmw_user_bo_unref(&buf);
return ret; } diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_drv.h b/drivers/gpu/drm/vmwgfx/vmwgfx_drv.h index 8459fab9d979..136f1cdcf8cd 100644 --- a/drivers/gpu/drm/vmwgfx/vmwgfx_drv.h +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_drv.h @@ -969,6 +969,11 @@ static inline void vmw_bo_prio_del(struct vmw_buffer_object *vbo, int prio) /** * GEM related functionality - vmwgfx_gem.c */ +extern int vmw_gem_object_create(struct vmw_private *dev_priv, + size_t size, struct ttm_placement *placement, + bool interruptible, bool pin, + void (*bo_free)(struct ttm_buffer_object *bo), + struct vmw_buffer_object **p_bo); extern int vmw_gem_object_create_with_handle(struct vmw_private *dev_priv, struct drm_file *filp, uint32_t size, @@ -1600,6 +1605,21 @@ vmw_bo_reference(struct vmw_buffer_object *buf) return buf; }
+static inline struct vmw_buffer_object *vmw_user_bo_ref(struct vmw_buffer_object *vbo) +{ + drm_gem_object_get(&vbo->base.base); + return vbo; +} + +static inline void vmw_user_bo_unref(struct vmw_buffer_object **buf) +{ + struct vmw_buffer_object *tmp_buf = *buf; + + *buf = NULL; + if (tmp_buf) + drm_gem_object_put(&tmp_buf->base.base); +} + static inline void vmw_fifo_resource_inc(struct vmw_private *dev_priv) { atomic_inc(&dev_priv->num_fifo_resources); diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c b/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c index 7e59469e1cb9..bc7f02e4eceb 100644 --- a/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c @@ -1147,7 +1147,7 @@ static int vmw_translate_mob_ptr(struct vmw_private *dev_priv, SVGAMobId *id, struct vmw_buffer_object **vmw_bo_p) { - struct vmw_buffer_object *vmw_bo; + struct vmw_buffer_object *vmw_bo, *tmp_bo; uint32_t handle = *id; struct vmw_relocation *reloc; int ret; @@ -1159,8 +1159,8 @@ static int vmw_translate_mob_ptr(struct vmw_private *dev_priv, return PTR_ERR(vmw_bo); } ret = vmw_validation_add_bo(sw_context->ctx, vmw_bo, true, false); - ttm_bo_put(&vmw_bo->base); - drm_gem_object_put(&vmw_bo->base.base); + tmp_bo = vmw_bo; + vmw_user_bo_unref(&tmp_bo); if (unlikely(ret != 0)) return ret;
@@ -1202,7 +1202,7 @@ static int vmw_translate_guest_ptr(struct vmw_private *dev_priv, SVGAGuestPtr *ptr, struct vmw_buffer_object **vmw_bo_p) { - struct vmw_buffer_object *vmw_bo; + struct vmw_buffer_object *vmw_bo, *tmp_bo; uint32_t handle = ptr->gmrId; struct vmw_relocation *reloc; int ret; @@ -1214,8 +1214,8 @@ static int vmw_translate_guest_ptr(struct vmw_private *dev_priv, return PTR_ERR(vmw_bo); } ret = vmw_validation_add_bo(sw_context->ctx, vmw_bo, false, false); - ttm_bo_put(&vmw_bo->base); - drm_gem_object_put(&vmw_bo->base.base); + tmp_bo = vmw_bo; + vmw_user_bo_unref(&tmp_bo); if (unlikely(ret != 0)) return ret;
diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_gem.c b/drivers/gpu/drm/vmwgfx/vmwgfx_gem.c index 4d2c28e39f4e..e7a533e39155 100644 --- a/drivers/gpu/drm/vmwgfx/vmwgfx_gem.c +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_gem.c @@ -133,6 +133,22 @@ void vmw_gem_destroy(struct ttm_buffer_object *bo) kfree(vbo); }
+int vmw_gem_object_create(struct vmw_private *vmw, + size_t size, struct ttm_placement *placement, + bool interruptible, bool pin, + void (*bo_free)(struct ttm_buffer_object *bo), + struct vmw_buffer_object **p_bo) +{ + int ret = vmw_bo_create(vmw, size, placement, interruptible, pin, bo_free, p_bo); + + if (ret != 0) + goto out_no_bo; + + (*p_bo)->base.base.funcs = &vmw_gem_object_funcs; +out_no_bo: + return ret; +} + int vmw_gem_object_create_with_handle(struct vmw_private *dev_priv, struct drm_file *filp, uint32_t size, @@ -141,16 +157,14 @@ int vmw_gem_object_create_with_handle(struct vmw_private *dev_priv, { int ret;
- ret = vmw_bo_create(dev_priv, size, - (dev_priv->has_mob) ? + ret = vmw_gem_object_create(dev_priv, size, + (dev_priv->has_mob) ? &vmw_sys_placement : &vmw_vram_sys_placement, - true, false, &vmw_gem_destroy, p_vbo); + true, false, &vmw_gem_destroy, p_vbo); if (ret != 0) goto out_no_bo;
- (*p_vbo)->base.base.funcs = &vmw_gem_object_funcs; - ret = drm_gem_handle_create(filp, &(*p_vbo)->base.base, handle); out_no_bo: return ret; diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_kms.c b/drivers/gpu/drm/vmwgfx/vmwgfx_kms.c index aab6389cb4aa..aa571b75cd07 100644 --- a/drivers/gpu/drm/vmwgfx/vmwgfx_kms.c +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_kms.c @@ -1402,8 +1402,8 @@ static int vmw_create_bo_proxy(struct drm_device *dev, /* Reserve and switch the backing mob. */ mutex_lock(&res->dev_priv->cmdbuf_mutex); (void) vmw_resource_reserve(res, false, true); - vmw_bo_unreference(&res->backup); - res->backup = vmw_bo_reference(bo_mob); + vmw_user_bo_unref(&res->backup); + res->backup = vmw_user_bo_ref(bo_mob); res->backup_offset = 0; vmw_resource_unreserve(res, false, false, false, NULL, 0); mutex_unlock(&res->dev_priv->cmdbuf_mutex); @@ -1599,10 +1599,8 @@ static struct drm_framebuffer *vmw_kms_fb_create(struct drm_device *dev,
err_out: /* vmw_user_lookup_handle takes one ref so does new_fb */ - if (bo) { - vmw_bo_unreference(&bo); - drm_gem_object_put(&bo->base.base); - } + if (bo) + vmw_user_bo_unref(&bo); if (surface) vmw_surface_unreference(&surface);
diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_overlay.c b/drivers/gpu/drm/vmwgfx/vmwgfx_overlay.c index b5b311f2a91a..abc354ead4e8 100644 --- a/drivers/gpu/drm/vmwgfx/vmwgfx_overlay.c +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_overlay.c @@ -457,8 +457,7 @@ int vmw_overlay_ioctl(struct drm_device *dev, void *data,
ret = vmw_overlay_update_stream(dev_priv, buf, arg, true);
- vmw_bo_unreference(&buf); - drm_gem_object_put(&buf->base.base); + vmw_user_bo_unref(&buf);
out_unlock: mutex_unlock(&overlay->mutex); diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_resource.c b/drivers/gpu/drm/vmwgfx/vmwgfx_resource.c index c7d645e5ec7b..30d1c1918bb4 100644 --- a/drivers/gpu/drm/vmwgfx/vmwgfx_resource.c +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_resource.c @@ -140,7 +140,7 @@ static void vmw_resource_release(struct kref *kref) if (res->coherent) vmw_bo_dirty_release(res->backup); ttm_bo_unreserve(bo); - vmw_bo_unreference(&res->backup); + vmw_user_bo_unref(&res->backup); }
if (likely(res->hw_destroy != NULL)) { @@ -330,10 +330,10 @@ static int vmw_resource_buf_alloc(struct vmw_resource *res, return 0; }
- ret = vmw_bo_create(res->dev_priv, res->backup_size, - res->func->backup_placement, - interruptible, false, - &vmw_bo_bo_free, &backup); + ret = vmw_gem_object_create(res->dev_priv, res->backup_size, + res->func->backup_placement, + interruptible, false, + &vmw_bo_bo_free, &backup); if (unlikely(ret != 0)) goto out_no_bo;
@@ -452,11 +452,11 @@ void vmw_resource_unreserve(struct vmw_resource *res, vmw_resource_mob_detach(res); if (res->coherent) vmw_bo_dirty_release(res->backup); - vmw_bo_unreference(&res->backup); + vmw_user_bo_unref(&res->backup); }
if (new_backup) { - res->backup = vmw_bo_reference(new_backup); + res->backup = vmw_user_bo_ref(new_backup);
/* * The validation code should already have added a @@ -544,7 +544,7 @@ vmw_resource_check_buffer(struct ww_acquire_ctx *ticket, ttm_bo_put(val_buf->bo); val_buf->bo = NULL; if (backup_dirty) - vmw_bo_unreference(&res->backup); + vmw_user_bo_unref(&res->backup);
return ret; } @@ -719,7 +719,7 @@ int vmw_resource_validate(struct vmw_resource *res, bool intr, goto out_no_validate; else if (!res->func->needs_backup && res->backup) { WARN_ON_ONCE(vmw_resource_mob_attached(res)); - vmw_bo_unreference(&res->backup); + vmw_user_bo_unref(&res->backup); }
return 0; diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_shader.c b/drivers/gpu/drm/vmwgfx/vmwgfx_shader.c index 51e83dfa1cac..303f7a82f350 100644 --- a/drivers/gpu/drm/vmwgfx/vmwgfx_shader.c +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_shader.c @@ -177,7 +177,7 @@ static int vmw_gb_shader_init(struct vmw_private *dev_priv,
res->backup_size = size; if (byte_code) { - res->backup = vmw_bo_reference(byte_code); + res->backup = vmw_user_bo_ref(byte_code); res->backup_offset = offset; } shader->size = size; @@ -806,8 +806,7 @@ static int vmw_shader_define(struct drm_device *dev, struct drm_file *file_priv, shader_type, num_input_sig, num_output_sig, tfile, shader_handle); out_bad_arg: - vmw_bo_unreference(&buffer); - drm_gem_object_put(&buffer->base.base); + vmw_user_bo_unref(&buffer); return ret; }
diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_surface.c b/drivers/gpu/drm/vmwgfx/vmwgfx_surface.c index 1a1a286bc749..50769528c3f3 100644 --- a/drivers/gpu/drm/vmwgfx/vmwgfx_surface.c +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_surface.c @@ -683,9 +683,6 @@ static void vmw_user_surface_base_release(struct ttm_base_object **p_base) container_of(base, struct vmw_user_surface, prime.base); struct vmw_resource *res = &user_srf->srf.res;
- if (res && res->backup) - drm_gem_object_put(&res->backup->base.base); - *p_base = NULL; vmw_resource_unreference(&res); } @@ -848,23 +845,17 @@ int vmw_surface_define_ioctl(struct drm_device *dev, void *data, * expect a backup buffer to be present. */ if (dev_priv->has_mob && req->shareable) { - uint32_t backup_handle; - - ret = vmw_gem_object_create_with_handle(dev_priv, - file_priv, - res->backup_size, - &backup_handle, - &res->backup); + ret = vmw_gem_object_create(dev_priv, + res->backup_size, + &vmw_sys_placement, + true, + false, + &vmw_gem_destroy, + &res->backup); if (unlikely(ret != 0)) { vmw_resource_unreference(&res); goto out_unlock; } - vmw_bo_reference(res->backup); - /* - * We don't expose the handle to the userspace and surface - * already holds a gem reference - */ - drm_gem_handle_delete(file_priv, backup_handle); }
tmp = vmw_resource_reference(&srf->res); @@ -1505,7 +1496,7 @@ vmw_gb_surface_define_internal(struct drm_device *dev, if (ret == 0) { if (res->backup->base.base.size < res->backup_size) { VMW_DEBUG_USER("Surface backup buffer too small.\n"); - vmw_bo_unreference(&res->backup); + vmw_user_bo_unref(&res->backup); ret = -EINVAL; goto out_unlock; } else { @@ -1519,8 +1510,6 @@ vmw_gb_surface_define_internal(struct drm_device *dev, res->backup_size, &backup_handle, &res->backup); - if (ret == 0) - vmw_bo_reference(res->backup); }
if (unlikely(ret != 0)) { diff --git a/drivers/hid/wacom_wac.c b/drivers/hid/wacom_wac.c index c1270db12178..165ed872fa4e 100644 --- a/drivers/hid/wacom_wac.c +++ b/drivers/hid/wacom_wac.c @@ -2646,8 +2646,8 @@ static void wacom_wac_finger_slot(struct wacom_wac *wacom_wac, { struct hid_data *hid_data = &wacom_wac->hid_data; bool mt = wacom_wac->features.touch_max > 1; - bool prox = hid_data->tipswitch && - report_touch_events(wacom_wac); + bool touch_down = hid_data->tipswitch && hid_data->confidence; + bool prox = touch_down && report_touch_events(wacom_wac);
if (touch_is_muted(wacom_wac)) { if (!wacom_wac->shared->touch_down) @@ -2697,24 +2697,6 @@ static void wacom_wac_finger_slot(struct wacom_wac *wacom_wac, } }
-static bool wacom_wac_slot_is_active(struct input_dev *dev, int key) -{ - struct input_mt *mt = dev->mt; - struct input_mt_slot *s; - - if (!mt) - return false; - - for (s = mt->slots; s != mt->slots + mt->num_slots; s++) { - if (s->key == key && - input_mt_get_value(s, ABS_MT_TRACKING_ID) >= 0) { - return true; - } - } - - return false; -} - static void wacom_wac_finger_event(struct hid_device *hdev, struct hid_field *field, struct hid_usage *usage, __s32 value) { @@ -2765,14 +2747,8 @@ static void wacom_wac_finger_event(struct hid_device *hdev, }
if (usage->usage_index + 1 == field->report_count) { - if (equivalent_usage == wacom_wac->hid_data.last_slot_field) { - bool touch_removed = wacom_wac_slot_is_active(wacom_wac->touch_input, - wacom_wac->hid_data.id) && !wacom_wac->hid_data.tipswitch; - - if (wacom_wac->hid_data.confidence || touch_removed) { - wacom_wac_finger_slot(wacom_wac, wacom_wac->touch_input); - } - } + if (equivalent_usage == wacom_wac->hid_data.last_slot_field) + wacom_wac_finger_slot(wacom_wac, wacom_wac->touch_input); } }
diff --git a/drivers/i2c/busses/i2c-s3c2410.c b/drivers/i2c/busses/i2c-s3c2410.c index 36dab9cd208c..8e3838c42a8c 100644 --- a/drivers/i2c/busses/i2c-s3c2410.c +++ b/drivers/i2c/busses/i2c-s3c2410.c @@ -220,8 +220,17 @@ static bool is_ack(struct s3c24xx_i2c *i2c) int tries;
for (tries = 50; tries; --tries) { - if (readl(i2c->regs + S3C2410_IICCON) - & S3C2410_IICCON_IRQPEND) { + unsigned long tmp = readl(i2c->regs + S3C2410_IICCON); + + if (!(tmp & S3C2410_IICCON_ACKEN)) { + /* + * Wait a bit for the bus to stabilize, + * delay estimated experimentally. + */ + usleep_range(100, 200); + return true; + } + if (tmp & S3C2410_IICCON_IRQPEND) { if (!(readl(i2c->regs + S3C2410_IICSTAT) & S3C2410_IICSTAT_LASTBIT)) return true; @@ -274,16 +283,6 @@ static void s3c24xx_i2c_message_start(struct s3c24xx_i2c *i2c,
stat |= S3C2410_IICSTAT_START; writel(stat, i2c->regs + S3C2410_IICSTAT); - - if (i2c->quirks & QUIRK_POLL) { - while ((i2c->msg_num != 0) && is_ack(i2c)) { - i2c_s3c_irq_nextbyte(i2c, stat); - stat = readl(i2c->regs + S3C2410_IICSTAT); - - if (stat & S3C2410_IICSTAT_ARBITR) - dev_err(i2c->dev, "deal with arbitration loss\n"); - } - } }
static inline void s3c24xx_i2c_stop(struct s3c24xx_i2c *i2c, int ret) @@ -690,7 +689,7 @@ static void s3c24xx_i2c_wait_idle(struct s3c24xx_i2c *i2c) static int s3c24xx_i2c_doxfer(struct s3c24xx_i2c *i2c, struct i2c_msg *msgs, int num) { - unsigned long timeout; + unsigned long timeout = 0; int ret;
ret = s3c24xx_i2c_set_master(i2c); @@ -710,16 +709,19 @@ static int s3c24xx_i2c_doxfer(struct s3c24xx_i2c *i2c, s3c24xx_i2c_message_start(i2c, msgs);
if (i2c->quirks & QUIRK_POLL) { - ret = i2c->msg_idx; + while ((i2c->msg_num != 0) && is_ack(i2c)) { + unsigned long stat = readl(i2c->regs + S3C2410_IICSTAT);
- if (ret != num) - dev_dbg(i2c->dev, "incomplete xfer (%d)\n", ret); + i2c_s3c_irq_nextbyte(i2c, stat);
- goto out; + stat = readl(i2c->regs + S3C2410_IICSTAT); + if (stat & S3C2410_IICSTAT_ARBITR) + dev_err(i2c->dev, "deal with arbitration loss\n"); + } + } else { + timeout = wait_event_timeout(i2c->wait, i2c->msg_num == 0, HZ * 5); }
- timeout = wait_event_timeout(i2c->wait, i2c->msg_num == 0, HZ * 5); - ret = i2c->msg_idx;
/* diff --git a/drivers/iio/adc/ad7091r-base.c b/drivers/iio/adc/ad7091r-base.c index 8e252cde735b..0e5d3d2e9c98 100644 --- a/drivers/iio/adc/ad7091r-base.c +++ b/drivers/iio/adc/ad7091r-base.c @@ -174,8 +174,8 @@ static const struct iio_info ad7091r_info = {
static irqreturn_t ad7091r_event_handler(int irq, void *private) { - struct ad7091r_state *st = (struct ad7091r_state *) private; - struct iio_dev *iio_dev = dev_get_drvdata(st->dev); + struct iio_dev *iio_dev = private; + struct ad7091r_state *st = iio_priv(iio_dev); unsigned int i, read_val; int ret; s64 timestamp = iio_get_time_ns(iio_dev); @@ -234,7 +234,7 @@ int ad7091r_probe(struct device *dev, const char *name, if (irq) { ret = devm_request_threaded_irq(dev, irq, NULL, ad7091r_event_handler, - IRQF_TRIGGER_FALLING | IRQF_ONESHOT, name, st); + IRQF_TRIGGER_FALLING | IRQF_ONESHOT, name, iio_dev); if (ret) return ret; } diff --git a/drivers/iio/adc/ad9467.c b/drivers/iio/adc/ad9467.c index 7534572f7475..811525857d29 100644 --- a/drivers/iio/adc/ad9467.c +++ b/drivers/iio/adc/ad9467.c @@ -119,9 +119,9 @@ struct ad9467_state { struct spi_device *spi; struct clk *clk; unsigned int output_mode; + unsigned int (*scales)[2];
struct gpio_desc *pwrdown_gpio; - struct gpio_desc *reset_gpio; };
static int ad9467_spi_read(struct spi_device *spi, unsigned int reg) @@ -163,9 +163,10 @@ static int ad9467_reg_access(struct adi_axi_adc_conv *conv, unsigned int reg,
if (readval == NULL) { ret = ad9467_spi_write(spi, reg, writeval); - ad9467_spi_write(spi, AN877_ADC_REG_TRANSFER, - AN877_ADC_TRANSFER_SYNC); - return ret; + if (ret) + return ret; + return ad9467_spi_write(spi, AN877_ADC_REG_TRANSFER, + AN877_ADC_TRANSFER_SYNC); }
ret = ad9467_spi_read(spi, reg); @@ -212,6 +213,7 @@ static void __ad9467_get_scale(struct adi_axi_adc_conv *conv, int index, .channel = _chan, \ .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE) | \ BIT(IIO_CHAN_INFO_SAMP_FREQ), \ + .info_mask_shared_by_type_available = BIT(IIO_CHAN_INFO_SCALE), \ .scan_index = _si, \ .scan_type = { \ .sign = _sign, \ @@ -273,10 +275,13 @@ static int ad9467_get_scale(struct adi_axi_adc_conv *conv, int *val, int *val2) const struct ad9467_chip_info *info1 = to_ad9467_chip_info(info); struct ad9467_state *st = adi_axi_adc_conv_priv(conv); unsigned int i, vref_val; + int ret;
- vref_val = ad9467_spi_read(st->spi, AN877_ADC_REG_VREF); + ret = ad9467_spi_read(st->spi, AN877_ADC_REG_VREF); + if (ret < 0) + return ret;
- vref_val &= info1->vref_mask; + vref_val = ret & info1->vref_mask;
for (i = 0; i < info->num_scales; i++) { if (vref_val == info->scale_table[i][1]) @@ -297,6 +302,7 @@ static int ad9467_set_scale(struct adi_axi_adc_conv *conv, int val, int val2) struct ad9467_state *st = adi_axi_adc_conv_priv(conv); unsigned int scale_val[2]; unsigned int i; + int ret;
if (val != 0) return -EINVAL; @@ -306,11 +312,13 @@ static int ad9467_set_scale(struct adi_axi_adc_conv *conv, int val, int val2) if (scale_val[0] != val || scale_val[1] != val2) continue;
- ad9467_spi_write(st->spi, AN877_ADC_REG_VREF, - info->scale_table[i][1]); - ad9467_spi_write(st->spi, AN877_ADC_REG_TRANSFER, - AN877_ADC_TRANSFER_SYNC); - return 0; + ret = ad9467_spi_write(st->spi, AN877_ADC_REG_VREF, + info->scale_table[i][1]); + if (ret < 0) + return ret; + + return ad9467_spi_write(st->spi, AN877_ADC_REG_TRANSFER, + AN877_ADC_TRANSFER_SYNC); }
return -EINVAL; @@ -359,6 +367,26 @@ static int ad9467_write_raw(struct adi_axi_adc_conv *conv, } }
+static int ad9467_read_avail(struct adi_axi_adc_conv *conv, + struct iio_chan_spec const *chan, + const int **vals, int *type, int *length, + long mask) +{ + const struct adi_axi_adc_chip_info *info = conv->chip_info; + struct ad9467_state *st = adi_axi_adc_conv_priv(conv); + + switch (mask) { + case IIO_CHAN_INFO_SCALE: + *vals = (const int *)st->scales; + *type = IIO_VAL_INT_PLUS_MICRO; + /* Values are stored in a 2D matrix */ + *length = info->num_scales * 2; + return IIO_AVAIL_LIST; + default: + return -EINVAL; + } +} + static int ad9467_outputmode_set(struct spi_device *spi, unsigned int mode) { int ret; @@ -371,6 +399,26 @@ static int ad9467_outputmode_set(struct spi_device *spi, unsigned int mode) AN877_ADC_TRANSFER_SYNC); }
+static int ad9467_scale_fill(struct adi_axi_adc_conv *conv) +{ + const struct adi_axi_adc_chip_info *info = conv->chip_info; + struct ad9467_state *st = adi_axi_adc_conv_priv(conv); + unsigned int i, val1, val2; + + st->scales = devm_kmalloc_array(&st->spi->dev, info->num_scales, + sizeof(*st->scales), GFP_KERNEL); + if (!st->scales) + return -ENOMEM; + + for (i = 0; i < info->num_scales; i++) { + __ad9467_get_scale(conv, i, &val1, &val2); + st->scales[i][0] = val1; + st->scales[i][1] = val2; + } + + return 0; +} + static int ad9467_preenable_setup(struct adi_axi_adc_conv *conv) { struct ad9467_state *st = adi_axi_adc_conv_priv(conv); @@ -378,6 +426,21 @@ static int ad9467_preenable_setup(struct adi_axi_adc_conv *conv) return ad9467_outputmode_set(st->spi, st->output_mode); }
+static int ad9467_reset(struct device *dev) +{ + struct gpio_desc *gpio; + + gpio = devm_gpiod_get_optional(dev, "reset", GPIOD_OUT_HIGH); + if (IS_ERR_OR_NULL(gpio)) + return PTR_ERR_OR_ZERO(gpio); + + fsleep(1); + gpiod_set_value_cansleep(gpio, 0); + fsleep(10 * USEC_PER_MSEC); + + return 0; +} + static int ad9467_probe(struct spi_device *spi) { const struct ad9467_chip_info *info; @@ -406,21 +469,16 @@ static int ad9467_probe(struct spi_device *spi) if (IS_ERR(st->pwrdown_gpio)) return PTR_ERR(st->pwrdown_gpio);
- st->reset_gpio = devm_gpiod_get_optional(&spi->dev, "reset", - GPIOD_OUT_LOW); - if (IS_ERR(st->reset_gpio)) - return PTR_ERR(st->reset_gpio); - - if (st->reset_gpio) { - udelay(1); - ret = gpiod_direction_output(st->reset_gpio, 1); - if (ret) - return ret; - mdelay(10); - } + ret = ad9467_reset(&spi->dev); + if (ret) + return ret;
conv->chip_info = &info->axi_adc_info;
+ ret = ad9467_scale_fill(conv); + if (ret) + return ret; + id = ad9467_spi_read(spi, AN877_ADC_REG_CHIP_ID); if (id != conv->chip_info->id) { dev_err(&spi->dev, "Mismatch CHIP_ID, got 0x%X, expected 0x%X\n", @@ -431,6 +489,7 @@ static int ad9467_probe(struct spi_device *spi) conv->reg_access = ad9467_reg_access; conv->write_raw = ad9467_write_raw; conv->read_raw = ad9467_read_raw; + conv->read_avail = ad9467_read_avail; conv->preenable_setup = ad9467_preenable_setup;
st->output_mode = info->default_output_mode | diff --git a/drivers/iio/adc/adi-axi-adc.c b/drivers/iio/adc/adi-axi-adc.c index e8a8ea4140f1..ad386ac7f03c 100644 --- a/drivers/iio/adc/adi-axi-adc.c +++ b/drivers/iio/adc/adi-axi-adc.c @@ -143,6 +143,20 @@ static int adi_axi_adc_write_raw(struct iio_dev *indio_dev, return conv->write_raw(conv, chan, val, val2, mask); }
+static int adi_axi_adc_read_avail(struct iio_dev *indio_dev, + struct iio_chan_spec const *chan, + const int **vals, int *type, int *length, + long mask) +{ + struct adi_axi_adc_state *st = iio_priv(indio_dev); + struct adi_axi_adc_conv *conv = &st->client->conv; + + if (!conv->read_avail) + return -EOPNOTSUPP; + + return conv->read_avail(conv, chan, vals, type, length, mask); +} + static int adi_axi_adc_update_scan_mode(struct iio_dev *indio_dev, const unsigned long *scan_mask) { @@ -227,69 +241,11 @@ struct adi_axi_adc_conv *devm_adi_axi_adc_conv_register(struct device *dev, } EXPORT_SYMBOL_NS_GPL(devm_adi_axi_adc_conv_register, IIO_ADI_AXI);
-static ssize_t in_voltage_scale_available_show(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - struct iio_dev *indio_dev = dev_to_iio_dev(dev); - struct adi_axi_adc_state *st = iio_priv(indio_dev); - struct adi_axi_adc_conv *conv = &st->client->conv; - size_t len = 0; - int i; - - for (i = 0; i < conv->chip_info->num_scales; i++) { - const unsigned int *s = conv->chip_info->scale_table[i]; - - len += scnprintf(buf + len, PAGE_SIZE - len, - "%u.%06u ", s[0], s[1]); - } - buf[len - 1] = '\n'; - - return len; -} - -static IIO_DEVICE_ATTR_RO(in_voltage_scale_available, 0); - -enum { - ADI_AXI_ATTR_SCALE_AVAIL, -}; - -#define ADI_AXI_ATTR(_en_, _file_) \ - [ADI_AXI_ATTR_##_en_] = &iio_dev_attr_##_file_.dev_attr.attr - -static struct attribute *adi_axi_adc_attributes[] = { - ADI_AXI_ATTR(SCALE_AVAIL, in_voltage_scale_available), - NULL -}; - -static umode_t axi_adc_attr_is_visible(struct kobject *kobj, - struct attribute *attr, int n) -{ - struct device *dev = kobj_to_dev(kobj); - struct iio_dev *indio_dev = dev_to_iio_dev(dev); - struct adi_axi_adc_state *st = iio_priv(indio_dev); - struct adi_axi_adc_conv *conv = &st->client->conv; - - switch (n) { - case ADI_AXI_ATTR_SCALE_AVAIL: - if (!conv->chip_info->num_scales) - return 0; - return attr->mode; - default: - return attr->mode; - } -} - -static const struct attribute_group adi_axi_adc_attribute_group = { - .attrs = adi_axi_adc_attributes, - .is_visible = axi_adc_attr_is_visible, -}; - static const struct iio_info adi_axi_adc_info = { .read_raw = &adi_axi_adc_read_raw, .write_raw = &adi_axi_adc_write_raw, - .attrs = &adi_axi_adc_attribute_group, .update_scan_mode = &adi_axi_adc_update_scan_mode, + .read_avail = &adi_axi_adc_read_avail, };
static const struct adi_axi_adc_core_info adi_axi_adc_10_0_a_info = { diff --git a/drivers/infiniband/hw/hns/hns_roce_hw_v2.c b/drivers/infiniband/hw/hns/hns_roce_hw_v2.c index c2ee80546d12..58fbb1d3b7f4 100644 --- a/drivers/infiniband/hw/hns/hns_roce_hw_v2.c +++ b/drivers/infiniband/hw/hns/hns_roce_hw_v2.c @@ -2819,6 +2819,10 @@ static int free_mr_alloc_res(struct hns_roce_dev *hr_dev) return 0;
create_failed_qp: + for (i--; i >= 0; i--) { + hns_roce_v2_destroy_qp(&free_mr->rsv_qp[i]->ibqp, NULL); + kfree(free_mr->rsv_qp[i]); + } hns_roce_destroy_cq(cq, NULL); kfree(cq);
@@ -5791,7 +5795,7 @@ static int hns_roce_v2_modify_srq(struct ib_srq *ibsrq,
/* Resizing SRQs is not supported yet */ if (srq_attr_mask & IB_SRQ_MAX_WR) - return -EINVAL; + return -EOPNOTSUPP;
if (srq_attr_mask & IB_SRQ_LIMIT) { if (srq_attr->srq_limit > srq->wqe_cnt) diff --git a/drivers/infiniband/hw/hns/hns_roce_pd.c b/drivers/infiniband/hw/hns/hns_roce_pd.c index 783e71852c50..bd1fe89ca205 100644 --- a/drivers/infiniband/hw/hns/hns_roce_pd.c +++ b/drivers/infiniband/hw/hns/hns_roce_pd.c @@ -150,7 +150,7 @@ int hns_roce_alloc_xrcd(struct ib_xrcd *ib_xrcd, struct ib_udata *udata) int ret;
if (!(hr_dev->caps.flags & HNS_ROCE_CAP_FLAG_XRC)) - return -EINVAL; + return -EOPNOTSUPP;
ret = hns_roce_xrcd_alloc(hr_dev, &xrcd->xrcdn); if (ret) diff --git a/drivers/infiniband/hw/mthca/mthca_cmd.c b/drivers/infiniband/hw/mthca/mthca_cmd.c index f330ce895d88..8fe0cef7e2be 100644 --- a/drivers/infiniband/hw/mthca/mthca_cmd.c +++ b/drivers/infiniband/hw/mthca/mthca_cmd.c @@ -635,7 +635,7 @@ void mthca_free_mailbox(struct mthca_dev *dev, struct mthca_mailbox *mailbox)
int mthca_SYS_EN(struct mthca_dev *dev) { - u64 out; + u64 out = 0; int ret;
ret = mthca_cmd_imm(dev, 0, &out, 0, 0, CMD_SYS_EN, CMD_TIME_CLASS_D); @@ -1955,7 +1955,7 @@ int mthca_WRITE_MGM(struct mthca_dev *dev, int index, int mthca_MGID_HASH(struct mthca_dev *dev, struct mthca_mailbox *mailbox, u16 *hash) { - u64 imm; + u64 imm = 0; int err;
err = mthca_cmd_imm(dev, mailbox->dma, &imm, 0, 0, CMD_MGID_HASH, diff --git a/drivers/infiniband/hw/mthca/mthca_main.c b/drivers/infiniband/hw/mthca/mthca_main.c index b54bc8865dae..1ab268b77096 100644 --- a/drivers/infiniband/hw/mthca/mthca_main.c +++ b/drivers/infiniband/hw/mthca/mthca_main.c @@ -382,7 +382,7 @@ static int mthca_init_icm(struct mthca_dev *mdev, struct mthca_init_hca_param *init_hca, u64 icm_size) { - u64 aux_pages; + u64 aux_pages = 0; int err;
err = mthca_SET_ICM_SIZE(mdev, icm_size, &aux_pages); diff --git a/drivers/infiniband/ulp/iser/iscsi_iser.h b/drivers/infiniband/ulp/iser/iscsi_iser.h index dee8c97ff056..d967d5532459 100644 --- a/drivers/infiniband/ulp/iser/iscsi_iser.h +++ b/drivers/infiniband/ulp/iser/iscsi_iser.h @@ -317,12 +317,10 @@ struct iser_device { * * @mr: memory region * @sig_mr: signature memory region - * @mr_valid: is mr valid indicator */ struct iser_reg_resources { struct ib_mr *mr; struct ib_mr *sig_mr; - u8 mr_valid:1; };
/** diff --git a/drivers/infiniband/ulp/iser/iser_initiator.c b/drivers/infiniband/ulp/iser/iser_initiator.c index 7b83f48f60c5..8ec470c519e8 100644 --- a/drivers/infiniband/ulp/iser/iser_initiator.c +++ b/drivers/infiniband/ulp/iser/iser_initiator.c @@ -580,7 +580,10 @@ static inline int iser_inv_desc(struct iser_fr_desc *desc, u32 rkey) return -EINVAL; }
- desc->rsc.mr_valid = 0; + if (desc->sig_protected) + desc->rsc.sig_mr->need_inval = false; + else + desc->rsc.mr->need_inval = false;
return 0; } diff --git a/drivers/infiniband/ulp/iser/iser_memory.c b/drivers/infiniband/ulp/iser/iser_memory.c index 29ae2c6a250a..6efcb79c8efe 100644 --- a/drivers/infiniband/ulp/iser/iser_memory.c +++ b/drivers/infiniband/ulp/iser/iser_memory.c @@ -264,7 +264,7 @@ static int iser_reg_sig_mr(struct iscsi_iser_task *iser_task,
iser_set_prot_checks(iser_task->sc, &sig_attrs->check_mask);
- if (rsc->mr_valid) + if (rsc->sig_mr->need_inval) iser_inv_rkey(&tx_desc->inv_wr, mr, cqe, &wr->wr);
ib_update_fast_reg_key(mr, ib_inc_rkey(mr->rkey)); @@ -288,7 +288,7 @@ static int iser_reg_sig_mr(struct iscsi_iser_task *iser_task, wr->access = IB_ACCESS_LOCAL_WRITE | IB_ACCESS_REMOTE_READ | IB_ACCESS_REMOTE_WRITE; - rsc->mr_valid = 1; + rsc->sig_mr->need_inval = true;
sig_reg->sge.lkey = mr->lkey; sig_reg->rkey = mr->rkey; @@ -313,7 +313,7 @@ static int iser_fast_reg_mr(struct iscsi_iser_task *iser_task, struct ib_reg_wr *wr = &tx_desc->reg_wr; int n;
- if (rsc->mr_valid) + if (rsc->mr->need_inval) iser_inv_rkey(&tx_desc->inv_wr, mr, cqe, &wr->wr);
ib_update_fast_reg_key(mr, ib_inc_rkey(mr->rkey)); @@ -336,7 +336,7 @@ static int iser_fast_reg_mr(struct iscsi_iser_task *iser_task, IB_ACCESS_REMOTE_WRITE | IB_ACCESS_REMOTE_READ;
- rsc->mr_valid = 1; + rsc->mr->need_inval = true;
reg->sge.lkey = mr->lkey; reg->rkey = mr->rkey; diff --git a/drivers/infiniband/ulp/iser/iser_verbs.c b/drivers/infiniband/ulp/iser/iser_verbs.c index a00ca117303a..057e69164e6d 100644 --- a/drivers/infiniband/ulp/iser/iser_verbs.c +++ b/drivers/infiniband/ulp/iser/iser_verbs.c @@ -135,7 +135,6 @@ iser_create_fastreg_desc(struct iser_device *device, goto err_alloc_mr_integrity; } } - desc->rsc.mr_valid = 0;
return desc;
diff --git a/drivers/input/keyboard/atkbd.c b/drivers/input/keyboard/atkbd.c index e1e4f1133296..c4d8caadec59 100644 --- a/drivers/input/keyboard/atkbd.c +++ b/drivers/input/keyboard/atkbd.c @@ -772,9 +772,9 @@ static bool atkbd_is_portable_device(void) * not work. So in this case simply assume a keyboard is connected to avoid * confusing some laptop keyboards. * - * Skipping ATKBD_CMD_GETID ends up using a fake keyboard id. Using a fake id is - * ok in translated mode, only atkbd_select_set() checks atkbd->id and in - * translated mode that is a no-op. + * Skipping ATKBD_CMD_GETID ends up using a fake keyboard id. Using the standard + * 0xab83 id is ok in translated mode, only atkbd_select_set() checks atkbd->id + * and in translated mode that is a no-op. */ static bool atkbd_skip_getid(struct atkbd *atkbd) { @@ -792,6 +792,7 @@ static int atkbd_probe(struct atkbd *atkbd) { struct ps2dev *ps2dev = &atkbd->ps2dev; unsigned char param[2]; + bool skip_getid;
/* * Some systems, where the bit-twiddling when testing the io-lines of the @@ -813,7 +814,8 @@ static int atkbd_probe(struct atkbd *atkbd) */
param[0] = param[1] = 0xa5; /* initialize with invalid values */ - if (atkbd_skip_getid(atkbd) || ps2_command(ps2dev, param, ATKBD_CMD_GETID)) { + skip_getid = atkbd_skip_getid(atkbd); + if (skip_getid || ps2_command(ps2dev, param, ATKBD_CMD_GETID)) {
/* * If the get ID command was skipped or failed, we check if we can at least set @@ -823,7 +825,7 @@ static int atkbd_probe(struct atkbd *atkbd) param[0] = 0; if (ps2_command(ps2dev, param, ATKBD_CMD_SETLEDS)) return -1; - atkbd->id = 0xabba; + atkbd->id = skip_getid ? 0xab83 : 0xabba; return 0; }
diff --git a/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c b/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c index b2708de25ea3..d80065c8105a 100644 --- a/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c +++ b/drivers/iommu/arm/arm-smmu/arm-smmu-qcom.c @@ -243,6 +243,7 @@ static int qcom_adreno_smmu_init_context(struct arm_smmu_domain *smmu_domain,
static const struct of_device_id qcom_smmu_client_of_match[] __maybe_unused = { { .compatible = "qcom,adreno" }, + { .compatible = "qcom,adreno-gmu" }, { .compatible = "qcom,mdp4" }, { .compatible = "qcom,mdss" }, { .compatible = "qcom,sc7180-mdss" }, diff --git a/drivers/iommu/dma-iommu.c b/drivers/iommu/dma-iommu.c index 9297b741f5e8..aa6d62cc567a 100644 --- a/drivers/iommu/dma-iommu.c +++ b/drivers/iommu/dma-iommu.c @@ -28,6 +28,7 @@ #include <linux/spinlock.h> #include <linux/swiotlb.h> #include <linux/vmalloc.h> +#include <trace/events/swiotlb.h>
#include "dma-iommu.h"
@@ -999,6 +1000,8 @@ static dma_addr_t iommu_dma_map_page(struct device *dev, struct page *page, return DMA_MAPPING_ERROR; }
+ trace_swiotlb_bounced(dev, phys, size); + aligned_size = iova_align(iovad, size); phys = swiotlb_tbl_map_single(dev, phys, size, aligned_size, iova_mask(iovad), dir, attrs); diff --git a/drivers/leds/Kconfig b/drivers/leds/Kconfig index 2378cfb7443e..509d03eb3e8d 100644 --- a/drivers/leds/Kconfig +++ b/drivers/leds/Kconfig @@ -97,6 +97,7 @@ config LEDS_ARIEL config LEDS_AW2013 tristate "LED support for Awinic AW2013" depends on LEDS_CLASS && I2C && OF + select REGMAP_I2C help This option enables support for the AW2013 3-channel LED driver. diff --git a/drivers/md/md.c b/drivers/md/md.c index 0c2801d77090..6120f26a7969 100644 --- a/drivers/md/md.c +++ b/drivers/md/md.c @@ -528,6 +528,9 @@ static void md_end_flush(struct bio *bio) rdev_dec_pending(rdev, mddev);
if (atomic_dec_and_test(&mddev->flush_pending)) { + /* The pair is percpu_ref_get() from md_flush_request() */ + percpu_ref_put(&mddev->active_io); + /* The pre-request flush has finished */ queue_work(md_wq, &mddev->flush_work); } @@ -547,12 +550,8 @@ static void submit_flushes(struct work_struct *ws) rdev_for_each_rcu(rdev, mddev) if (rdev->raid_disk >= 0 && !test_bit(Faulty, &rdev->flags)) { - /* Take two references, one is dropped - * when request finishes, one after - * we reclaim rcu_read_lock - */ struct bio *bi; - atomic_inc(&rdev->nr_pending); + atomic_inc(&rdev->nr_pending); rcu_read_unlock(); bi = bio_alloc_bioset(rdev->bdev, 0, @@ -563,7 +562,6 @@ static void submit_flushes(struct work_struct *ws) atomic_inc(&mddev->flush_pending); submit_bio(bi); rcu_read_lock(); - rdev_dec_pending(rdev, mddev); } rcu_read_unlock(); if (atomic_dec_and_test(&mddev->flush_pending)) @@ -616,6 +614,18 @@ bool md_flush_request(struct mddev *mddev, struct bio *bio) /* new request after previous flush is completed */ if (ktime_after(req_start, mddev->prev_flush_start)) { WARN_ON(mddev->flush_bio); + /* + * Grab a reference to make sure mddev_suspend() will wait for + * this flush to be done. + * + * md_flush_reqeust() is called under md_handle_request() and + * 'active_io' is already grabbed, hence percpu_ref_is_zero() + * won't pass, percpu_ref_tryget_live() can't be used because + * percpu_ref_kill() can be called by mddev_suspend() + * concurrently. + */ + WARN_ON(percpu_ref_is_zero(&mddev->active_io)); + percpu_ref_get(&mddev->active_io); mddev->flush_bio = bio; bio = NULL; } diff --git a/drivers/md/raid1.c b/drivers/md/raid1.c index 30f906a67def..76f7ca53d812 100644 --- a/drivers/md/raid1.c +++ b/drivers/md/raid1.c @@ -1972,12 +1972,12 @@ static void end_sync_write(struct bio *bio) }
static int r1_sync_page_io(struct md_rdev *rdev, sector_t sector, - int sectors, struct page *page, int rw) + int sectors, struct page *page, blk_opf_t rw) { if (sync_page_io(rdev, sector, sectors << 9, page, rw, false)) /* success */ return 1; - if (rw == WRITE) { + if (rw == REQ_OP_WRITE) { set_bit(WriteErrorSeen, &rdev->flags); if (!test_and_set_bit(WantReplacement, &rdev->flags)) @@ -2094,7 +2094,7 @@ static int fix_sync_read_error(struct r1bio *r1_bio) rdev = conf->mirrors[d].rdev; if (r1_sync_page_io(rdev, sect, s, pages[idx], - WRITE) == 0) { + REQ_OP_WRITE) == 0) { r1_bio->bios[d]->bi_end_io = NULL; rdev_dec_pending(rdev, mddev); } @@ -2109,7 +2109,7 @@ static int fix_sync_read_error(struct r1bio *r1_bio) rdev = conf->mirrors[d].rdev; if (r1_sync_page_io(rdev, sect, s, pages[idx], - READ) != 0) + REQ_OP_READ) != 0) atomic_add(s, &rdev->corrected_errors); } sectors -= s; @@ -2321,7 +2321,7 @@ static void fix_read_error(struct r1conf *conf, int read_disk, atomic_inc(&rdev->nr_pending); rcu_read_unlock(); r1_sync_page_io(rdev, sect, s, - conf->tmppage, WRITE); + conf->tmppage, REQ_OP_WRITE); rdev_dec_pending(rdev, mddev); } else rcu_read_unlock(); @@ -2338,7 +2338,7 @@ static void fix_read_error(struct r1conf *conf, int read_disk, atomic_inc(&rdev->nr_pending); rcu_read_unlock(); if (r1_sync_page_io(rdev, sect, s, - conf->tmppage, READ)) { + conf->tmppage, REQ_OP_READ)) { atomic_add(s, &rdev->corrected_errors); pr_info("md/raid1:%s: read error corrected (%d sectors at %llu on %pg)\n", mdname(mddev), s, diff --git a/drivers/md/raid5.c b/drivers/md/raid5.c index f7783199f81d..e4564ca1f243 100644 --- a/drivers/md/raid5.c +++ b/drivers/md/raid5.c @@ -36,6 +36,7 @@ */
#include <linux/blkdev.h> +#include <linux/delay.h> #include <linux/kthread.h> #include <linux/raid/pq.h> #include <linux/async_tx.h> @@ -6832,7 +6833,18 @@ static void raid5d(struct md_thread *thread) spin_unlock_irq(&conf->device_lock); md_check_recovery(mddev); spin_lock_irq(&conf->device_lock); + + /* + * Waiting on MD_SB_CHANGE_PENDING below may deadlock + * seeing md_check_recovery() is needed to clear + * the flag when using mdmon. + */ + continue; } + + wait_event_lock_irq(mddev->sb_wait, + !test_bit(MD_SB_CHANGE_PENDING, &mddev->sb_flags), + conf->device_lock); } pr_debug("%d stripes handled\n", handled);
diff --git a/drivers/media/dvb-core/dvbdev.c b/drivers/media/dvb-core/dvbdev.c index 9f9a97652708..d352e028491a 100644 --- a/drivers/media/dvb-core/dvbdev.c +++ b/drivers/media/dvb-core/dvbdev.c @@ -104,6 +104,8 @@ static int dvb_device_open(struct inode *inode, struct file *file) err = file->f_op->open(inode, file); up_read(&minor_rwsem); mutex_unlock(&dvbdev_mutex); + if (err) + dvb_device_put(dvbdev); return err; } fail: diff --git a/drivers/media/dvb-frontends/m88ds3103.c b/drivers/media/dvb-frontends/m88ds3103.c index 9a0d43c7ba9e..ce99f7dfb5a5 100644 --- a/drivers/media/dvb-frontends/m88ds3103.c +++ b/drivers/media/dvb-frontends/m88ds3103.c @@ -1894,7 +1894,7 @@ static int m88ds3103_probe(struct i2c_client *client, /* get frontend address */ ret = regmap_read(dev->regmap, 0x29, &utmp); if (ret) - goto err_kfree; + goto err_del_adapters; dev->dt_addr = ((utmp & 0x80) == 0) ? 0x42 >> 1 : 0x40 >> 1; dev_dbg(&client->dev, "dt addr is 0x%02x\n", dev->dt_addr);
@@ -1902,11 +1902,14 @@ static int m88ds3103_probe(struct i2c_client *client, dev->dt_addr); if (IS_ERR(dev->dt_client)) { ret = PTR_ERR(dev->dt_client); - goto err_kfree; + goto err_del_adapters; } }
return 0; + +err_del_adapters: + i2c_mux_del_adapters(dev->muxc); err_kfree: kfree(dev); err: diff --git a/drivers/media/platform/mediatek/jpeg/mtk_jpeg_core.c b/drivers/media/platform/mediatek/jpeg/mtk_jpeg_core.c index e9a4f8abd21c..3071b61946c3 100644 --- a/drivers/media/platform/mediatek/jpeg/mtk_jpeg_core.c +++ b/drivers/media/platform/mediatek/jpeg/mtk_jpeg_core.c @@ -1412,7 +1412,6 @@ static int mtk_jpeg_remove(struct platform_device *pdev) { struct mtk_jpeg_dev *jpeg = platform_get_drvdata(pdev);
- cancel_delayed_work_sync(&jpeg->job_timeout_work); pm_runtime_disable(&pdev->dev); video_unregister_device(jpeg->vdev); v4l2_m2m_release(jpeg->m2m_dev); diff --git a/drivers/media/platform/mediatek/jpeg/mtk_jpeg_dec_hw.c b/drivers/media/platform/mediatek/jpeg/mtk_jpeg_dec_hw.c index afbbfd5d02bc..6d200e23754e 100644 --- a/drivers/media/platform/mediatek/jpeg/mtk_jpeg_dec_hw.c +++ b/drivers/media/platform/mediatek/jpeg/mtk_jpeg_dec_hw.c @@ -188,6 +188,7 @@ int mtk_jpeg_dec_fill_param(struct mtk_jpeg_dec_param *param)
return 0; } +EXPORT_SYMBOL_GPL(mtk_jpeg_dec_fill_param);
u32 mtk_jpeg_dec_get_int_status(void __iomem *base) { @@ -199,6 +200,7 @@ u32 mtk_jpeg_dec_get_int_status(void __iomem *base)
return ret; } +EXPORT_SYMBOL_GPL(mtk_jpeg_dec_get_int_status);
u32 mtk_jpeg_dec_enum_result(u32 irq_result) { @@ -215,11 +217,13 @@ u32 mtk_jpeg_dec_enum_result(u32 irq_result)
return MTK_JPEG_DEC_RESULT_ERROR_UNKNOWN; } +EXPORT_SYMBOL_GPL(mtk_jpeg_dec_enum_result);
void mtk_jpeg_dec_start(void __iomem *base) { writel(0, base + JPGDEC_REG_TRIG); } +EXPORT_SYMBOL_GPL(mtk_jpeg_dec_start);
static void mtk_jpeg_dec_soft_reset(void __iomem *base) { @@ -239,6 +243,7 @@ void mtk_jpeg_dec_reset(void __iomem *base) mtk_jpeg_dec_soft_reset(base); mtk_jpeg_dec_hard_reset(base); } +EXPORT_SYMBOL_GPL(mtk_jpeg_dec_reset);
static void mtk_jpeg_dec_set_brz_factor(void __iomem *base, u8 yscale_w, u8 yscale_h, u8 uvscale_w, u8 uvscale_h) @@ -407,3 +412,4 @@ void mtk_jpeg_dec_set_config(void __iomem *base, config->dma_last_mcu); mtk_jpeg_dec_set_pause_mcu_idx(base, config->total_mcu); } +EXPORT_SYMBOL_GPL(mtk_jpeg_dec_set_config); diff --git a/drivers/media/platform/nxp/imx-mipi-csis.c b/drivers/media/platform/nxp/imx-mipi-csis.c index 905072871ed2..196f2bba419f 100644 --- a/drivers/media/platform/nxp/imx-mipi-csis.c +++ b/drivers/media/platform/nxp/imx-mipi-csis.c @@ -1553,8 +1553,10 @@ static int mipi_csis_remove(struct platform_device *pdev) v4l2_async_nf_cleanup(&csis->notifier); v4l2_async_unregister_subdev(&csis->sd);
+ if (!pm_runtime_enabled(&pdev->dev)) + mipi_csis_runtime_suspend(&pdev->dev); + pm_runtime_disable(&pdev->dev); - mipi_csis_runtime_suspend(&pdev->dev); mipi_csis_clk_disable(csis); media_entity_cleanup(&csis->sd.entity); fwnode_handle_put(csis->sd.fwnode); diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c index f2475c6235ea..2b76339f9381 100644 --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c @@ -582,7 +582,7 @@ static int rkisp1_probe(struct platform_device *pdev)
ret = v4l2_device_register(rkisp1->dev, &rkisp1->v4l2_dev); if (ret) - goto err_pm_runtime_disable; + goto err_media_dev_cleanup;
ret = media_device_register(&rkisp1->media_dev); if (ret) { @@ -617,6 +617,8 @@ static int rkisp1_probe(struct platform_device *pdev) media_device_unregister(&rkisp1->media_dev); err_unreg_v4l2_dev: v4l2_device_unregister(&rkisp1->v4l2_dev); +err_media_dev_cleanup: + media_device_cleanup(&rkisp1->media_dev); err_pm_runtime_disable: pm_runtime_disable(&pdev->dev); return ret; @@ -637,6 +639,8 @@ static int rkisp1_remove(struct platform_device *pdev) media_device_unregister(&rkisp1->media_dev); v4l2_device_unregister(&rkisp1->v4l2_dev);
+ media_device_cleanup(&rkisp1->media_dev); + pm_runtime_disable(&pdev->dev);
return 0; diff --git a/drivers/media/platform/verisilicon/hantro_drv.c b/drivers/media/platform/verisilicon/hantro_drv.c index 08840ba313e7..69a2442f3122 100644 --- a/drivers/media/platform/verisilicon/hantro_drv.c +++ b/drivers/media/platform/verisilicon/hantro_drv.c @@ -813,6 +813,8 @@ static int hantro_add_func(struct hantro_dev *vpu, unsigned int funcid)
if (funcid == MEDIA_ENT_F_PROC_VIDEO_ENCODER) { vpu->encoder = func; + v4l2_disable_ioctl(vfd, VIDIOC_TRY_DECODER_CMD); + v4l2_disable_ioctl(vfd, VIDIOC_DECODER_CMD); } else { vpu->decoder = func; v4l2_disable_ioctl(vfd, VIDIOC_TRY_ENCODER_CMD); diff --git a/drivers/media/platform/verisilicon/hantro_v4l2.c b/drivers/media/platform/verisilicon/hantro_v4l2.c index 30e650edaea8..b2da48936e3f 100644 --- a/drivers/media/platform/verisilicon/hantro_v4l2.c +++ b/drivers/media/platform/verisilicon/hantro_v4l2.c @@ -759,6 +759,9 @@ const struct v4l2_ioctl_ops hantro_ioctl_ops = { .vidioc_g_selection = vidioc_g_selection, .vidioc_s_selection = vidioc_s_selection,
+ .vidioc_decoder_cmd = v4l2_m2m_ioctl_stateless_decoder_cmd, + .vidioc_try_decoder_cmd = v4l2_m2m_ioctl_stateless_try_decoder_cmd, + .vidioc_try_encoder_cmd = v4l2_m2m_ioctl_try_encoder_cmd, .vidioc_encoder_cmd = vidioc_encoder_cmd, }; diff --git a/drivers/media/usb/cx231xx/cx231xx-core.c b/drivers/media/usb/cx231xx/cx231xx-core.c index 727e6268567f..f1feccc28bf0 100644 --- a/drivers/media/usb/cx231xx/cx231xx-core.c +++ b/drivers/media/usb/cx231xx/cx231xx-core.c @@ -1024,6 +1024,7 @@ int cx231xx_init_isoc(struct cx231xx *dev, int max_packets, if (!dev->video_mode.isoc_ctl.urb) { dev_err(dev->dev, "cannot alloc memory for usb buffers\n"); + kfree(dma_q->p_left_data); return -ENOMEM; }
@@ -1033,6 +1034,7 @@ int cx231xx_init_isoc(struct cx231xx *dev, int max_packets, dev_err(dev->dev, "cannot allocate memory for usbtransfer\n"); kfree(dev->video_mode.isoc_ctl.urb); + kfree(dma_q->p_left_data); return -ENOMEM; }
diff --git a/drivers/media/usb/pvrusb2/pvrusb2-context.c b/drivers/media/usb/pvrusb2/pvrusb2-context.c index 14170a5d72b3..1764674de98b 100644 --- a/drivers/media/usb/pvrusb2/pvrusb2-context.c +++ b/drivers/media/usb/pvrusb2/pvrusb2-context.c @@ -268,7 +268,8 @@ void pvr2_context_disconnect(struct pvr2_context *mp) { pvr2_hdw_disconnect(mp->hdw); mp->disconnect_flag = !0; - pvr2_context_notify(mp); + if (!pvr2_context_shutok()) + pvr2_context_notify(mp); }
diff --git a/drivers/mfd/intel-lpss.c b/drivers/mfd/intel-lpss.c index cfbee2cfba6b..c50387600b81 100644 --- a/drivers/mfd/intel-lpss.c +++ b/drivers/mfd/intel-lpss.c @@ -301,8 +301,8 @@ static int intel_lpss_register_clock_divider(struct intel_lpss *lpss,
snprintf(name, sizeof(name), "%s-div", devname); tmp = clk_register_fractional_divider(NULL, name, __clk_get_name(tmp), + 0, lpss->priv, 1, 15, 16, 15, CLK_FRAC_DIVIDER_POWER_OF_TWO_PS, - lpss->priv, 1, 15, 16, 15, 0, NULL); if (IS_ERR(tmp)) return PTR_ERR(tmp); diff --git a/drivers/mfd/syscon.c b/drivers/mfd/syscon.c index bdb2ce7ff03b..6196724ef39b 100644 --- a/drivers/mfd/syscon.c +++ b/drivers/mfd/syscon.c @@ -102,6 +102,10 @@ static struct syscon *of_syscon_register(struct device_node *np, bool check_clk) }
syscon_config.name = kasprintf(GFP_KERNEL, "%pOFn@%pa", np, &res.start); + if (!syscon_config.name) { + ret = -ENOMEM; + goto err_regmap; + } syscon_config.reg_stride = reg_io_width; syscon_config.val_bits = reg_io_width * 8; syscon_config.max_register = resource_size(&res) - reg_io_width; diff --git a/drivers/misc/habanalabs/common/habanalabs_ioctl.c b/drivers/misc/habanalabs/common/habanalabs_ioctl.c index 43afe40966e5..1ea1ae34b7a7 100644 --- a/drivers/misc/habanalabs/common/habanalabs_ioctl.c +++ b/drivers/misc/habanalabs/common/habanalabs_ioctl.c @@ -677,7 +677,7 @@ static int sec_attest_info(struct hl_fpriv *hpriv, struct hl_info_args *args) if (!sec_attest_info) return -ENOMEM;
- info = kmalloc(sizeof(*info), GFP_KERNEL); + info = kzalloc(sizeof(*info), GFP_KERNEL); if (!info) { rc = -ENOMEM; goto free_sec_attest_info; diff --git a/drivers/mmc/host/Kconfig b/drivers/mmc/host/Kconfig index 9b5a2cb110b3..d84bdb69f56b 100644 --- a/drivers/mmc/host/Kconfig +++ b/drivers/mmc/host/Kconfig @@ -1061,14 +1061,15 @@ config MMC_SDHCI_XENON
config MMC_SDHCI_OMAP tristate "TI SDHCI Controller Support" + depends on ARCH_OMAP2PLUS || ARCH_KEYSTONE || COMPILE_TEST depends on MMC_SDHCI_PLTFM && OF select THERMAL imply TI_SOC_THERMAL select MMC_SDHCI_EXTERNAL_DMA if DMA_ENGINE help This selects the Secure Digital Host Controller Interface (SDHCI) - support present in TI's DRA7 SOCs. The controller supports - SD/MMC/SDIO devices. + support present in TI's Keystone/OMAP2+/DRA7 SOCs. The controller + supports SD/MMC/SDIO devices.
If you have a controller with this interface, say Y or M here.
@@ -1076,14 +1077,15 @@ config MMC_SDHCI_OMAP
config MMC_SDHCI_AM654 tristate "Support for the SDHCI Controller in TI's AM654 SOCs" + depends on ARCH_K3 || COMPILE_TEST depends on MMC_SDHCI_PLTFM && OF select MMC_SDHCI_IO_ACCESSORS select MMC_CQHCI select REGMAP_MMIO help This selects the Secure Digital Host Controller Interface (SDHCI) - support present in TI's AM654 SOCs. The controller supports - SD/MMC/SDIO devices. + support present in TI's AM65x/AM64x/AM62x/J721E SOCs. The controller + supports SD/MMC/SDIO devices.
If you have a controller with this interface, say Y or M here.
diff --git a/drivers/mtd/mtd_blkdevs.c b/drivers/mtd/mtd_blkdevs.c index 60b222799871..8ee60605a6dc 100644 --- a/drivers/mtd/mtd_blkdevs.c +++ b/drivers/mtd/mtd_blkdevs.c @@ -463,7 +463,7 @@ static void blktrans_notify_add(struct mtd_info *mtd) { struct mtd_blktrans_ops *tr;
- if (mtd->type == MTD_ABSENT) + if (mtd->type == MTD_ABSENT || mtd->type == MTD_UBIVOLUME) return;
list_for_each_entry(tr, &blktrans_majors, list) @@ -503,7 +503,7 @@ int register_mtd_blktrans(struct mtd_blktrans_ops *tr) mutex_lock(&mtd_table_mutex); list_add(&tr->list, &blktrans_majors); mtd_for_each_device(mtd) - if (mtd->type != MTD_ABSENT) + if (mtd->type != MTD_ABSENT && mtd->type != MTD_UBIVOLUME) tr->add_mtd(tr, mtd); mutex_unlock(&mtd_table_mutex); return 0; diff --git a/drivers/mtd/nand/raw/fsl_ifc_nand.c b/drivers/mtd/nand/raw/fsl_ifc_nand.c index 02d500176838..bea1a7d3edd7 100644 --- a/drivers/mtd/nand/raw/fsl_ifc_nand.c +++ b/drivers/mtd/nand/raw/fsl_ifc_nand.c @@ -20,7 +20,7 @@
#define ERR_BYTE 0xFF /* Value returned for read bytes when read failed */ -#define IFC_TIMEOUT_MSECS 500 /* Maximum number of mSecs to wait +#define IFC_TIMEOUT_MSECS 1000 /* Maximum timeout to wait for IFC NAND Machine */
struct fsl_ifc_ctrl; diff --git a/drivers/net/amt.c b/drivers/net/amt.c index 2d20be6ffb7e..ddd087c2c3ed 100644 --- a/drivers/net/amt.c +++ b/drivers/net/amt.c @@ -11,7 +11,7 @@ #include <linux/net.h> #include <linux/igmp.h> #include <linux/workqueue.h> -#include <net/sch_generic.h> +#include <net/pkt_sched.h> #include <net/net_namespace.h> #include <net/ip.h> #include <net/udp.h> @@ -80,11 +80,11 @@ static struct mld2_grec mldv2_zero_grec;
static struct amt_skb_cb *amt_skb_cb(struct sk_buff *skb) { - BUILD_BUG_ON(sizeof(struct amt_skb_cb) + sizeof(struct qdisc_skb_cb) > + BUILD_BUG_ON(sizeof(struct amt_skb_cb) + sizeof(struct tc_skb_cb) > sizeof_field(struct sk_buff, cb));
return (struct amt_skb_cb *)((void *)skb->cb + - sizeof(struct qdisc_skb_cb)); + sizeof(struct tc_skb_cb)); }
static void __amt_source_gc_work(void) diff --git a/drivers/net/dsa/vitesse-vsc73xx-core.c b/drivers/net/dsa/vitesse-vsc73xx-core.c index ef1a4a7c47b2..3efd55669056 100644 --- a/drivers/net/dsa/vitesse-vsc73xx-core.c +++ b/drivers/net/dsa/vitesse-vsc73xx-core.c @@ -1119,6 +1119,8 @@ static int vsc73xx_gpio_probe(struct vsc73xx *vsc)
vsc->gc.label = devm_kasprintf(vsc->dev, GFP_KERNEL, "VSC%04x", vsc->chipid); + if (!vsc->gc.label) + return -ENOMEM; vsc->gc.ngpio = 4; vsc->gc.owner = THIS_MODULE; vsc->gc.parent = vsc->dev; diff --git a/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_main.c b/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_main.c index 2292d63a279c..83c4659390fd 100644 --- a/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_main.c +++ b/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_main.c @@ -130,9 +130,15 @@ static int mlxbf_gige_open(struct net_device *netdev) { struct mlxbf_gige *priv = netdev_priv(netdev); struct phy_device *phydev = netdev->phydev; + u64 control; u64 int_en; int err;
+ /* Perform general init of GigE block */ + control = readq(priv->base + MLXBF_GIGE_CONTROL); + control |= MLXBF_GIGE_CONTROL_PORT_EN; + writeq(control, priv->base + MLXBF_GIGE_CONTROL); + err = mlxbf_gige_request_irqs(priv); if (err) return err; @@ -147,14 +153,14 @@ static int mlxbf_gige_open(struct net_device *netdev) */ priv->valid_polarity = 0;
- err = mlxbf_gige_rx_init(priv); + phy_start(phydev); + + err = mlxbf_gige_tx_init(priv); if (err) goto free_irqs; - err = mlxbf_gige_tx_init(priv); + err = mlxbf_gige_rx_init(priv); if (err) - goto rx_deinit; - - phy_start(phydev); + goto tx_deinit;
netif_napi_add(netdev, &priv->napi, mlxbf_gige_poll); napi_enable(&priv->napi); @@ -176,8 +182,8 @@ static int mlxbf_gige_open(struct net_device *netdev)
return 0;
-rx_deinit: - mlxbf_gige_rx_deinit(priv); +tx_deinit: + mlxbf_gige_tx_deinit(priv);
free_irqs: mlxbf_gige_free_irqs(priv); @@ -279,7 +285,6 @@ static int mlxbf_gige_probe(struct platform_device *pdev) void __iomem *plu_base; void __iomem *base; int addr, phy_irq; - u64 control; int err;
base = devm_platform_ioremap_resource(pdev, MLXBF_GIGE_RES_MAC); @@ -294,11 +299,6 @@ static int mlxbf_gige_probe(struct platform_device *pdev) if (IS_ERR(plu_base)) return PTR_ERR(plu_base);
- /* Perform general init of GigE block */ - control = readq(base + MLXBF_GIGE_CONTROL); - control |= MLXBF_GIGE_CONTROL_PORT_EN; - writeq(control, base + MLXBF_GIGE_CONTROL); - netdev = devm_alloc_etherdev(&pdev->dev, sizeof(*priv)); if (!netdev) return -ENOMEM; diff --git a/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_rx.c b/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_rx.c index 227d01cace3f..699984358493 100644 --- a/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_rx.c +++ b/drivers/net/ethernet/mellanox/mlxbf_gige/mlxbf_gige_rx.c @@ -142,6 +142,9 @@ int mlxbf_gige_rx_init(struct mlxbf_gige *priv) writeq(MLXBF_GIGE_RX_MAC_FILTER_COUNT_PASS_EN, priv->base + MLXBF_GIGE_RX_MAC_FILTER_COUNT_PASS);
+ writeq(ilog2(priv->rx_q_entries), + priv->base + MLXBF_GIGE_RX_WQE_SIZE_LOG2); + /* Clear MLXBF_GIGE_INT_MASK 'receive pkt' bit to * indicate readiness to receive interrupts */ @@ -154,9 +157,6 @@ int mlxbf_gige_rx_init(struct mlxbf_gige *priv) data |= MLXBF_GIGE_RX_DMA_EN; writeq(data, priv->base + MLXBF_GIGE_RX_DMA);
- writeq(ilog2(priv->rx_q_entries), - priv->base + MLXBF_GIGE_RX_WQE_SIZE_LOG2); - return 0;
free_wqe_and_skb: diff --git a/drivers/net/ethernet/mellanox/mlxsw/spectrum_acl_erp.c b/drivers/net/ethernet/mellanox/mlxsw/spectrum_acl_erp.c index 4c98950380d5..d231f4d2888b 100644 --- a/drivers/net/ethernet/mellanox/mlxsw/spectrum_acl_erp.c +++ b/drivers/net/ethernet/mellanox/mlxsw/spectrum_acl_erp.c @@ -301,6 +301,7 @@ mlxsw_sp_acl_erp_table_alloc(struct mlxsw_sp_acl_erp_core *erp_core, unsigned long *p_index) { unsigned int num_rows, entry_size; + unsigned long index;
/* We only allow allocations of entire rows */ if (num_erps % erp_core->num_erp_banks != 0) @@ -309,10 +310,11 @@ mlxsw_sp_acl_erp_table_alloc(struct mlxsw_sp_acl_erp_core *erp_core, entry_size = erp_core->erpt_entries_size[region_type]; num_rows = num_erps / erp_core->num_erp_banks;
- *p_index = gen_pool_alloc(erp_core->erp_tables, num_rows * entry_size); - if (*p_index == 0) + index = gen_pool_alloc(erp_core->erp_tables, num_rows * entry_size); + if (!index) return -ENOBUFS; - *p_index -= MLXSW_SP_ACL_ERP_GENALLOC_OFFSET; + + *p_index = index - MLXSW_SP_ACL_ERP_GENALLOC_OFFSET;
return 0; } diff --git a/drivers/net/ethernet/qualcomm/rmnet/rmnet_config.c b/drivers/net/ethernet/qualcomm/rmnet/rmnet_config.c index 27b1663c476e..64b209a0ad21 100644 --- a/drivers/net/ethernet/qualcomm/rmnet/rmnet_config.c +++ b/drivers/net/ethernet/qualcomm/rmnet/rmnet_config.c @@ -391,7 +391,7 @@ static int rmnet_fill_info(struct sk_buff *skb, const struct net_device *dev)
struct rtnl_link_ops rmnet_link_ops __read_mostly = { .kind = "rmnet", - .maxtype = __IFLA_RMNET_MAX, + .maxtype = IFLA_RMNET_MAX, .priv_size = sizeof(struct rmnet_priv), .setup = rmnet_vnd_setup, .validate = rmnet_rtnl_validate, diff --git a/drivers/net/ethernet/renesas/ravb_main.c b/drivers/net/ethernet/renesas/ravb_main.c index c2c56a5289ca..e7b70006261f 100644 --- a/drivers/net/ethernet/renesas/ravb_main.c +++ b/drivers/net/ethernet/renesas/ravb_main.c @@ -1965,7 +1965,7 @@ static netdev_tx_t ravb_start_xmit(struct sk_buff *skb, struct net_device *ndev) struct ravb_tstamp_skb *ts_skb; struct ravb_tx_desc *desc; unsigned long flags; - u32 dma_addr; + dma_addr_t dma_addr; void *buffer; u32 entry; u32 len; diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac.h b/drivers/net/ethernet/stmicro/stmmac/stmmac.h index bdbf86cb102a..46944c02b45e 100644 --- a/drivers/net/ethernet/stmicro/stmmac/stmmac.h +++ b/drivers/net/ethernet/stmicro/stmmac/stmmac.h @@ -247,6 +247,7 @@ struct stmmac_priv { u32 msg_enable; int wolopts; int wol_irq; + bool wol_irq_disabled; int clk_csr; struct timer_list eee_ctrl_timer; int lpi_irq; diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_ethtool.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_ethtool.c index 35c8dd92d369..f03aa8a0b895 100644 --- a/drivers/net/ethernet/stmicro/stmmac/stmmac_ethtool.c +++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_ethtool.c @@ -761,10 +761,16 @@ static int stmmac_set_wol(struct net_device *dev, struct ethtool_wolinfo *wol) if (wol->wolopts) { pr_info("stmmac: wakeup enable\n"); device_set_wakeup_enable(priv->device, 1); - enable_irq_wake(priv->wol_irq); + /* Avoid unbalanced enable_irq_wake calls */ + if (priv->wol_irq_disabled) + enable_irq_wake(priv->wol_irq); + priv->wol_irq_disabled = false; } else { device_set_wakeup_enable(priv->device, 0); - disable_irq_wake(priv->wol_irq); + /* Avoid unbalanced disable_irq_wake calls */ + if (!priv->wol_irq_disabled) + disable_irq_wake(priv->wol_irq); + priv->wol_irq_disabled = true; }
mutex_lock(&priv->lock); diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c index deb6e95a1bca..8f8de14347a9 100644 --- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c +++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c @@ -3519,6 +3519,7 @@ static int stmmac_request_irq_multi_msi(struct net_device *dev) /* Request the Wake IRQ in case of another line * is used for WoL */ + priv->wol_irq_disabled = true; if (priv->wol_irq > 0 && priv->wol_irq != dev->irq) { int_name = priv->int_name_wol; sprintf(int_name, "%s:%s", dev->name, "wol"); diff --git a/drivers/net/ethernet/ti/am65-cpsw-nuss.c b/drivers/net/ethernet/ti/am65-cpsw-nuss.c index 9f2553799895..76fabeae512d 100644 --- a/drivers/net/ethernet/ti/am65-cpsw-nuss.c +++ b/drivers/net/ethernet/ti/am65-cpsw-nuss.c @@ -54,7 +54,7 @@ #define AM65_CPSW_MAX_PORTS 8
#define AM65_CPSW_MIN_PACKET_SIZE VLAN_ETH_ZLEN -#define AM65_CPSW_MAX_PACKET_SIZE (VLAN_ETH_FRAME_LEN + ETH_FCS_LEN) +#define AM65_CPSW_MAX_PACKET_SIZE 2024
#define AM65_CPSW_REG_CTL 0x004 #define AM65_CPSW_REG_STAT_PORT_EN 0x014 @@ -1990,7 +1990,8 @@ am65_cpsw_nuss_init_port_ndev(struct am65_cpsw_common *common, u32 port_idx) eth_hw_addr_set(port->ndev, port->slave.mac_addr);
port->ndev->min_mtu = AM65_CPSW_MIN_PACKET_SIZE; - port->ndev->max_mtu = AM65_CPSW_MAX_PACKET_SIZE; + port->ndev->max_mtu = AM65_CPSW_MAX_PACKET_SIZE - + (VLAN_ETH_HLEN + ETH_FCS_LEN); port->ndev->hw_features = NETIF_F_SG | NETIF_F_RXCSUM | NETIF_F_HW_CSUM | diff --git a/drivers/net/phy/micrel.c b/drivers/net/phy/micrel.c index 54a17b576eac..7cbcf51bae92 100644 --- a/drivers/net/phy/micrel.c +++ b/drivers/net/phy/micrel.c @@ -3302,6 +3302,7 @@ static struct phy_driver ksphy_driver[] = { .flags = PHY_POLL_CABLE_TEST, .driver_data = &ksz9021_type, .probe = kszphy_probe, + .soft_reset = genphy_soft_reset, .config_init = ksz9131_config_init, .config_intr = kszphy_config_intr, .handle_interrupt = kszphy_handle_interrupt, diff --git a/drivers/net/wireless/ath/ath11k/ahb.c b/drivers/net/wireless/ath/ath11k/ahb.c index 76f275ca53e9..70d468f01338 100644 --- a/drivers/net/wireless/ath/ath11k/ahb.c +++ b/drivers/net/wireless/ath/ath11k/ahb.c @@ -813,8 +813,8 @@ static int ath11k_core_get_rproc(struct ath11k_base *ab)
prproc = rproc_get_by_phandle(rproc_phandle); if (!prproc) { - ath11k_err(ab, "failed to get rproc\n"); - return -EINVAL; + ath11k_dbg(ab, ATH11K_DBG_AHB, "failed to get rproc, deferring\n"); + return -EPROBE_DEFER; } ab_ahb->tgt_rproc = prproc;
diff --git a/drivers/net/wireless/intel/iwlwifi/mvm/phy-ctxt.c b/drivers/net/wireless/intel/iwlwifi/mvm/phy-ctxt.c index a3cefbc43e80..2c14188f34bb 100644 --- a/drivers/net/wireless/intel/iwlwifi/mvm/phy-ctxt.c +++ b/drivers/net/wireless/intel/iwlwifi/mvm/phy-ctxt.c @@ -99,17 +99,6 @@ static void iwl_mvm_phy_ctxt_set_rxchain(struct iwl_mvm *mvm, active_cnt = 2; }
- /* - * If the firmware requested it, then we know that it supports - * getting zero for the values to indicate "use one, but pick - * which one yourself", which means it can dynamically pick one - * that e.g. has better RSSI. - */ - if (mvm->fw_static_smps_request && active_cnt == 1 && idle_cnt == 1) { - idle_cnt = 0; - active_cnt = 0; - } - *rxchain_info = cpu_to_le32(iwl_mvm_get_valid_rx_ant(mvm) << PHY_RX_CHAIN_VALID_POS); *rxchain_info |= cpu_to_le32(idle_cnt << PHY_RX_CHAIN_CNT_POS); diff --git a/drivers/net/wireless/intel/iwlwifi/mvm/tx.c b/drivers/net/wireless/intel/iwlwifi/mvm/tx.c index caaf4d52e2c6..76219486b9c2 100644 --- a/drivers/net/wireless/intel/iwlwifi/mvm/tx.c +++ b/drivers/net/wireless/intel/iwlwifi/mvm/tx.c @@ -2200,7 +2200,7 @@ int iwl_mvm_flush_sta_tids(struct iwl_mvm *mvm, u32 sta_id, u16 tids) WARN_ON(!iwl_mvm_has_new_tx_api(mvm));
if (iwl_fw_lookup_notif_ver(mvm->fw, LONG_GROUP, TXPATH_FLUSH, 0) > 0) - cmd.flags |= CMD_WANT_SKB; + cmd.flags |= CMD_WANT_SKB | CMD_SEND_IN_RFKILL;
IWL_DEBUG_TX_QUEUES(mvm, "flush for sta id %d tid mask 0x%x\n", sta_id, tids); diff --git a/drivers/net/wireless/marvell/libertas/Kconfig b/drivers/net/wireless/marvell/libertas/Kconfig index 6d62ab49aa8d..c7d02adb3eea 100644 --- a/drivers/net/wireless/marvell/libertas/Kconfig +++ b/drivers/net/wireless/marvell/libertas/Kconfig @@ -2,8 +2,6 @@ config LIBERTAS tristate "Marvell 8xxx Libertas WLAN driver support" depends on CFG80211 - select WIRELESS_EXT - select WEXT_SPY select LIB80211 select FW_LOADER help diff --git a/drivers/net/wireless/marvell/mwifiex/cfg80211.c b/drivers/net/wireless/marvell/mwifiex/cfg80211.c index bcd564dc3554..c907da2a4789 100644 --- a/drivers/net/wireless/marvell/mwifiex/cfg80211.c +++ b/drivers/net/wireless/marvell/mwifiex/cfg80211.c @@ -2046,6 +2046,8 @@ static int mwifiex_cfg80211_start_ap(struct wiphy *wiphy,
mwifiex_set_sys_config_invalid_data(bss_cfg);
+ memcpy(bss_cfg->mac_addr, priv->curr_addr, ETH_ALEN); + if (params->beacon_interval) bss_cfg->beacon_period = params->beacon_interval; if (params->dtim_period) diff --git a/drivers/net/wireless/marvell/mwifiex/fw.h b/drivers/net/wireless/marvell/mwifiex/fw.h index b4f945a549f7..863f5f2247a0 100644 --- a/drivers/net/wireless/marvell/mwifiex/fw.h +++ b/drivers/net/wireless/marvell/mwifiex/fw.h @@ -165,6 +165,7 @@ enum MWIFIEX_802_11_PRIVACY_FILTER { #define TLV_TYPE_STA_MAC_ADDR (PROPRIETARY_TLV_BASE_ID + 32) #define TLV_TYPE_BSSID (PROPRIETARY_TLV_BASE_ID + 35) #define TLV_TYPE_CHANNELBANDLIST (PROPRIETARY_TLV_BASE_ID + 42) +#define TLV_TYPE_UAP_MAC_ADDRESS (PROPRIETARY_TLV_BASE_ID + 43) #define TLV_TYPE_UAP_BEACON_PERIOD (PROPRIETARY_TLV_BASE_ID + 44) #define TLV_TYPE_UAP_DTIM_PERIOD (PROPRIETARY_TLV_BASE_ID + 45) #define TLV_TYPE_UAP_BCAST_SSID (PROPRIETARY_TLV_BASE_ID + 48) diff --git a/drivers/net/wireless/marvell/mwifiex/ioctl.h b/drivers/net/wireless/marvell/mwifiex/ioctl.h index 091e7ca79376..e8825f302de8 100644 --- a/drivers/net/wireless/marvell/mwifiex/ioctl.h +++ b/drivers/net/wireless/marvell/mwifiex/ioctl.h @@ -107,6 +107,7 @@ struct mwifiex_uap_bss_param { u8 qos_info; u8 power_constraint; struct mwifiex_types_wmm_info wmm_info; + u8 mac_addr[ETH_ALEN]; };
enum { diff --git a/drivers/net/wireless/marvell/mwifiex/uap_cmd.c b/drivers/net/wireless/marvell/mwifiex/uap_cmd.c index e78a201cd150..491e36611909 100644 --- a/drivers/net/wireless/marvell/mwifiex/uap_cmd.c +++ b/drivers/net/wireless/marvell/mwifiex/uap_cmd.c @@ -468,6 +468,7 @@ void mwifiex_config_uap_11d(struct mwifiex_private *priv, static int mwifiex_uap_bss_param_prepare(u8 *tlv, void *cmd_buf, u16 *param_size) { + struct host_cmd_tlv_mac_addr *mac_tlv; struct host_cmd_tlv_dtim_period *dtim_period; struct host_cmd_tlv_beacon_period *beacon_period; struct host_cmd_tlv_ssid *ssid; @@ -487,6 +488,13 @@ mwifiex_uap_bss_param_prepare(u8 *tlv, void *cmd_buf, u16 *param_size) int i; u16 cmd_size = *param_size;
+ mac_tlv = (struct host_cmd_tlv_mac_addr *)tlv; + mac_tlv->header.type = cpu_to_le16(TLV_TYPE_UAP_MAC_ADDRESS); + mac_tlv->header.len = cpu_to_le16(ETH_ALEN); + memcpy(mac_tlv->mac_addr, bss_cfg->mac_addr, ETH_ALEN); + cmd_size += sizeof(struct host_cmd_tlv_mac_addr); + tlv += sizeof(struct host_cmd_tlv_mac_addr); + if (bss_cfg->ssid.ssid_len) { ssid = (struct host_cmd_tlv_ssid *)tlv; ssid->header.type = cpu_to_le16(TLV_TYPE_UAP_SSID); diff --git a/drivers/net/wireless/mediatek/mt76/eeprom.c b/drivers/net/wireless/mediatek/mt76/eeprom.c index 9bc8758573fc..0a88048b8976 100644 --- a/drivers/net/wireless/mediatek/mt76/eeprom.c +++ b/drivers/net/wireless/mediatek/mt76/eeprom.c @@ -62,7 +62,7 @@ int mt76_get_of_eeprom(struct mt76_dev *dev, void *eep, int offset, int len) goto out_put_node; }
- offset = be32_to_cpup(list); + offset += be32_to_cpup(list); ret = mtd_read(mtd, offset, len, &retlen, eep); put_mtd_device(mtd); if (mtd_is_bitflip(ret)) diff --git a/drivers/net/wireless/mediatek/mt76/mt76.h b/drivers/net/wireless/mediatek/mt76/mt76.h index 9c753c6aabef..60c9f9c56a4f 100644 --- a/drivers/net/wireless/mediatek/mt76/mt76.h +++ b/drivers/net/wireless/mediatek/mt76/mt76.h @@ -564,8 +564,7 @@ struct mt76_sdio { struct mt76_worker txrx_worker; struct mt76_worker status_worker; struct mt76_worker net_worker; - - struct work_struct stat_work; + struct mt76_worker stat_worker;
u8 *xmit_buf; u32 xmit_buf_sz; diff --git a/drivers/net/wireless/mediatek/mt76/mt7615/sdio.c b/drivers/net/wireless/mediatek/mt76/mt7615/sdio.c index 304212f5f8da..d742b22428f0 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7615/sdio.c +++ b/drivers/net/wireless/mediatek/mt76/mt7615/sdio.c @@ -205,8 +205,8 @@ static int mt7663s_suspend(struct device *dev) mt76_worker_disable(&mdev->mt76.sdio.txrx_worker); mt76_worker_disable(&mdev->mt76.sdio.status_worker); mt76_worker_disable(&mdev->mt76.sdio.net_worker); + mt76_worker_disable(&mdev->mt76.sdio.stat_worker);
- cancel_work_sync(&mdev->mt76.sdio.stat_work); clear_bit(MT76_READING_STATS, &mdev->mphy.state);
mt76_tx_status_check(&mdev->mt76, true); diff --git a/drivers/net/wireless/mediatek/mt76/mt7921/mcu.c b/drivers/net/wireless/mediatek/mt76/mt7921/mcu.c index 10dda1693d7d..19640ff76bdc 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7921/mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mt7921/mcu.c @@ -1036,21 +1036,26 @@ int __mt7921_mcu_set_clc(struct mt7921_dev *dev, u8 *alpha2, u8 type[2]; u8 rsvd[64]; } __packed req = { + .ver = 1, .idx = idx, .env = env_cap, }; int ret, valid_cnt = 0; - u8 i, *pos; + u16 buf_len = 0; + u8 *pos;
if (!clc) return 0;
+ buf_len = le16_to_cpu(clc->len) - sizeof(*clc); pos = clc->data; - for (i = 0; i < clc->nr_country; i++) { + while (buf_len > 16) { struct mt7921_clc_rule *rule = (struct mt7921_clc_rule *)pos; u16 len = le16_to_cpu(rule->len); + u16 offset = len + sizeof(*rule);
- pos += len + sizeof(*rule); + pos += offset; + buf_len -= offset; if (rule->alpha2[0] != alpha2[0] || rule->alpha2[1] != alpha2[1]) continue; diff --git a/drivers/net/wireless/mediatek/mt76/mt7921/sdio.c b/drivers/net/wireless/mediatek/mt76/mt7921/sdio.c index 3b25a06fd946..8898ba69b8e9 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7921/sdio.c +++ b/drivers/net/wireless/mediatek/mt76/mt7921/sdio.c @@ -222,7 +222,7 @@ static int mt7921s_suspend(struct device *__dev) mt76_txq_schedule_all(&dev->mphy); mt76_worker_disable(&mdev->tx_worker); mt76_worker_disable(&mdev->sdio.status_worker); - cancel_work_sync(&mdev->sdio.stat_work); + mt76_worker_disable(&mdev->sdio.stat_worker); clear_bit(MT76_READING_STATS, &dev->mphy.state); mt76_tx_status_check(mdev, true);
@@ -254,6 +254,7 @@ static int mt7921s_suspend(struct device *__dev) restore_worker: mt76_worker_enable(&mdev->tx_worker); mt76_worker_enable(&mdev->sdio.status_worker); + mt76_worker_enable(&mdev->sdio.stat_worker);
if (!pm->ds_enable) mt76_connac_mcu_set_deep_sleep(mdev, false); @@ -286,6 +287,7 @@ static int mt7921s_resume(struct device *__dev) mt76_worker_enable(&mdev->sdio.txrx_worker); mt76_worker_enable(&mdev->sdio.status_worker); mt76_worker_enable(&mdev->sdio.net_worker); + mt76_worker_enable(&mdev->sdio.stat_worker);
/* restore previous ds setting */ if (!pm->ds_enable) diff --git a/drivers/net/wireless/mediatek/mt76/mt7921/sdio_mac.c b/drivers/net/wireless/mediatek/mt76/mt7921/sdio_mac.c index 1b3adb3d91e8..fd07b6623392 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7921/sdio_mac.c +++ b/drivers/net/wireless/mediatek/mt76/mt7921/sdio_mac.c @@ -107,7 +107,7 @@ int mt7921s_mac_reset(struct mt7921_dev *dev) mt76_worker_disable(&dev->mt76.sdio.txrx_worker); mt76_worker_disable(&dev->mt76.sdio.status_worker); mt76_worker_disable(&dev->mt76.sdio.net_worker); - cancel_work_sync(&dev->mt76.sdio.stat_work); + mt76_worker_disable(&dev->mt76.sdio.stat_worker);
mt7921s_disable_irq(&dev->mt76); mt7921s_wfsys_reset(dev); @@ -115,6 +115,7 @@ int mt7921s_mac_reset(struct mt7921_dev *dev) mt76_worker_enable(&dev->mt76.sdio.txrx_worker); mt76_worker_enable(&dev->mt76.sdio.status_worker); mt76_worker_enable(&dev->mt76.sdio.net_worker); + mt76_worker_enable(&dev->mt76.sdio.stat_worker);
dev->fw_assert = false; clear_bit(MT76_MCU_RESET, &dev->mphy.state); diff --git a/drivers/net/wireless/mediatek/mt76/sdio.c b/drivers/net/wireless/mediatek/mt76/sdio.c index 176207f3177c..fc4fb9463564 100644 --- a/drivers/net/wireless/mediatek/mt76/sdio.c +++ b/drivers/net/wireless/mediatek/mt76/sdio.c @@ -481,21 +481,21 @@ static void mt76s_status_worker(struct mt76_worker *w) if (dev->drv->tx_status_data && ndata_frames > 0 && !test_and_set_bit(MT76_READING_STATS, &dev->phy.state) && !test_bit(MT76_STATE_SUSPEND, &dev->phy.state)) - ieee80211_queue_work(dev->hw, &dev->sdio.stat_work); + mt76_worker_schedule(&sdio->stat_worker); } while (nframes > 0);
if (resched) mt76_worker_schedule(&dev->tx_worker); }
-static void mt76s_tx_status_data(struct work_struct *work) +static void mt76s_tx_status_data(struct mt76_worker *worker) { struct mt76_sdio *sdio; struct mt76_dev *dev; u8 update = 1; u16 count = 0;
- sdio = container_of(work, struct mt76_sdio, stat_work); + sdio = container_of(worker, struct mt76_sdio, stat_worker); dev = container_of(sdio, struct mt76_dev, sdio);
while (true) { @@ -508,7 +508,7 @@ static void mt76s_tx_status_data(struct work_struct *work) }
if (count && test_bit(MT76_STATE_RUNNING, &dev->phy.state)) - ieee80211_queue_work(dev->hw, &sdio->stat_work); + mt76_worker_schedule(&sdio->status_worker); else clear_bit(MT76_READING_STATS, &dev->phy.state); } @@ -600,8 +600,8 @@ void mt76s_deinit(struct mt76_dev *dev) mt76_worker_teardown(&sdio->txrx_worker); mt76_worker_teardown(&sdio->status_worker); mt76_worker_teardown(&sdio->net_worker); + mt76_worker_teardown(&sdio->stat_worker);
- cancel_work_sync(&sdio->stat_work); clear_bit(MT76_READING_STATS, &dev->phy.state);
mt76_tx_status_check(dev, true); @@ -644,10 +644,14 @@ int mt76s_init(struct mt76_dev *dev, struct sdio_func *func, if (err) return err;
+ err = mt76_worker_setup(dev->hw, &sdio->stat_worker, mt76s_tx_status_data, + "sdio-sta"); + if (err) + return err; + sched_set_fifo_low(sdio->status_worker.task); sched_set_fifo_low(sdio->net_worker.task); - - INIT_WORK(&sdio->stat_work, mt76s_tx_status_data); + sched_set_fifo_low(sdio->stat_worker.task);
dev->queue_ops = &sdio_queue_ops; dev->bus = bus_ops; diff --git a/drivers/net/wireless/purelifi/plfxlc/usb.c b/drivers/net/wireless/purelifi/plfxlc/usb.c index 76d0a778636a..311676c1ece0 100644 --- a/drivers/net/wireless/purelifi/plfxlc/usb.c +++ b/drivers/net/wireless/purelifi/plfxlc/usb.c @@ -493,9 +493,12 @@ int plfxlc_usb_wreq_async(struct plfxlc_usb *usb, const u8 *buffer, void *context) { struct usb_device *udev = interface_to_usbdev(usb->ez_usb); - struct urb *urb = usb_alloc_urb(0, GFP_ATOMIC); + struct urb *urb; int r;
+ urb = usb_alloc_urb(0, GFP_ATOMIC); + if (!urb) + return -ENOMEM; usb_fill_bulk_urb(urb, udev, usb_sndbulkpipe(udev, EP_DATA_OUT), (void *)buffer, buffer_len, complete_fn, context);
diff --git a/drivers/net/wireless/realtek/rtlwifi/pci.c b/drivers/net/wireless/realtek/rtlwifi/pci.c index ca79f652fef3..6116c1bec155 100644 --- a/drivers/net/wireless/realtek/rtlwifi/pci.c +++ b/drivers/net/wireless/realtek/rtlwifi/pci.c @@ -164,21 +164,29 @@ static bool _rtl_pci_platform_switch_device_pci_aspm( struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw)); struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
+ value &= PCI_EXP_LNKCTL_ASPMC; + if (rtlhal->hw_type != HARDWARE_TYPE_RTL8192SE) - value |= 0x40; + value |= PCI_EXP_LNKCTL_CCC;
- pci_write_config_byte(rtlpci->pdev, 0x80, value); + pcie_capability_clear_and_set_word(rtlpci->pdev, PCI_EXP_LNKCTL, + PCI_EXP_LNKCTL_ASPMC | value, + value);
return false; }
-/*When we set 0x01 to enable clk request. Set 0x0 to disable clk req.*/ -static void _rtl_pci_switch_clk_req(struct ieee80211_hw *hw, u8 value) +/* @value is PCI_EXP_LNKCTL_CLKREQ_EN or 0 to enable/disable clk request. */ +static void _rtl_pci_switch_clk_req(struct ieee80211_hw *hw, u16 value) { struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw)); struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
- pci_write_config_byte(rtlpci->pdev, 0x81, value); + value &= PCI_EXP_LNKCTL_CLKREQ_EN; + + pcie_capability_clear_and_set_word(rtlpci->pdev, PCI_EXP_LNKCTL, + PCI_EXP_LNKCTL_CLKREQ_EN, + value);
if (rtlhal->hw_type == HARDWARE_TYPE_RTL8192SE) udelay(100); @@ -192,11 +200,8 @@ static void rtl_pci_disable_aspm(struct ieee80211_hw *hw) struct rtl_ps_ctl *ppsc = rtl_psc(rtl_priv(hw)); struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw)); u8 pcibridge_vendor = pcipriv->ndis_adapter.pcibridge_vendor; - u8 num4bytes = pcipriv->ndis_adapter.num4bytes; /*Retrieve original configuration settings. */ u8 linkctrl_reg = pcipriv->ndis_adapter.linkctrl_reg; - u16 pcibridge_linkctrlreg = pcipriv->ndis_adapter. - pcibridge_linkctrlreg; u16 aspmlevel = 0; u8 tmp_u1b = 0;
@@ -221,16 +226,8 @@ static void rtl_pci_disable_aspm(struct ieee80211_hw *hw) /*Set corresponding value. */ aspmlevel |= BIT(0) | BIT(1); linkctrl_reg &= ~aspmlevel; - pcibridge_linkctrlreg &= ~(BIT(0) | BIT(1));
_rtl_pci_platform_switch_device_pci_aspm(hw, linkctrl_reg); - udelay(50); - - /*4 Disable Pci Bridge ASPM */ - pci_write_config_byte(rtlpci->pdev, (num4bytes << 2), - pcibridge_linkctrlreg); - - udelay(50); }
/*Enable RTL8192SE ASPM & Enable Pci Bridge ASPM for @@ -245,9 +242,7 @@ static void rtl_pci_enable_aspm(struct ieee80211_hw *hw) struct rtl_ps_ctl *ppsc = rtl_psc(rtl_priv(hw)); struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw)); u8 pcibridge_vendor = pcipriv->ndis_adapter.pcibridge_vendor; - u8 num4bytes = pcipriv->ndis_adapter.num4bytes; u16 aspmlevel; - u8 u_pcibridge_aspmsetting; u8 u_device_aspmsetting;
if (!ppsc->support_aspm) @@ -259,25 +254,6 @@ static void rtl_pci_enable_aspm(struct ieee80211_hw *hw) return; }
- /*4 Enable Pci Bridge ASPM */ - - u_pcibridge_aspmsetting = - pcipriv->ndis_adapter.pcibridge_linkctrlreg | - rtlpci->const_hostpci_aspm_setting; - - if (pcibridge_vendor == PCI_BRIDGE_VENDOR_INTEL) - u_pcibridge_aspmsetting &= ~BIT(0); - - pci_write_config_byte(rtlpci->pdev, (num4bytes << 2), - u_pcibridge_aspmsetting); - - rtl_dbg(rtlpriv, COMP_INIT, DBG_LOUD, - "PlatformEnableASPM(): Write reg[%x] = %x\n", - (pcipriv->ndis_adapter.pcibridge_pciehdr_offset + 0x10), - u_pcibridge_aspmsetting); - - udelay(50); - /*Get ASPM level (with/without Clock Req) */ aspmlevel = rtlpci->const_devicepci_aspm_setting; u_device_aspmsetting = pcipriv->ndis_adapter.linkctrl_reg; @@ -291,7 +267,8 @@ static void rtl_pci_enable_aspm(struct ieee80211_hw *hw)
if (ppsc->reg_rfps_level & RT_RF_OFF_LEVL_CLK_REQ) { _rtl_pci_switch_clk_req(hw, (ppsc->reg_rfps_level & - RT_RF_OFF_LEVL_CLK_REQ) ? 1 : 0); + RT_RF_OFF_LEVL_CLK_REQ) ? + PCI_EXP_LNKCTL_CLKREQ_EN : 0); RT_SET_PS_LEVEL(ppsc, RT_RF_OFF_LEVL_CLK_REQ); } udelay(100); @@ -358,22 +335,6 @@ static bool rtl_pci_check_buddy_priv(struct ieee80211_hw *hw, return tpriv != NULL; }
-static void rtl_pci_get_linkcontrol_field(struct ieee80211_hw *hw) -{ - struct rtl_pci_priv *pcipriv = rtl_pcipriv(hw); - struct rtl_pci *rtlpci = rtl_pcidev(pcipriv); - u8 capabilityoffset = pcipriv->ndis_adapter.pcibridge_pciehdr_offset; - u8 linkctrl_reg; - u8 num4bbytes; - - num4bbytes = (capabilityoffset + 0x10) / 4; - - /*Read Link Control Register */ - pci_read_config_byte(rtlpci->pdev, (num4bbytes << 2), &linkctrl_reg); - - pcipriv->ndis_adapter.pcibridge_linkctrlreg = linkctrl_reg; -} - static void rtl_pci_parse_configuration(struct pci_dev *pdev, struct ieee80211_hw *hw) { @@ -2033,12 +1994,6 @@ static bool _rtl_pci_find_adapter(struct pci_dev *pdev, PCI_SLOT(bridge_pdev->devfn); pcipriv->ndis_adapter.pcibridge_funcnum = PCI_FUNC(bridge_pdev->devfn); - pcipriv->ndis_adapter.pcibridge_pciehdr_offset = - pci_pcie_cap(bridge_pdev); - pcipriv->ndis_adapter.num4bytes = - (pcipriv->ndis_adapter.pcibridge_pciehdr_offset + 0x10) / 4; - - rtl_pci_get_linkcontrol_field(hw);
if (pcipriv->ndis_adapter.pcibridge_vendor == PCI_BRIDGE_VENDOR_AMD) { @@ -2055,13 +2010,11 @@ static bool _rtl_pci_find_adapter(struct pci_dev *pdev, pdev->vendor, pcipriv->ndis_adapter.linkctrl_reg);
rtl_dbg(rtlpriv, COMP_INIT, DBG_DMESG, - "pci_bridge busnumber:devnumber:funcnumber:vendor:pcie_cap:link_ctl_reg:amd %d:%d:%d:%x:%x:%x:%x\n", + "pci_bridge busnumber:devnumber:funcnumber:vendor:amd %d:%d:%d:%x:%x\n", pcipriv->ndis_adapter.pcibridge_busnum, pcipriv->ndis_adapter.pcibridge_devnum, pcipriv->ndis_adapter.pcibridge_funcnum, pcibridge_vendors[pcipriv->ndis_adapter.pcibridge_vendor], - pcipriv->ndis_adapter.pcibridge_pciehdr_offset, - pcipriv->ndis_adapter.pcibridge_linkctrlreg, pcipriv->ndis_adapter.amd_l1_patch);
rtl_pci_parse_configuration(pdev, hw); diff --git a/drivers/net/wireless/realtek/rtlwifi/pci.h b/drivers/net/wireless/realtek/rtlwifi/pci.h index 866861626a0a..d6307197dfea 100644 --- a/drivers/net/wireless/realtek/rtlwifi/pci.h +++ b/drivers/net/wireless/realtek/rtlwifi/pci.h @@ -236,11 +236,6 @@ struct mp_adapter { u16 pcibridge_vendorid; u16 pcibridge_deviceid;
- u8 num4bytes; - - u8 pcibridge_pciehdr_offset; - u8 pcibridge_linkctrlreg; - bool amd_l1_patch; };
diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8188ee/phy.c b/drivers/net/wireless/realtek/rtlwifi/rtl8188ee/phy.c index 12d0b3a87af7..0fab3a0c7d49 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8188ee/phy.c +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8188ee/phy.c @@ -16,12 +16,6 @@ static u32 _rtl88e_phy_rf_serial_read(struct ieee80211_hw *hw, static void _rtl88e_phy_rf_serial_write(struct ieee80211_hw *hw, enum radio_path rfpath, u32 offset, u32 data); -static u32 _rtl88e_phy_calculate_bit_shift(u32 bitmask) -{ - u32 i = ffs(bitmask); - - return i ? i - 1 : 32; -} static bool _rtl88e_phy_bb8188e_config_parafile(struct ieee80211_hw *hw); static bool _rtl88e_phy_config_mac_with_headerfile(struct ieee80211_hw *hw); static bool phy_config_bb_with_headerfile(struct ieee80211_hw *hw, @@ -51,7 +45,7 @@ u32 rtl88e_phy_query_bb_reg(struct ieee80211_hw *hw, u32 regaddr, u32 bitmask) rtl_dbg(rtlpriv, COMP_RF, DBG_TRACE, "regaddr(%#x), bitmask(%#x)\n", regaddr, bitmask); originalvalue = rtl_read_dword(rtlpriv, regaddr); - bitshift = _rtl88e_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); returnvalue = (originalvalue & bitmask) >> bitshift;
rtl_dbg(rtlpriv, COMP_RF, DBG_TRACE, @@ -74,7 +68,7 @@ void rtl88e_phy_set_bb_reg(struct ieee80211_hw *hw,
if (bitmask != MASKDWORD) { originalvalue = rtl_read_dword(rtlpriv, regaddr); - bitshift = _rtl88e_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); data = ((originalvalue & (~bitmask)) | (data << bitshift)); }
@@ -99,7 +93,7 @@ u32 rtl88e_phy_query_rf_reg(struct ieee80211_hw *hw,
original_value = _rtl88e_phy_rf_serial_read(hw, rfpath, regaddr); - bitshift = _rtl88e_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); readback_value = (original_value & bitmask) >> bitshift;
spin_unlock(&rtlpriv->locks.rf_lock); @@ -127,7 +121,7 @@ void rtl88e_phy_set_rf_reg(struct ieee80211_hw *hw, original_value = _rtl88e_phy_rf_serial_read(hw, rfpath, regaddr); - bitshift = _rtl88e_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); data = ((original_value & (~bitmask)) | (data << bitshift)); diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8192c/phy_common.c b/drivers/net/wireless/realtek/rtlwifi/rtl8192c/phy_common.c index 3d29c8dbb255..144ee780e1b6 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8192c/phy_common.c +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8192c/phy_common.c @@ -17,7 +17,7 @@ u32 rtl92c_phy_query_bb_reg(struct ieee80211_hw *hw, u32 regaddr, u32 bitmask) rtl_dbg(rtlpriv, COMP_RF, DBG_TRACE, "regaddr(%#x), bitmask(%#x)\n", regaddr, bitmask); originalvalue = rtl_read_dword(rtlpriv, regaddr); - bitshift = _rtl92c_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); returnvalue = (originalvalue & bitmask) >> bitshift;
rtl_dbg(rtlpriv, COMP_RF, DBG_TRACE, @@ -40,7 +40,7 @@ void rtl92c_phy_set_bb_reg(struct ieee80211_hw *hw,
if (bitmask != MASKDWORD) { originalvalue = rtl_read_dword(rtlpriv, regaddr); - bitshift = _rtl92c_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); data = ((originalvalue & (~bitmask)) | (data << bitshift)); }
@@ -143,14 +143,6 @@ void _rtl92c_phy_rf_serial_write(struct ieee80211_hw *hw, } EXPORT_SYMBOL(_rtl92c_phy_rf_serial_write);
-u32 _rtl92c_phy_calculate_bit_shift(u32 bitmask) -{ - u32 i = ffs(bitmask); - - return i ? i - 1 : 32; -} -EXPORT_SYMBOL(_rtl92c_phy_calculate_bit_shift); - static void _rtl92c_phy_bb_config_1t(struct ieee80211_hw *hw) { rtl_set_bbreg(hw, RFPGA0_TXINFO, 0x3, 0x2); diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8192c/phy_common.h b/drivers/net/wireless/realtek/rtlwifi/rtl8192c/phy_common.h index 75afa6253ad0..e64d377dfe9e 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8192c/phy_common.h +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8192c/phy_common.h @@ -196,7 +196,6 @@ bool rtl92c_phy_set_rf_power_state(struct ieee80211_hw *hw, void rtl92ce_phy_set_rf_on(struct ieee80211_hw *hw); void rtl92c_phy_set_io(struct ieee80211_hw *hw); void rtl92c_bb_block_on(struct ieee80211_hw *hw); -u32 _rtl92c_phy_calculate_bit_shift(u32 bitmask); long _rtl92c_phy_txpwr_idx_to_dbm(struct ieee80211_hw *hw, enum wireless_mode wirelessmode, u8 txpwridx); diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8192ce/phy.c b/drivers/net/wireless/realtek/rtlwifi/rtl8192ce/phy.c index da54e51badd3..fa70a7d5539f 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8192ce/phy.c +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8192ce/phy.c @@ -39,7 +39,7 @@ u32 rtl92c_phy_query_rf_reg(struct ieee80211_hw *hw, rfpath, regaddr); }
- bitshift = _rtl92c_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); readback_value = (original_value & bitmask) >> bitshift;
spin_unlock(&rtlpriv->locks.rf_lock); @@ -110,7 +110,7 @@ void rtl92ce_phy_set_rf_reg(struct ieee80211_hw *hw, original_value = _rtl92c_phy_rf_serial_read(hw, rfpath, regaddr); - bitshift = _rtl92c_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); data = ((original_value & (~bitmask)) | (data << bitshift)); @@ -122,7 +122,7 @@ void rtl92ce_phy_set_rf_reg(struct ieee80211_hw *hw, original_value = _rtl92c_phy_fw_rf_serial_read(hw, rfpath, regaddr); - bitshift = _rtl92c_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); data = ((original_value & (~bitmask)) | (data << bitshift)); diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8192ce/phy.h b/drivers/net/wireless/realtek/rtlwifi/rtl8192ce/phy.h index 7582a162bd11..c7a0d4c776f0 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8192ce/phy.h +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8192ce/phy.h @@ -94,7 +94,6 @@ u32 _rtl92c_phy_rf_serial_read(struct ieee80211_hw *hw, enum radio_path rfpath, u32 offset); u32 _rtl92c_phy_fw_rf_serial_read(struct ieee80211_hw *hw, enum radio_path rfpath, u32 offset); -u32 _rtl92c_phy_calculate_bit_shift(u32 bitmask); void _rtl92c_phy_rf_serial_write(struct ieee80211_hw *hw, enum radio_path rfpath, u32 offset, u32 data); void _rtl92c_phy_fw_rf_serial_write(struct ieee80211_hw *hw, diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8192cu/phy.c b/drivers/net/wireless/realtek/rtlwifi/rtl8192cu/phy.c index a8d9fe269f31..0b8cb7e61fd8 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8192cu/phy.c +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8192cu/phy.c @@ -32,7 +32,7 @@ u32 rtl92cu_phy_query_rf_reg(struct ieee80211_hw *hw, original_value = _rtl92c_phy_fw_rf_serial_read(hw, rfpath, regaddr); } - bitshift = _rtl92c_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); readback_value = (original_value & bitmask) >> bitshift; rtl_dbg(rtlpriv, COMP_RF, DBG_TRACE, "regaddr(%#x), rfpath(%#x), bitmask(%#x), original_value(%#x)\n", @@ -56,7 +56,7 @@ void rtl92cu_phy_set_rf_reg(struct ieee80211_hw *hw, original_value = _rtl92c_phy_rf_serial_read(hw, rfpath, regaddr); - bitshift = _rtl92c_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); data = ((original_value & (~bitmask)) | (data << bitshift)); @@ -67,7 +67,7 @@ void rtl92cu_phy_set_rf_reg(struct ieee80211_hw *hw, original_value = _rtl92c_phy_fw_rf_serial_read(hw, rfpath, regaddr); - bitshift = _rtl92c_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); data = ((original_value & (~bitmask)) | (data << bitshift)); diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8192de/phy.c b/drivers/net/wireless/realtek/rtlwifi/rtl8192de/phy.c index d18c092b6142..d835a27429f0 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8192de/phy.c +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8192de/phy.c @@ -169,13 +169,6 @@ static const u8 channel_all[59] = { 157, 159, 161, 163, 165 };
-static u32 _rtl92d_phy_calculate_bit_shift(u32 bitmask) -{ - u32 i = ffs(bitmask); - - return i ? i - 1 : 32; -} - u32 rtl92d_phy_query_bb_reg(struct ieee80211_hw *hw, u32 regaddr, u32 bitmask) { struct rtl_priv *rtlpriv = rtl_priv(hw); @@ -198,7 +191,7 @@ u32 rtl92d_phy_query_bb_reg(struct ieee80211_hw *hw, u32 regaddr, u32 bitmask) } else { originalvalue = rtl_read_dword(rtlpriv, regaddr); } - bitshift = _rtl92d_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); returnvalue = (originalvalue & bitmask) >> bitshift; rtl_dbg(rtlpriv, COMP_RF, DBG_TRACE, "BBR MASK=0x%x Addr[0x%x]=0x%x\n", @@ -230,7 +223,7 @@ void rtl92d_phy_set_bb_reg(struct ieee80211_hw *hw, dbi_direct); else originalvalue = rtl_read_dword(rtlpriv, regaddr); - bitshift = _rtl92d_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); data = ((originalvalue & (~bitmask)) | (data << bitshift)); } if (rtlhal->during_mac1init_radioa || rtlhal->during_mac0init_radiob) @@ -317,7 +310,7 @@ u32 rtl92d_phy_query_rf_reg(struct ieee80211_hw *hw, regaddr, rfpath, bitmask); spin_lock(&rtlpriv->locks.rf_lock); original_value = _rtl92d_phy_rf_serial_read(hw, rfpath, regaddr); - bitshift = _rtl92d_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); readback_value = (original_value & bitmask) >> bitshift; spin_unlock(&rtlpriv->locks.rf_lock); rtl_dbg(rtlpriv, COMP_RF, DBG_TRACE, @@ -343,7 +336,7 @@ void rtl92d_phy_set_rf_reg(struct ieee80211_hw *hw, enum radio_path rfpath, if (bitmask != RFREG_OFFSET_MASK) { original_value = _rtl92d_phy_rf_serial_read(hw, rfpath, regaddr); - bitshift = _rtl92d_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); data = ((original_value & (~bitmask)) | (data << bitshift)); } diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8192ee/phy.c b/drivers/net/wireless/realtek/rtlwifi/rtl8192ee/phy.c index cc0bcaf13e96..73ef602bfb01 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8192ee/phy.c +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8192ee/phy.c @@ -16,7 +16,6 @@ static u32 _rtl92ee_phy_rf_serial_read(struct ieee80211_hw *hw, static void _rtl92ee_phy_rf_serial_write(struct ieee80211_hw *hw, enum radio_path rfpath, u32 offset, u32 data); -static u32 _rtl92ee_phy_calculate_bit_shift(u32 bitmask); static bool _rtl92ee_phy_bb8192ee_config_parafile(struct ieee80211_hw *hw); static bool _rtl92ee_phy_config_mac_with_headerfile(struct ieee80211_hw *hw); static bool phy_config_bb_with_hdr_file(struct ieee80211_hw *hw, @@ -46,7 +45,7 @@ u32 rtl92ee_phy_query_bb_reg(struct ieee80211_hw *hw, u32 regaddr, u32 bitmask) rtl_dbg(rtlpriv, COMP_RF, DBG_TRACE, "regaddr(%#x), bitmask(%#x)\n", regaddr, bitmask); originalvalue = rtl_read_dword(rtlpriv, regaddr); - bitshift = _rtl92ee_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); returnvalue = (originalvalue & bitmask) >> bitshift;
rtl_dbg(rtlpriv, COMP_RF, DBG_TRACE, @@ -68,7 +67,7 @@ void rtl92ee_phy_set_bb_reg(struct ieee80211_hw *hw, u32 regaddr,
if (bitmask != MASKDWORD) { originalvalue = rtl_read_dword(rtlpriv, regaddr); - bitshift = _rtl92ee_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); data = ((originalvalue & (~bitmask)) | (data << bitshift)); }
@@ -92,7 +91,7 @@ u32 rtl92ee_phy_query_rf_reg(struct ieee80211_hw *hw, spin_lock(&rtlpriv->locks.rf_lock);
original_value = _rtl92ee_phy_rf_serial_read(hw , rfpath, regaddr); - bitshift = _rtl92ee_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); readback_value = (original_value & bitmask) >> bitshift;
spin_unlock(&rtlpriv->locks.rf_lock); @@ -119,7 +118,7 @@ void rtl92ee_phy_set_rf_reg(struct ieee80211_hw *hw,
if (bitmask != RFREG_OFFSET_MASK) { original_value = _rtl92ee_phy_rf_serial_read(hw, rfpath, addr); - bitshift = _rtl92ee_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); data = (original_value & (~bitmask)) | (data << bitshift); }
@@ -201,13 +200,6 @@ static void _rtl92ee_phy_rf_serial_write(struct ieee80211_hw *hw, pphyreg->rf3wire_offset, data_and_addr); }
-static u32 _rtl92ee_phy_calculate_bit_shift(u32 bitmask) -{ - u32 i = ffs(bitmask); - - return i ? i - 1 : 32; -} - bool rtl92ee_phy_mac_config(struct ieee80211_hw *hw) { return _rtl92ee_phy_config_mac_with_headerfile(hw); diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8192se/phy.c b/drivers/net/wireless/realtek/rtlwifi/rtl8192se/phy.c index aaa004d4d6d0..0e2b9698088b 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8192se/phy.c +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8192se/phy.c @@ -14,13 +14,6 @@ #include "hw.h" #include "table.h"
-static u32 _rtl92s_phy_calculate_bit_shift(u32 bitmask) -{ - u32 i = ffs(bitmask); - - return i ? i - 1 : 32; -} - u32 rtl92s_phy_query_bb_reg(struct ieee80211_hw *hw, u32 regaddr, u32 bitmask) { struct rtl_priv *rtlpriv = rtl_priv(hw); @@ -30,7 +23,7 @@ u32 rtl92s_phy_query_bb_reg(struct ieee80211_hw *hw, u32 regaddr, u32 bitmask) regaddr, bitmask);
originalvalue = rtl_read_dword(rtlpriv, regaddr); - bitshift = _rtl92s_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); returnvalue = (originalvalue & bitmask) >> bitshift;
rtl_dbg(rtlpriv, COMP_RF, DBG_TRACE, "BBR MASK=0x%x Addr[0x%x]=0x%x\n", @@ -52,7 +45,7 @@ void rtl92s_phy_set_bb_reg(struct ieee80211_hw *hw, u32 regaddr, u32 bitmask,
if (bitmask != MASKDWORD) { originalvalue = rtl_read_dword(rtlpriv, regaddr); - bitshift = _rtl92s_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); data = ((originalvalue & (~bitmask)) | (data << bitshift)); }
@@ -160,7 +153,7 @@ u32 rtl92s_phy_query_rf_reg(struct ieee80211_hw *hw, enum radio_path rfpath,
original_value = _rtl92s_phy_rf_serial_read(hw, rfpath, regaddr);
- bitshift = _rtl92s_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); readback_value = (original_value & bitmask) >> bitshift;
spin_unlock(&rtlpriv->locks.rf_lock); @@ -191,7 +184,7 @@ void rtl92s_phy_set_rf_reg(struct ieee80211_hw *hw, enum radio_path rfpath, if (bitmask != RFREG_OFFSET_MASK) { original_value = _rtl92s_phy_rf_serial_read(hw, rfpath, regaddr); - bitshift = _rtl92s_phy_calculate_bit_shift(bitmask); + bitshift = calculate_bit_shift(bitmask); data = ((original_value & (~bitmask)) | (data << bitshift)); }
diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8821ae/phy.c b/drivers/net/wireless/realtek/rtlwifi/rtl8821ae/phy.c index 5323ead30db0..fa1839d8ee55 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8821ae/phy.c +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8821ae/phy.c @@ -29,9 +29,10 @@ static void _rtl8821ae_phy_rf_serial_write(struct ieee80211_hw *hw, u32 data); static u32 _rtl8821ae_phy_calculate_bit_shift(u32 bitmask) { - u32 i = ffs(bitmask); + if (WARN_ON_ONCE(!bitmask)) + return 0;
- return i ? i - 1 : 32; + return __ffs(bitmask); } static bool _rtl8821ae_phy_bb8821a_config_parafile(struct ieee80211_hw *hw); /*static bool _rtl8812ae_phy_config_mac_with_headerfile(struct ieee80211_hw *hw);*/ diff --git a/drivers/net/wireless/realtek/rtlwifi/wifi.h b/drivers/net/wireless/realtek/rtlwifi/wifi.h index 31f9e9e5c680..0bac788ccd6e 100644 --- a/drivers/net/wireless/realtek/rtlwifi/wifi.h +++ b/drivers/net/wireless/realtek/rtlwifi/wifi.h @@ -3105,4 +3105,11 @@ static inline struct ieee80211_sta *rtl_find_sta(struct ieee80211_hw *hw, return ieee80211_find_sta(mac->vif, mac_addr); }
+static inline u32 calculate_bit_shift(u32 bitmask) +{ + if (WARN_ON_ONCE(!bitmask)) + return 0; + + return __ffs(bitmask); +} #endif diff --git a/drivers/net/wireless/realtek/rtw88/mac80211.c b/drivers/net/wireless/realtek/rtw88/mac80211.c index fabca307867a..0970d6bcba43 100644 --- a/drivers/net/wireless/realtek/rtw88/mac80211.c +++ b/drivers/net/wireless/realtek/rtw88/mac80211.c @@ -266,9 +266,9 @@ static void rtw_ops_configure_filter(struct ieee80211_hw *hw,
if (changed_flags & FIF_ALLMULTI) { if (*new_flags & FIF_ALLMULTI) - rtwdev->hal.rcr |= BIT_AM | BIT_AB; + rtwdev->hal.rcr |= BIT_AM; else - rtwdev->hal.rcr &= ~(BIT_AM | BIT_AB); + rtwdev->hal.rcr &= ~(BIT_AM); } if (changed_flags & FIF_FCSFAIL) { if (*new_flags & FIF_FCSFAIL) diff --git a/drivers/net/xen-netback/netback.c b/drivers/net/xen-netback/netback.c index c3a8d78a41a7..271604098574 100644 --- a/drivers/net/xen-netback/netback.c +++ b/drivers/net/xen-netback/netback.c @@ -463,12 +463,25 @@ static void xenvif_get_requests(struct xenvif_queue *queue, }
for (shinfo->nr_frags = 0; nr_slots > 0 && shinfo->nr_frags < MAX_SKB_FRAGS; - shinfo->nr_frags++, gop++, nr_slots--) { + nr_slots--) { + if (unlikely(!txp->size)) { + unsigned long flags; + + spin_lock_irqsave(&queue->response_lock, flags); + make_tx_response(queue, txp, 0, XEN_NETIF_RSP_OKAY); + push_tx_responses(queue); + spin_unlock_irqrestore(&queue->response_lock, flags); + ++txp; + continue; + } + index = pending_index(queue->pending_cons++); pending_idx = queue->pending_ring[index]; xenvif_tx_create_map_op(queue, pending_idx, txp, txp == first ? extra_count : 0, gop); frag_set_pending_idx(&frags[shinfo->nr_frags], pending_idx); + ++shinfo->nr_frags; + ++gop;
if (txp == first) txp = txfrags; @@ -481,20 +494,39 @@ static void xenvif_get_requests(struct xenvif_queue *queue, shinfo = skb_shinfo(nskb); frags = shinfo->frags;
- for (shinfo->nr_frags = 0; shinfo->nr_frags < nr_slots; - shinfo->nr_frags++, txp++, gop++) { + for (shinfo->nr_frags = 0; shinfo->nr_frags < nr_slots; ++txp) { + if (unlikely(!txp->size)) { + unsigned long flags; + + spin_lock_irqsave(&queue->response_lock, flags); + make_tx_response(queue, txp, 0, + XEN_NETIF_RSP_OKAY); + push_tx_responses(queue); + spin_unlock_irqrestore(&queue->response_lock, + flags); + continue; + } + index = pending_index(queue->pending_cons++); pending_idx = queue->pending_ring[index]; xenvif_tx_create_map_op(queue, pending_idx, txp, 0, gop); frag_set_pending_idx(&frags[shinfo->nr_frags], pending_idx); + ++shinfo->nr_frags; + ++gop; }
- skb_shinfo(skb)->frag_list = nskb; - } else if (nskb) { + if (shinfo->nr_frags) { + skb_shinfo(skb)->frag_list = nskb; + nskb = NULL; + } + } + + if (nskb) { /* A frag_list skb was allocated but it is no longer needed - * because enough slots were converted to copy ops above. + * because enough slots were converted to copy ops above or some + * were empty. */ kfree_skb(nskb); } diff --git a/drivers/nvme/target/tcp.c b/drivers/nvme/target/tcp.c index 355d80323b83..ce42afe8f64e 100644 --- a/drivers/nvme/target/tcp.c +++ b/drivers/nvme/target/tcp.c @@ -18,6 +18,7 @@ #include "nvmet.h"
#define NVMET_TCP_DEF_INLINE_DATA_SIZE (4 * PAGE_SIZE) +#define NVMET_TCP_MAXH2CDATA 0x400000 /* 16M arbitrary limit */
/* Define the socket priority to use for connections were it is desirable * that the NIC consider performing optimized packet processing or filtering. @@ -861,7 +862,7 @@ static int nvmet_tcp_handle_icreq(struct nvmet_tcp_queue *queue) icresp->hdr.pdo = 0; icresp->hdr.plen = cpu_to_le32(icresp->hdr.hlen); icresp->pfv = cpu_to_le16(NVME_TCP_PFV_1_0); - icresp->maxdata = cpu_to_le32(0x400000); /* 16M arbitrary limit */ + icresp->maxdata = cpu_to_le32(NVMET_TCP_MAXH2CDATA); icresp->cpda = 0; if (queue->hdr_digest) icresp->digest |= NVME_TCP_HDR_DIGEST_ENABLE; @@ -914,6 +915,7 @@ static int nvmet_tcp_handle_h2c_data_pdu(struct nvmet_tcp_queue *queue) { struct nvme_tcp_data_pdu *data = &queue->pdu.data; struct nvmet_tcp_cmd *cmd; + unsigned int exp_data_len;
if (likely(queue->nr_cmds)) { if (unlikely(data->ttag >= queue->nr_cmds)) { @@ -932,12 +934,24 @@ static int nvmet_tcp_handle_h2c_data_pdu(struct nvmet_tcp_queue *queue) data->ttag, le32_to_cpu(data->data_offset), cmd->rbytes_done); /* FIXME: use path and transport errors */ - nvmet_req_complete(&cmd->req, - NVME_SC_INVALID_FIELD | NVME_SC_DNR); + nvmet_tcp_fatal_error(queue); return -EPROTO; }
+ exp_data_len = le32_to_cpu(data->hdr.plen) - + nvmet_tcp_hdgst_len(queue) - + nvmet_tcp_ddgst_len(queue) - + sizeof(*data); + cmd->pdu_len = le32_to_cpu(data->data_length); + if (unlikely(cmd->pdu_len != exp_data_len || + cmd->pdu_len == 0 || + cmd->pdu_len > NVMET_TCP_MAXH2CDATA)) { + pr_err("H2CData PDU len %u is invalid\n", cmd->pdu_len); + /* FIXME: use proper transport errors */ + nvmet_tcp_fatal_error(queue); + return -EPROTO; + } cmd->pdu_recv = 0; nvmet_tcp_build_pdu_iovec(cmd); queue->cmd = cmd; diff --git a/drivers/nvme/target/trace.h b/drivers/nvme/target/trace.h index 6109b3806b12..974d99d47f51 100644 --- a/drivers/nvme/target/trace.h +++ b/drivers/nvme/target/trace.h @@ -53,8 +53,7 @@ static inline void __assign_req_name(char *name, struct nvmet_req *req) return; }
- strncpy(name, req->ns->device_path, - min_t(size_t, DISK_NAME_LEN, strlen(req->ns->device_path))); + strscpy_pad(name, req->ns->device_path, DISK_NAME_LEN); } #endif
@@ -85,7 +84,7 @@ TRACE_EVENT(nvmet_req_init, __entry->flags = cmd->common.flags; __entry->nsid = le32_to_cpu(cmd->common.nsid); __entry->metadata = le64_to_cpu(cmd->common.metadata); - memcpy(__entry->cdw10, &cmd->common.cdw10, + memcpy(__entry->cdw10, &cmd->common.cdws, sizeof(__entry->cdw10)); ), TP_printk("nvmet%s: %sqid=%d, cmdid=%u, nsid=%u, flags=%#x, " diff --git a/drivers/of/base.c b/drivers/of/base.c index d5a5c35eba72..f849bbb9ef8c 100644 --- a/drivers/of/base.c +++ b/drivers/of/base.c @@ -1646,6 +1646,7 @@ int of_parse_phandle_with_args_map(const struct device_node *np, out_args->np = new; of_node_put(cur); cur = new; + new = NULL; } put: of_node_put(cur); diff --git a/drivers/of/unittest-data/tests-phandle.dtsi b/drivers/of/unittest-data/tests-phandle.dtsi index 6b33be4c4416..aa0d7027ffa6 100644 --- a/drivers/of/unittest-data/tests-phandle.dtsi +++ b/drivers/of/unittest-data/tests-phandle.dtsi @@ -38,6 +38,13 @@ provider4: provider4 { phandle-map-pass-thru = <0x0 0xf0>; };
+ provider5: provider5 { + #phandle-cells = <2>; + phandle-map = <2 7 &provider4 2 3>; + phandle-map-mask = <0xff 0xf>; + phandle-map-pass-thru = <0x0 0xf0>; + }; + consumer-a { phandle-list = <&provider1 1>, <&provider2 2 0>, @@ -64,7 +71,8 @@ consumer-b { <&provider4 4 0x100>, <&provider4 0 0x61>, <&provider0>, - <&provider4 19 0x20>; + <&provider4 19 0x20>, + <&provider5 2 7>; phandle-list-bad-phandle = <12345678 0 0>; phandle-list-bad-args = <&provider2 1 0>, <&provider4 0>; diff --git a/drivers/of/unittest.c b/drivers/of/unittest.c index edd2342598e4..e541a8960f1d 100644 --- a/drivers/of/unittest.c +++ b/drivers/of/unittest.c @@ -448,6 +448,9 @@ static void __init of_unittest_parse_phandle_with_args(void)
unittest(passed, "index %i - data error on node %pOF rc=%i\n", i, args.np, rc); + + if (rc == 0) + of_node_put(args.np); }
/* Check for missing list property */ @@ -537,8 +540,9 @@ static void __init of_unittest_parse_phandle_with_args(void)
static void __init of_unittest_parse_phandle_with_args_map(void) { - struct device_node *np, *p0, *p1, *p2, *p3; + struct device_node *np, *p[6] = {}; struct of_phandle_args args; + unsigned int prefs[6]; int i, rc;
np = of_find_node_by_path("/testcase-data/phandle-tests/consumer-b"); @@ -547,34 +551,24 @@ static void __init of_unittest_parse_phandle_with_args_map(void) return; }
- p0 = of_find_node_by_path("/testcase-data/phandle-tests/provider0"); - if (!p0) { - pr_err("missing testcase data\n"); - return; - } - - p1 = of_find_node_by_path("/testcase-data/phandle-tests/provider1"); - if (!p1) { - pr_err("missing testcase data\n"); - return; - } - - p2 = of_find_node_by_path("/testcase-data/phandle-tests/provider2"); - if (!p2) { - pr_err("missing testcase data\n"); - return; - } - - p3 = of_find_node_by_path("/testcase-data/phandle-tests/provider3"); - if (!p3) { - pr_err("missing testcase data\n"); - return; + p[0] = of_find_node_by_path("/testcase-data/phandle-tests/provider0"); + p[1] = of_find_node_by_path("/testcase-data/phandle-tests/provider1"); + p[2] = of_find_node_by_path("/testcase-data/phandle-tests/provider2"); + p[3] = of_find_node_by_path("/testcase-data/phandle-tests/provider3"); + p[4] = of_find_node_by_path("/testcase-data/phandle-tests/provider4"); + p[5] = of_find_node_by_path("/testcase-data/phandle-tests/provider5"); + for (i = 0; i < ARRAY_SIZE(p); ++i) { + if (!p[i]) { + pr_err("missing testcase data\n"); + return; + } + prefs[i] = kref_read(&p[i]->kobj.kref); }
rc = of_count_phandle_with_args(np, "phandle-list", "#phandle-cells"); - unittest(rc == 7, "of_count_phandle_with_args() returned %i, expected 7\n", rc); + unittest(rc == 8, "of_count_phandle_with_args() returned %i, expected 8\n", rc);
- for (i = 0; i < 8; i++) { + for (i = 0; i < 9; i++) { bool passed = true;
memset(&args, 0, sizeof(args)); @@ -585,13 +579,13 @@ static void __init of_unittest_parse_phandle_with_args_map(void) switch (i) { case 0: passed &= !rc; - passed &= (args.np == p1); + passed &= (args.np == p[1]); passed &= (args.args_count == 1); passed &= (args.args[0] == 1); break; case 1: passed &= !rc; - passed &= (args.np == p3); + passed &= (args.np == p[3]); passed &= (args.args_count == 3); passed &= (args.args[0] == 2); passed &= (args.args[1] == 5); @@ -602,28 +596,36 @@ static void __init of_unittest_parse_phandle_with_args_map(void) break; case 3: passed &= !rc; - passed &= (args.np == p0); + passed &= (args.np == p[0]); passed &= (args.args_count == 0); break; case 4: passed &= !rc; - passed &= (args.np == p1); + passed &= (args.np == p[1]); passed &= (args.args_count == 1); passed &= (args.args[0] == 3); break; case 5: passed &= !rc; - passed &= (args.np == p0); + passed &= (args.np == p[0]); passed &= (args.args_count == 0); break; case 6: passed &= !rc; - passed &= (args.np == p2); + passed &= (args.np == p[2]); passed &= (args.args_count == 2); passed &= (args.args[0] == 15); passed &= (args.args[1] == 0x20); break; case 7: + passed &= !rc; + passed &= (args.np == p[3]); + passed &= (args.args_count == 3); + passed &= (args.args[0] == 2); + passed &= (args.args[1] == 5); + passed &= (args.args[2] == 3); + break; + case 8: passed &= (rc == -ENOENT); break; default: @@ -632,6 +634,9 @@ static void __init of_unittest_parse_phandle_with_args_map(void)
unittest(passed, "index %i - data error on node %s rc=%i\n", i, args.np->full_name, rc); + + if (rc == 0) + of_node_put(args.np); }
/* Check for missing list property */ @@ -678,6 +683,13 @@ static void __init of_unittest_parse_phandle_with_args_map(void) "OF: /testcase-data/phandle-tests/consumer-b: #phandle-cells = 2 found 1");
unittest(rc == -EINVAL, "expected:%i got:%i\n", -EINVAL, rc); + + for (i = 0; i < ARRAY_SIZE(p); ++i) { + unittest(prefs[i] == kref_read(&p[i]->kobj.kref), + "provider%d: expected:%d got:%d\n", + i, prefs[i], kref_read(&p[i]->kobj.kref)); + of_node_put(p[i]); + } }
static void __init of_unittest_property_string(void) diff --git a/drivers/pci/controller/dwc/pci-keystone.c b/drivers/pci/controller/dwc/pci-keystone.c index d2634dafb68e..7ecad72cff7e 100644 --- a/drivers/pci/controller/dwc/pci-keystone.c +++ b/drivers/pci/controller/dwc/pci-keystone.c @@ -1219,7 +1219,16 @@ static int ks_pcie_probe(struct platform_device *pdev) goto err_link; }
+ /* Obtain references to the PHYs */ + for (i = 0; i < num_lanes; i++) + phy_pm_runtime_get_sync(ks_pcie->phy[i]); + ret = ks_pcie_enable_phy(ks_pcie); + + /* Release references to the PHYs */ + for (i = 0; i < num_lanes; i++) + phy_pm_runtime_put_sync(ks_pcie->phy[i]); + if (ret) { dev_err(dev, "failed to enable phy\n"); goto err_link; diff --git a/drivers/pci/controller/dwc/pcie-designware-ep.c b/drivers/pci/controller/dwc/pcie-designware-ep.c index 83ddb190292e..59c164b5c64a 100644 --- a/drivers/pci/controller/dwc/pcie-designware-ep.c +++ b/drivers/pci/controller/dwc/pcie-designware-ep.c @@ -600,6 +600,7 @@ int dw_pcie_ep_raise_msix_irq(struct dw_pcie_ep *ep, u8 func_no, }
aligned_offset = msg_addr & (epc->mem->window.page_size - 1); + msg_addr &= ~aligned_offset; ret = dw_pcie_ep_map_addr(epc, func_no, 0, ep->msi_mem_phys, msg_addr, epc->mem->window.page_size); if (ret) diff --git a/drivers/pci/controller/pcie-mediatek-gen3.c b/drivers/pci/controller/pcie-mediatek-gen3.c index b8612ce5f4d0..40c38ca5a42e 100644 --- a/drivers/pci/controller/pcie-mediatek-gen3.c +++ b/drivers/pci/controller/pcie-mediatek-gen3.c @@ -245,35 +245,60 @@ static int mtk_pcie_set_trans_table(struct mtk_gen3_pcie *pcie, resource_size_t cpu_addr, resource_size_t pci_addr, resource_size_t size, - unsigned long type, int num) + unsigned long type, int *num) { + resource_size_t remaining = size; + resource_size_t table_size; + resource_size_t addr_align; + const char *range_type; void __iomem *table; u32 val;
- if (num >= PCIE_MAX_TRANS_TABLES) { - dev_err(pcie->dev, "not enough translate table for addr: %#llx, limited to [%d]\n", - (unsigned long long)cpu_addr, PCIE_MAX_TRANS_TABLES); - return -ENODEV; - } + while (remaining && (*num < PCIE_MAX_TRANS_TABLES)) { + /* Table size needs to be a power of 2 */ + table_size = BIT(fls(remaining) - 1); + + if (cpu_addr > 0) { + addr_align = BIT(ffs(cpu_addr) - 1); + table_size = min(table_size, addr_align); + } + + /* Minimum size of translate table is 4KiB */ + if (table_size < 0x1000) { + dev_err(pcie->dev, "illegal table size %#llx\n", + (unsigned long long)table_size); + return -EINVAL; + }
- table = pcie->base + PCIE_TRANS_TABLE_BASE_REG + - num * PCIE_ATR_TLB_SET_OFFSET; + table = pcie->base + PCIE_TRANS_TABLE_BASE_REG + *num * PCIE_ATR_TLB_SET_OFFSET; + writel_relaxed(lower_32_bits(cpu_addr) | PCIE_ATR_SIZE(fls(table_size) - 1), table); + writel_relaxed(upper_32_bits(cpu_addr), table + PCIE_ATR_SRC_ADDR_MSB_OFFSET); + writel_relaxed(lower_32_bits(pci_addr), table + PCIE_ATR_TRSL_ADDR_LSB_OFFSET); + writel_relaxed(upper_32_bits(pci_addr), table + PCIE_ATR_TRSL_ADDR_MSB_OFFSET);
- writel_relaxed(lower_32_bits(cpu_addr) | PCIE_ATR_SIZE(fls(size) - 1), - table); - writel_relaxed(upper_32_bits(cpu_addr), - table + PCIE_ATR_SRC_ADDR_MSB_OFFSET); - writel_relaxed(lower_32_bits(pci_addr), - table + PCIE_ATR_TRSL_ADDR_LSB_OFFSET); - writel_relaxed(upper_32_bits(pci_addr), - table + PCIE_ATR_TRSL_ADDR_MSB_OFFSET); + if (type == IORESOURCE_IO) { + val = PCIE_ATR_TYPE_IO | PCIE_ATR_TLP_TYPE_IO; + range_type = "IO"; + } else { + val = PCIE_ATR_TYPE_MEM | PCIE_ATR_TLP_TYPE_MEM; + range_type = "MEM"; + }
- if (type == IORESOURCE_IO) - val = PCIE_ATR_TYPE_IO | PCIE_ATR_TLP_TYPE_IO; - else - val = PCIE_ATR_TYPE_MEM | PCIE_ATR_TLP_TYPE_MEM; + writel_relaxed(val, table + PCIE_ATR_TRSL_PARAM_OFFSET);
- writel_relaxed(val, table + PCIE_ATR_TRSL_PARAM_OFFSET); + dev_dbg(pcie->dev, "set %s trans window[%d]: cpu_addr = %#llx, pci_addr = %#llx, size = %#llx\n", + range_type, *num, (unsigned long long)cpu_addr, + (unsigned long long)pci_addr, (unsigned long long)table_size); + + cpu_addr += table_size; + pci_addr += table_size; + remaining -= table_size; + (*num)++; + } + + if (remaining) + dev_warn(pcie->dev, "not enough translate table for addr: %#llx, limited to [%d]\n", + (unsigned long long)cpu_addr, PCIE_MAX_TRANS_TABLES);
return 0; } @@ -380,30 +405,20 @@ static int mtk_pcie_startup_port(struct mtk_gen3_pcie *pcie) resource_size_t cpu_addr; resource_size_t pci_addr; resource_size_t size; - const char *range_type;
- if (type == IORESOURCE_IO) { + if (type == IORESOURCE_IO) cpu_addr = pci_pio_to_address(res->start); - range_type = "IO"; - } else if (type == IORESOURCE_MEM) { + else if (type == IORESOURCE_MEM) cpu_addr = res->start; - range_type = "MEM"; - } else { + else continue; - }
pci_addr = res->start - entry->offset; size = resource_size(res); err = mtk_pcie_set_trans_table(pcie, cpu_addr, pci_addr, size, - type, table_index); + type, &table_index); if (err) return err; - - dev_dbg(pcie->dev, "set %s trans window[%d]: cpu_addr = %#llx, pci_addr = %#llx, size = %#llx\n", - range_type, table_index, (unsigned long long)cpu_addr, - (unsigned long long)pci_addr, (unsigned long long)size); - - table_index++; }
return 0; diff --git a/drivers/pci/controller/pcie-mediatek.c b/drivers/pci/controller/pcie-mediatek.c index ae5ad05ddc1d..11bdef206d12 100644 --- a/drivers/pci/controller/pcie-mediatek.c +++ b/drivers/pci/controller/pcie-mediatek.c @@ -617,12 +617,18 @@ static void mtk_pcie_intr_handler(struct irq_desc *desc) if (status & MSI_STATUS){ unsigned long imsi_status;
+ /* + * The interrupt status can be cleared even if the + * MSI status remains pending. As such, given the + * edge-triggered interrupt type, its status should + * be cleared before being dispatched to the + * handler of the underlying device. + */ + writel(MSI_STATUS, port->base + PCIE_INT_STATUS); while ((imsi_status = readl(port->base + PCIE_IMSI_STATUS))) { for_each_set_bit(bit, &imsi_status, MTK_MSI_IRQS_NUM) generic_handle_domain_irq(port->inner_domain, bit); } - /* Clear MSI interrupt status */ - writel(MSI_STATUS, port->base + PCIE_INT_STATUS); } }
diff --git a/drivers/platform/x86/intel/vsec.c b/drivers/platform/x86/intel/vsec.c index 483bb6565166..40477d1d41b5 100644 --- a/drivers/platform/x86/intel/vsec.c +++ b/drivers/platform/x86/intel/vsec.c @@ -124,36 +124,60 @@ static void intel_vsec_remove_aux(void *data) auxiliary_device_uninit(data); }
+static DEFINE_MUTEX(vsec_ida_lock); + static void intel_vsec_dev_release(struct device *dev) { struct intel_vsec_device *intel_vsec_dev = dev_to_ivdev(dev);
+ xa_erase(&auxdev_array, intel_vsec_dev->id); + + mutex_lock(&vsec_ida_lock); ida_free(intel_vsec_dev->ida, intel_vsec_dev->auxdev.id); + mutex_unlock(&vsec_ida_lock); + kfree(intel_vsec_dev->resource); kfree(intel_vsec_dev); }
-static int intel_vsec_add_aux(struct pci_dev *pdev, struct intel_vsec_device *intel_vsec_dev, - const char *name) +int intel_vsec_add_aux(struct pci_dev *pdev, struct device *parent, + struct intel_vsec_device *intel_vsec_dev, + const char *name) { struct auxiliary_device *auxdev = &intel_vsec_dev->auxdev; int ret, id;
- ret = ida_alloc(intel_vsec_dev->ida, GFP_KERNEL); + ret = xa_alloc(&auxdev_array, &intel_vsec_dev->id, intel_vsec_dev, + PMT_XA_LIMIT, GFP_KERNEL); if (ret < 0) { kfree(intel_vsec_dev->resource); kfree(intel_vsec_dev); return ret; }
- auxdev->id = ret; + mutex_lock(&vsec_ida_lock); + id = ida_alloc(intel_vsec_dev->ida, GFP_KERNEL); + mutex_unlock(&vsec_ida_lock); + if (id < 0) { + xa_erase(&auxdev_array, intel_vsec_dev->id); + kfree(intel_vsec_dev->resource); + kfree(intel_vsec_dev); + return id; + } + + if (!parent) + parent = &pdev->dev; + + auxdev->id = id; auxdev->name = name; - auxdev->dev.parent = &pdev->dev; + auxdev->dev.parent = parent; auxdev->dev.release = intel_vsec_dev_release;
ret = auxiliary_device_init(auxdev); if (ret < 0) { + mutex_lock(&vsec_ida_lock); ida_free(intel_vsec_dev->ida, auxdev->id); + mutex_unlock(&vsec_ida_lock); kfree(intel_vsec_dev->resource); kfree(intel_vsec_dev); return ret; @@ -165,19 +189,14 @@ static int intel_vsec_add_aux(struct pci_dev *pdev, struct intel_vsec_device *in return ret; }
- ret = devm_add_action_or_reset(&pdev->dev, intel_vsec_remove_aux, + ret = devm_add_action_or_reset(parent, intel_vsec_remove_aux, auxdev); if (ret < 0) return ret;
- /* Add auxdev to list */ - ret = xa_alloc(&auxdev_array, &id, intel_vsec_dev, PMT_XA_LIMIT, - GFP_KERNEL); - if (ret) - return ret; - return 0; } +EXPORT_SYMBOL_NS_GPL(intel_vsec_add_aux, INTEL_VSEC);
static int intel_vsec_add_dev(struct pci_dev *pdev, struct intel_vsec_header *header, struct intel_vsec_platform_info *info) @@ -235,7 +254,8 @@ static int intel_vsec_add_dev(struct pci_dev *pdev, struct intel_vsec_header *he else intel_vsec_dev->ida = &intel_vsec_ida;
- return intel_vsec_add_aux(pdev, intel_vsec_dev, intel_vsec_name(header->id)); + return intel_vsec_add_aux(pdev, NULL, intel_vsec_dev, + intel_vsec_name(header->id)); }
static bool intel_vsec_walk_header(struct pci_dev *pdev, diff --git a/drivers/platform/x86/intel/vsec.h b/drivers/platform/x86/intel/vsec.h index 3deeb05cf394..330672588868 100644 --- a/drivers/platform/x86/intel/vsec.h +++ b/drivers/platform/x86/intel/vsec.h @@ -38,8 +38,15 @@ struct intel_vsec_device { struct ida *ida; struct intel_vsec_platform_info *info; int num_resources; + int id; /* xa */ + void *priv_data; + size_t priv_data_size; };
+int intel_vsec_add_aux(struct pci_dev *pdev, struct device *parent, + struct intel_vsec_device *intel_vsec_dev, + const char *name); + static inline struct intel_vsec_device *dev_to_ivdev(struct device *dev) { return container_of(dev, struct intel_vsec_device, auxdev.dev); diff --git a/drivers/power/supply/bq256xx_charger.c b/drivers/power/supply/bq256xx_charger.c index 01ad84fd147c..686eb8d86e22 100644 --- a/drivers/power/supply/bq256xx_charger.c +++ b/drivers/power/supply/bq256xx_charger.c @@ -1514,13 +1514,16 @@ static int bq256xx_hw_init(struct bq256xx_device *bq) wd_reg_val = i; break; } - if (bq->watchdog_timer > bq256xx_watchdog_time[i] && + if (i + 1 < BQ256XX_NUM_WD_VAL && + bq->watchdog_timer > bq256xx_watchdog_time[i] && bq->watchdog_timer < bq256xx_watchdog_time[i + 1]) wd_reg_val = i; } ret = regmap_update_bits(bq->regmap, BQ256XX_CHARGER_CONTROL_1, BQ256XX_WATCHDOG_MASK, wd_reg_val << BQ256XX_WDT_BIT_SHIFT); + if (ret) + return ret;
ret = power_supply_get_battery_info(bq->charger, &bat_info); if (ret == -ENOMEM) diff --git a/drivers/power/supply/cw2015_battery.c b/drivers/power/supply/cw2015_battery.c index 473522b4326a..9d957cf8edf0 100644 --- a/drivers/power/supply/cw2015_battery.c +++ b/drivers/power/supply/cw2015_battery.c @@ -491,7 +491,7 @@ static int cw_battery_get_property(struct power_supply *psy,
case POWER_SUPPLY_PROP_TIME_TO_EMPTY_NOW: if (cw_battery_valid_time_to_empty(cw_bat)) - val->intval = cw_bat->time_to_empty; + val->intval = cw_bat->time_to_empty * 60; else val->intval = 0; break; diff --git a/drivers/pwm/core.c b/drivers/pwm/core.c index d333e7422f4a..9726f96bf763 100644 --- a/drivers/pwm/core.c +++ b/drivers/pwm/core.c @@ -171,7 +171,7 @@ of_pwm_single_xlate(struct pwm_chip *pc, const struct of_phandle_args *args) pwm->args.period = args->args[0]; pwm->args.polarity = PWM_POLARITY_NORMAL;
- if (args->args_count == 2 && args->args[2] & PWM_POLARITY_INVERTED) + if (args->args_count == 2 && args->args[1] & PWM_POLARITY_INVERTED) pwm->args.polarity = PWM_POLARITY_INVERSED;
return pwm; diff --git a/drivers/pwm/pwm-jz4740.c b/drivers/pwm/pwm-jz4740.c index a5fdf97c0d2e..246499128142 100644 --- a/drivers/pwm/pwm-jz4740.c +++ b/drivers/pwm/pwm-jz4740.c @@ -60,9 +60,10 @@ static int jz4740_pwm_request(struct pwm_chip *chip, struct pwm_device *pwm) snprintf(name, sizeof(name), "timer%u", pwm->hwpwm);
clk = clk_get(chip->dev, name); - if (IS_ERR(clk)) - return dev_err_probe(chip->dev, PTR_ERR(clk), - "Failed to get clock\n"); + if (IS_ERR(clk)) { + dev_err(chip->dev, "error %pe: Failed to get clock\n", clk); + return PTR_ERR(clk); + }
err = clk_prepare_enable(clk); if (err < 0) { diff --git a/drivers/pwm/pwm-stm32.c b/drivers/pwm/pwm-stm32.c index 794ca5b02968..bdcdb7f38312 100644 --- a/drivers/pwm/pwm-stm32.c +++ b/drivers/pwm/pwm-stm32.c @@ -115,14 +115,14 @@ static int stm32_pwm_raw_capture(struct stm32_pwm *priv, struct pwm_device *pwm, int ret;
/* Ensure registers have been updated, enable counter and capture */ - regmap_update_bits(priv->regmap, TIM_EGR, TIM_EGR_UG, TIM_EGR_UG); - regmap_update_bits(priv->regmap, TIM_CR1, TIM_CR1_CEN, TIM_CR1_CEN); + regmap_set_bits(priv->regmap, TIM_EGR, TIM_EGR_UG); + regmap_set_bits(priv->regmap, TIM_CR1, TIM_CR1_CEN);
/* Use cc1 or cc3 DMA resp for PWM input channels 1 & 2 or 3 & 4 */ dma_id = pwm->hwpwm < 2 ? STM32_TIMERS_DMA_CH1 : STM32_TIMERS_DMA_CH3; ccen = pwm->hwpwm < 2 ? TIM_CCER_CC12E : TIM_CCER_CC34E; ccr = pwm->hwpwm < 2 ? TIM_CCR1 : TIM_CCR3; - regmap_update_bits(priv->regmap, TIM_CCER, ccen, ccen); + regmap_set_bits(priv->regmap, TIM_CCER, ccen);
/* * Timer DMA burst mode. Request 2 registers, 2 bursts, to get both @@ -160,8 +160,8 @@ static int stm32_pwm_raw_capture(struct stm32_pwm *priv, struct pwm_device *pwm, }
stop: - regmap_update_bits(priv->regmap, TIM_CCER, ccen, 0); - regmap_update_bits(priv->regmap, TIM_CR1, TIM_CR1_CEN, 0); + regmap_clear_bits(priv->regmap, TIM_CCER, ccen); + regmap_clear_bits(priv->regmap, TIM_CR1, TIM_CR1_CEN);
return ret; } @@ -359,7 +359,7 @@ static int stm32_pwm_config(struct stm32_pwm *priv, int ch,
regmap_write(priv->regmap, TIM_PSC, prescaler); regmap_write(priv->regmap, TIM_ARR, prd - 1); - regmap_update_bits(priv->regmap, TIM_CR1, TIM_CR1_ARPE, TIM_CR1_ARPE); + regmap_set_bits(priv->regmap, TIM_CR1, TIM_CR1_ARPE);
/* Calculate the duty cycles */ dty = prd * duty_ns; @@ -377,7 +377,7 @@ static int stm32_pwm_config(struct stm32_pwm *priv, int ch, else regmap_update_bits(priv->regmap, TIM_CCMR2, mask, ccmr);
- regmap_update_bits(priv->regmap, TIM_BDTR, TIM_BDTR_MOE, TIM_BDTR_MOE); + regmap_set_bits(priv->regmap, TIM_BDTR, TIM_BDTR_MOE);
return 0; } @@ -411,13 +411,13 @@ static int stm32_pwm_enable(struct stm32_pwm *priv, int ch) if (priv->have_complementary_output) mask |= TIM_CCER_CC1NE << (ch * 4);
- regmap_update_bits(priv->regmap, TIM_CCER, mask, mask); + regmap_set_bits(priv->regmap, TIM_CCER, mask);
/* Make sure that registers are updated */ - regmap_update_bits(priv->regmap, TIM_EGR, TIM_EGR_UG, TIM_EGR_UG); + regmap_set_bits(priv->regmap, TIM_EGR, TIM_EGR_UG);
/* Enable controller */ - regmap_update_bits(priv->regmap, TIM_CR1, TIM_CR1_CEN, TIM_CR1_CEN); + regmap_set_bits(priv->regmap, TIM_CR1, TIM_CR1_CEN);
return 0; } @@ -431,11 +431,11 @@ static void stm32_pwm_disable(struct stm32_pwm *priv, int ch) if (priv->have_complementary_output) mask |= TIM_CCER_CC1NE << (ch * 4);
- regmap_update_bits(priv->regmap, TIM_CCER, mask, 0); + regmap_clear_bits(priv->regmap, TIM_CCER, mask);
/* When all channels are disabled, we can disable the controller */ if (!active_channels(priv)) - regmap_update_bits(priv->regmap, TIM_CR1, TIM_CR1_CEN, 0); + regmap_clear_bits(priv->regmap, TIM_CR1, TIM_CR1_CEN);
clk_disable(priv->clk); } @@ -568,41 +568,30 @@ static void stm32_pwm_detect_complementary(struct stm32_pwm *priv) * If complementary bit doesn't exist writing 1 will have no * effect so we can detect it. */ - regmap_update_bits(priv->regmap, - TIM_CCER, TIM_CCER_CC1NE, TIM_CCER_CC1NE); + regmap_set_bits(priv->regmap, TIM_CCER, TIM_CCER_CC1NE); regmap_read(priv->regmap, TIM_CCER, &ccer); - regmap_update_bits(priv->regmap, TIM_CCER, TIM_CCER_CC1NE, 0); + regmap_clear_bits(priv->regmap, TIM_CCER, TIM_CCER_CC1NE);
priv->have_complementary_output = (ccer != 0); }
-static int stm32_pwm_detect_channels(struct stm32_pwm *priv) +static unsigned int stm32_pwm_detect_channels(struct stm32_pwm *priv, + unsigned int *num_enabled) { - u32 ccer; - int npwm = 0; + u32 ccer, ccer_backup;
/* * If channels enable bits don't exist writing 1 will have no * effect so we can detect and count them. */ - regmap_update_bits(priv->regmap, - TIM_CCER, TIM_CCER_CCXE, TIM_CCER_CCXE); + regmap_read(priv->regmap, TIM_CCER, &ccer_backup); + regmap_set_bits(priv->regmap, TIM_CCER, TIM_CCER_CCXE); regmap_read(priv->regmap, TIM_CCER, &ccer); - regmap_update_bits(priv->regmap, TIM_CCER, TIM_CCER_CCXE, 0); - - if (ccer & TIM_CCER_CC1E) - npwm++; + regmap_write(priv->regmap, TIM_CCER, ccer_backup);
- if (ccer & TIM_CCER_CC2E) - npwm++; + *num_enabled = hweight32(ccer_backup & TIM_CCER_CCXE);
- if (ccer & TIM_CCER_CC3E) - npwm++; - - if (ccer & TIM_CCER_CC4E) - npwm++; - - return npwm; + return hweight32(ccer & TIM_CCER_CCXE); }
static int stm32_pwm_probe(struct platform_device *pdev) @@ -611,6 +600,8 @@ static int stm32_pwm_probe(struct platform_device *pdev) struct device_node *np = dev->of_node; struct stm32_timers *ddata = dev_get_drvdata(pdev->dev.parent); struct stm32_pwm *priv; + unsigned int num_enabled; + unsigned int i; int ret;
priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); @@ -633,7 +624,11 @@ static int stm32_pwm_probe(struct platform_device *pdev)
priv->chip.dev = dev; priv->chip.ops = &stm32pwm_ops; - priv->chip.npwm = stm32_pwm_detect_channels(priv); + priv->chip.npwm = stm32_pwm_detect_channels(priv, &num_enabled); + + /* Initialize clock refcount to number of enabled PWM channels. */ + for (i = 0; i < num_enabled; i++) + clk_enable(priv->clk);
ret = pwmchip_add(&priv->chip); if (ret < 0) diff --git a/drivers/scsi/fnic/fnic_debugfs.c b/drivers/scsi/fnic/fnic_debugfs.c index 6fedc3b7d1ab..eb895a65ea8f 100644 --- a/drivers/scsi/fnic/fnic_debugfs.c +++ b/drivers/scsi/fnic/fnic_debugfs.c @@ -52,9 +52,10 @@ int fnic_debugfs_init(void) fc_trc_flag->fnic_trace = 2; fc_trc_flag->fc_trace = 3; fc_trc_flag->fc_clear = 4; + return 0; }
- return 0; + return -ENOMEM; }
/* diff --git a/drivers/scsi/hisi_sas/hisi_sas_main.c b/drivers/scsi/hisi_sas/hisi_sas_main.c index a8142e2b9643..450a8578157c 100644 --- a/drivers/scsi/hisi_sas/hisi_sas_main.c +++ b/drivers/scsi/hisi_sas/hisi_sas_main.c @@ -1502,12 +1502,12 @@ EXPORT_SYMBOL_GPL(hisi_sas_controller_reset_done); static int hisi_sas_controller_prereset(struct hisi_hba *hisi_hba) { if (!hisi_hba->hw->soft_reset) - return -1; + return -ENOENT;
down(&hisi_hba->sem); if (test_and_set_bit(HISI_SAS_RESETTING_BIT, &hisi_hba->flags)) { up(&hisi_hba->sem); - return -1; + return -EPERM; }
if (hisi_sas_debugfs_enable && hisi_hba->debugfs_itct[0].itct) diff --git a/drivers/scsi/hisi_sas/hisi_sas_v3_hw.c b/drivers/scsi/hisi_sas/hisi_sas_v3_hw.c index c4305ec38ebf..0c80ff9affa3 100644 --- a/drivers/scsi/hisi_sas/hisi_sas_v3_hw.c +++ b/drivers/scsi/hisi_sas/hisi_sas_v3_hw.c @@ -3330,7 +3330,7 @@ static void debugfs_snapshot_global_reg_v3_hw(struct hisi_hba *hisi_hba) u32 *databuf = hisi_hba->debugfs_regs[dump_index][DEBUGFS_GLOBAL].data; int i;
- for (i = 0; i < debugfs_axi_reg.count; i++, databuf++) + for (i = 0; i < debugfs_global_reg.count; i++, databuf++) *databuf = hisi_sas_read32(hisi_hba, 4 * i); }
@@ -4946,6 +4946,7 @@ static void hisi_sas_reset_done_v3_hw(struct pci_dev *pdev) { struct sas_ha_struct *sha = pci_get_drvdata(pdev); struct hisi_hba *hisi_hba = sha->lldd_ha; + struct Scsi_Host *shost = hisi_hba->shost; struct device *dev = hisi_hba->dev; int rc;
@@ -4954,6 +4955,10 @@ static void hisi_sas_reset_done_v3_hw(struct pci_dev *pdev) rc = hw_init_v3_hw(hisi_hba); if (rc) { dev_err(dev, "FLR: hw init failed rc=%d\n", rc); + clear_bit(HISI_SAS_REJECT_CMD_BIT, &hisi_hba->flags); + scsi_unblock_requests(shost); + clear_bit(HISI_SAS_RESETTING_BIT, &hisi_hba->flags); + up(&hisi_hba->sem); return; }
@@ -4981,7 +4986,7 @@ static int _suspend_v3_hw(struct device *device) }
if (test_and_set_bit(HISI_SAS_RESETTING_BIT, &hisi_hba->flags)) - return -1; + return -EPERM;
dev_warn(dev, "entering suspend state\n");
diff --git a/drivers/scsi/mpi3mr/mpi3mr_app.c b/drivers/scsi/mpi3mr/mpi3mr_app.c index d10c6afb7f9c..8c662d08706f 100644 --- a/drivers/scsi/mpi3mr/mpi3mr_app.c +++ b/drivers/scsi/mpi3mr/mpi3mr_app.c @@ -223,6 +223,22 @@ static long mpi3mr_bsg_pel_enable(struct mpi3mr_ioc *mrioc, return rval; }
+ if (mrioc->unrecoverable) { + dprint_bsg_err(mrioc, "%s: unrecoverable controller\n", + __func__); + return -EFAULT; + } + + if (mrioc->reset_in_progress) { + dprint_bsg_err(mrioc, "%s: reset in progress\n", __func__); + return -EAGAIN; + } + + if (mrioc->stop_bsgs) { + dprint_bsg_err(mrioc, "%s: bsgs are blocked\n", __func__); + return -EAGAIN; + } + sg_copy_to_buffer(job->request_payload.sg_list, job->request_payload.sg_cnt, &pel_enable, sizeof(pel_enable)); diff --git a/drivers/scsi/mpi3mr/mpi3mr_os.c b/drivers/scsi/mpi3mr/mpi3mr_os.c index 6d55698ea4d1..85f5b349c7e4 100644 --- a/drivers/scsi/mpi3mr/mpi3mr_os.c +++ b/drivers/scsi/mpi3mr/mpi3mr_os.c @@ -1044,8 +1044,14 @@ void mpi3mr_rfresh_tgtdevs(struct mpi3mr_ioc *mrioc) tgtdev = NULL; list_for_each_entry(tgtdev, &mrioc->tgtdev_list, list) { if ((tgtdev->dev_handle != MPI3MR_INVALID_DEV_HANDLE) && - !tgtdev->is_hidden && !tgtdev->host_exposed) - mpi3mr_report_tgtdev_to_host(mrioc, tgtdev->perst_id); + !tgtdev->is_hidden) { + if (!tgtdev->host_exposed) + mpi3mr_report_tgtdev_to_host(mrioc, + tgtdev->perst_id); + else if (tgtdev->starget) + starget_for_each_device(tgtdev->starget, + (void *)tgtdev, mpi3mr_update_sdev); + } } }
diff --git a/drivers/soc/qcom/llcc-qcom.c b/drivers/soc/qcom/llcc-qcom.c index bc400669ee02..16a05143d0d6 100644 --- a/drivers/soc/qcom/llcc-qcom.c +++ b/drivers/soc/qcom/llcc-qcom.c @@ -680,14 +680,14 @@ static int _qcom_llcc_cfg_program(const struct llcc_slice_config *config, u32 disable_cap_alloc, retain_pc;
disable_cap_alloc = config->dis_cap_alloc << config->slice_id; - ret = regmap_write(drv_data->bcast_regmap, - LLCC_TRP_SCID_DIS_CAP_ALLOC, disable_cap_alloc); + ret = regmap_update_bits(drv_data->bcast_regmap, LLCC_TRP_SCID_DIS_CAP_ALLOC, + BIT(config->slice_id), disable_cap_alloc); if (ret) return ret;
retain_pc = config->retain_on_pc << config->slice_id; - ret = regmap_write(drv_data->bcast_regmap, - LLCC_TRP_PCB_ACT, retain_pc); + ret = regmap_update_bits(drv_data->bcast_regmap, LLCC_TRP_PCB_ACT, + BIT(config->slice_id), retain_pc); if (ret) return ret; } diff --git a/drivers/spi/Kconfig b/drivers/spi/Kconfig index 946e2186d244..15ea11ebcbe0 100644 --- a/drivers/spi/Kconfig +++ b/drivers/spi/Kconfig @@ -1101,9 +1101,10 @@ config SPI_ZYNQ_QSPI
config SPI_ZYNQMP_GQSPI tristate "Xilinx ZynqMP GQSPI controller" - depends on (SPI_MASTER && HAS_DMA) || COMPILE_TEST + depends on (SPI_MEM && HAS_DMA) || COMPILE_TEST help Enables Xilinx GQSPI controller driver for Zynq UltraScale+ MPSoC. + This controller only supports SPI memory interface.
config SPI_AMD tristate "AMD SPI controller" diff --git a/drivers/spi/spi-sh-msiof.c b/drivers/spi/spi-sh-msiof.c index 9bca3d076f05..51ceaa485724 100644 --- a/drivers/spi/spi-sh-msiof.c +++ b/drivers/spi/spi-sh-msiof.c @@ -30,12 +30,15 @@
#include <asm/unaligned.h>
+#define SH_MSIOF_FLAG_FIXED_DTDL_200 BIT(0) + struct sh_msiof_chipdata { u32 bits_per_word_mask; u16 tx_fifo_size; u16 rx_fifo_size; u16 ctlr_flags; u16 min_div_pow; + u32 flags; };
struct sh_msiof_spi_priv { @@ -1073,6 +1076,16 @@ static const struct sh_msiof_chipdata rcar_gen3_data = { .min_div_pow = 1, };
+static const struct sh_msiof_chipdata rcar_r8a7795_data = { + .bits_per_word_mask = SPI_BPW_MASK(8) | SPI_BPW_MASK(16) | + SPI_BPW_MASK(24) | SPI_BPW_MASK(32), + .tx_fifo_size = 64, + .rx_fifo_size = 64, + .ctlr_flags = SPI_CONTROLLER_MUST_TX, + .min_div_pow = 1, + .flags = SH_MSIOF_FLAG_FIXED_DTDL_200, +}; + static const struct of_device_id sh_msiof_match[] = { { .compatible = "renesas,sh-mobile-msiof", .data = &sh_data }, { .compatible = "renesas,msiof-r8a7743", .data = &rcar_gen2_data }, @@ -1083,6 +1096,7 @@ static const struct of_device_id sh_msiof_match[] = { { .compatible = "renesas,msiof-r8a7793", .data = &rcar_gen2_data }, { .compatible = "renesas,msiof-r8a7794", .data = &rcar_gen2_data }, { .compatible = "renesas,rcar-gen2-msiof", .data = &rcar_gen2_data }, + { .compatible = "renesas,msiof-r8a7795", .data = &rcar_r8a7795_data }, { .compatible = "renesas,msiof-r8a7796", .data = &rcar_gen3_data }, { .compatible = "renesas,rcar-gen3-msiof", .data = &rcar_gen3_data }, { .compatible = "renesas,rcar-gen4-msiof", .data = &rcar_gen3_data }, @@ -1280,6 +1294,9 @@ static int sh_msiof_spi_probe(struct platform_device *pdev) return -ENXIO; }
+ if (chipdata->flags & SH_MSIOF_FLAG_FIXED_DTDL_200) + info->dtdl = 200; + if (info->mode == MSIOF_SPI_SLAVE) ctlr = spi_alloc_slave(&pdev->dev, sizeof(struct sh_msiof_spi_priv)); diff --git a/drivers/spmi/spmi-mtk-pmif.c b/drivers/spmi/spmi-mtk-pmif.c index ad511f2c3324..01e8851e639d 100644 --- a/drivers/spmi/spmi-mtk-pmif.c +++ b/drivers/spmi/spmi-mtk-pmif.c @@ -50,6 +50,7 @@ struct pmif { struct clk_bulk_data clks[PMIF_MAX_CLKS]; size_t nclks; const struct pmif_data *data; + raw_spinlock_t lock; };
static const char * const pmif_clock_names[] = { @@ -314,6 +315,7 @@ static int pmif_spmi_read_cmd(struct spmi_controller *ctrl, u8 opc, u8 sid, struct ch_reg *inf_reg; int ret; u32 data, cmd; + unsigned long flags;
/* Check for argument validation. */ if (sid & ~0xf) { @@ -334,6 +336,7 @@ static int pmif_spmi_read_cmd(struct spmi_controller *ctrl, u8 opc, u8 sid, else return -EINVAL;
+ raw_spin_lock_irqsave(&arb->lock, flags); /* Wait for Software Interface FSM state to be IDLE. */ inf_reg = &arb->chan; ret = readl_poll_timeout_atomic(arb->base + arb->data->regs[inf_reg->ch_sta], @@ -343,6 +346,7 @@ static int pmif_spmi_read_cmd(struct spmi_controller *ctrl, u8 opc, u8 sid, /* set channel ready if the data has transferred */ if (pmif_is_fsm_vldclr(arb)) pmif_writel(arb, 1, inf_reg->ch_rdy); + raw_spin_unlock_irqrestore(&arb->lock, flags); dev_err(&ctrl->dev, "failed to wait for SWINF_IDLE\n"); return ret; } @@ -350,6 +354,7 @@ static int pmif_spmi_read_cmd(struct spmi_controller *ctrl, u8 opc, u8 sid, /* Send the command. */ cmd = (opc << 30) | (sid << 24) | ((len - 1) << 16) | addr; pmif_writel(arb, cmd, inf_reg->ch_send); + raw_spin_unlock_irqrestore(&arb->lock, flags);
/* * Wait for Software Interface FSM state to be WFVLDCLR, @@ -376,7 +381,8 @@ static int pmif_spmi_write_cmd(struct spmi_controller *ctrl, u8 opc, u8 sid, struct pmif *arb = spmi_controller_get_drvdata(ctrl); struct ch_reg *inf_reg; int ret; - u32 data, cmd; + u32 data, wdata, cmd; + unsigned long flags;
if (len > 4) { dev_err(&ctrl->dev, "pmif supports 1..4 bytes per trans, but:%zu requested", len); @@ -394,6 +400,10 @@ static int pmif_spmi_write_cmd(struct spmi_controller *ctrl, u8 opc, u8 sid, else return -EINVAL;
+ /* Set the write data. */ + memcpy(&wdata, buf, len); + + raw_spin_lock_irqsave(&arb->lock, flags); /* Wait for Software Interface FSM state to be IDLE. */ inf_reg = &arb->chan; ret = readl_poll_timeout_atomic(arb->base + arb->data->regs[inf_reg->ch_sta], @@ -403,17 +413,17 @@ static int pmif_spmi_write_cmd(struct spmi_controller *ctrl, u8 opc, u8 sid, /* set channel ready if the data has transferred */ if (pmif_is_fsm_vldclr(arb)) pmif_writel(arb, 1, inf_reg->ch_rdy); + raw_spin_unlock_irqrestore(&arb->lock, flags); dev_err(&ctrl->dev, "failed to wait for SWINF_IDLE\n"); return ret; }
- /* Set the write data. */ - memcpy(&data, buf, len); - pmif_writel(arb, data, inf_reg->wdata); + pmif_writel(arb, wdata, inf_reg->wdata);
/* Send the command. */ cmd = (opc << 30) | BIT(29) | (sid << 24) | ((len - 1) << 16) | addr; pmif_writel(arb, cmd, inf_reg->ch_send); + raw_spin_unlock_irqrestore(&arb->lock, flags);
return 0; } @@ -488,6 +498,8 @@ static int mtk_spmi_probe(struct platform_device *pdev) arb->chan.ch_send = PMIF_SWINF_0_ACC + chan_offset; arb->chan.ch_rdy = PMIF_SWINF_0_VLD_CLR + chan_offset;
+ raw_spin_lock_init(&arb->lock); + platform_set_drvdata(pdev, ctrl);
err = spmi_controller_add(ctrl); diff --git a/drivers/staging/media/rkvdec/rkvdec.c b/drivers/staging/media/rkvdec/rkvdec.c index a9bd1e71ea48..d16cf4115d03 100644 --- a/drivers/staging/media/rkvdec/rkvdec.c +++ b/drivers/staging/media/rkvdec/rkvdec.c @@ -461,6 +461,9 @@ static const struct v4l2_ioctl_ops rkvdec_ioctl_ops = {
.vidioc_streamon = v4l2_m2m_ioctl_streamon, .vidioc_streamoff = v4l2_m2m_ioctl_streamoff, + + .vidioc_decoder_cmd = v4l2_m2m_ioctl_stateless_decoder_cmd, + .vidioc_try_decoder_cmd = v4l2_m2m_ioctl_stateless_try_decoder_cmd, };
static int rkvdec_queue_setup(struct vb2_queue *vq, unsigned int *num_buffers, diff --git a/drivers/target/target_core_file.c b/drivers/target/target_core_file.c index 7e81a53dbf3c..8d74e97c9874 100644 --- a/drivers/target/target_core_file.c +++ b/drivers/target/target_core_file.c @@ -338,11 +338,13 @@ static int fd_do_rw(struct se_cmd *cmd, struct file *fd, }
iov_iter_bvec(&iter, is_write, bvec, sgl_nents, len); - if (is_write) + if (is_write) { + file_start_write(fd); ret = vfs_iter_write(fd, &iter, &pos, 0); - else + file_end_write(fd); + } else { ret = vfs_iter_read(fd, &iter, &pos, 0); - + } if (is_write) { if (ret < 0 || ret != data_length) { pr_err("%s() write returned %d\n", __func__, ret); @@ -474,7 +476,9 @@ fd_execute_write_same(struct se_cmd *cmd) }
iov_iter_bvec(&iter, ITER_SOURCE, bvec, nolb, len); + file_start_write(fd_dev->fd_file); ret = vfs_iter_write(fd_dev->fd_file, &iter, &pos, 0); + file_end_write(fd_dev->fd_file);
kfree(bvec); if (ret < 0 || ret != len) { diff --git a/drivers/tty/serial/8250/8250_bcm2835aux.c b/drivers/tty/serial/8250/8250_bcm2835aux.c index 15a2387a5b25..4f4502fb5454 100644 --- a/drivers/tty/serial/8250/8250_bcm2835aux.c +++ b/drivers/tty/serial/8250/8250_bcm2835aux.c @@ -119,6 +119,8 @@ static int bcm2835aux_serial_probe(struct platform_device *pdev)
/* get the clock - this also enables the HW */ data->clk = devm_clk_get_optional(&pdev->dev, NULL); + if (IS_ERR(data->clk)) + return dev_err_probe(&pdev->dev, PTR_ERR(data->clk), "could not get clk\n");
/* get the interrupt */ ret = platform_get_irq(pdev, 0); diff --git a/drivers/tty/serial/8250/8250_exar.c b/drivers/tty/serial/8250/8250_exar.c index b406cba10b0e..dca1abe36324 100644 --- a/drivers/tty/serial/8250/8250_exar.c +++ b/drivers/tty/serial/8250/8250_exar.c @@ -442,7 +442,7 @@ static int generic_rs485_config(struct uart_port *port, struct ktermios *termios }
static const struct serial_rs485 generic_rs485_supported = { - .flags = SER_RS485_ENABLED, + .flags = SER_RS485_ENABLED | SER_RS485_RTS_ON_SEND, };
static const struct exar8250_platform exar8250_default_platform = { @@ -486,7 +486,8 @@ static int iot2040_rs485_config(struct uart_port *port, struct ktermios *termios }
static const struct serial_rs485 iot2040_rs485_supported = { - .flags = SER_RS485_ENABLED | SER_RS485_RX_DURING_TX | SER_RS485_TERMINATE_BUS, + .flags = SER_RS485_ENABLED | SER_RS485_RTS_ON_SEND | + SER_RS485_RX_DURING_TX | SER_RS485_TERMINATE_BUS, };
static const struct property_entry iot2040_gpio_properties[] = { diff --git a/drivers/tty/serial/8250/8250_omap.c b/drivers/tty/serial/8250/8250_omap.c index 0b04d810b3e6..037d613006f5 100644 --- a/drivers/tty/serial/8250/8250_omap.c +++ b/drivers/tty/serial/8250/8250_omap.c @@ -1476,7 +1476,7 @@ static int omap8250_remove(struct platform_device *pdev)
err = pm_runtime_resume_and_get(&pdev->dev); if (err) - return err; + dev_err(&pdev->dev, "Failed to resume hardware\n");
serial8250_unregister_port(priv->line); priv->line = -ENODEV; diff --git a/drivers/tty/serial/imx.c b/drivers/tty/serial/imx.c index d2137f6eff32..f8962a3d4421 100644 --- a/drivers/tty/serial/imx.c +++ b/drivers/tty/serial/imx.c @@ -450,13 +450,13 @@ static void imx_uart_stop_tx(struct uart_port *port) ucr1 = imx_uart_readl(sport, UCR1); imx_uart_writel(sport, ucr1 & ~UCR1_TRDYEN, UCR1);
+ ucr4 = imx_uart_readl(sport, UCR4); usr2 = imx_uart_readl(sport, USR2); - if (!(usr2 & USR2_TXDC)) { + if ((!(usr2 & USR2_TXDC)) && (ucr4 & UCR4_TCEN)) { /* The shifter is still busy, so retry once TC triggers */ return; }
- ucr4 = imx_uart_readl(sport, UCR4); ucr4 &= ~UCR4_TCEN; imx_uart_writel(sport, ucr4, UCR4);
@@ -2229,7 +2229,6 @@ static enum hrtimer_restart imx_trigger_stop_tx(struct hrtimer *t) return HRTIMER_NORESTART; }
-static const struct serial_rs485 imx_no_rs485 = {}; /* No RS485 if no RTS */ static const struct serial_rs485 imx_rs485_supported = { .flags = SER_RS485_ENABLED | SER_RS485_RTS_ON_SEND | SER_RS485_RTS_AFTER_SEND | SER_RS485_RX_DURING_TX, @@ -2319,8 +2318,6 @@ static int imx_uart_probe(struct platform_device *pdev) /* RTS is required to control the RS485 transmitter */ if (sport->have_rtscts || sport->have_rtsgpio) sport->port.rs485_supported = imx_rs485_supported; - else - sport->port.rs485_supported = imx_no_rs485; sport->port.flags = UPF_BOOT_AUTOCONF; timer_setup(&sport->timer, imx_uart_timeout, 0);
@@ -2347,7 +2344,7 @@ static int imx_uart_probe(struct platform_device *pdev) /* For register access, we only need to enable the ipg clock. */ ret = clk_prepare_enable(sport->clk_ipg); if (ret) { - dev_err(&pdev->dev, "failed to enable per clk: %d\n", ret); + dev_err(&pdev->dev, "failed to enable ipg clk: %d\n", ret); return ret; }
@@ -2359,14 +2356,8 @@ static int imx_uart_probe(struct platform_device *pdev) sport->ufcr = readl(sport->port.membase + UFCR);
ret = uart_get_rs485_mode(&sport->port); - if (ret) { - clk_disable_unprepare(sport->clk_ipg); - return ret; - } - - if (sport->port.rs485.flags & SER_RS485_ENABLED && - (!sport->have_rtscts && !sport->have_rtsgpio)) - dev_err(&pdev->dev, "no RTS control, disabling rs485\n"); + if (ret) + goto err_clk;
/* * If using the i.MX UART RTS/CTS control then the RTS (CTS_B) @@ -2446,8 +2437,6 @@ static int imx_uart_probe(struct platform_device *pdev) imx_uart_writel(sport, ucr3, UCR3); }
- clk_disable_unprepare(sport->clk_ipg); - hrtimer_init(&sport->trigger_start_tx, CLOCK_MONOTONIC, HRTIMER_MODE_REL); hrtimer_init(&sport->trigger_stop_tx, CLOCK_MONOTONIC, HRTIMER_MODE_REL); sport->trigger_start_tx.function = imx_trigger_start_tx; @@ -2463,7 +2452,7 @@ static int imx_uart_probe(struct platform_device *pdev) if (ret) { dev_err(&pdev->dev, "failed to request rx irq: %d\n", ret); - return ret; + goto err_clk; }
ret = devm_request_irq(&pdev->dev, txirq, imx_uart_txint, 0, @@ -2471,7 +2460,7 @@ static int imx_uart_probe(struct platform_device *pdev) if (ret) { dev_err(&pdev->dev, "failed to request tx irq: %d\n", ret); - return ret; + goto err_clk; }
ret = devm_request_irq(&pdev->dev, rtsirq, imx_uart_rtsint, 0, @@ -2479,14 +2468,14 @@ static int imx_uart_probe(struct platform_device *pdev) if (ret) { dev_err(&pdev->dev, "failed to request rts irq: %d\n", ret); - return ret; + goto err_clk; } } else { ret = devm_request_irq(&pdev->dev, rxirq, imx_uart_int, 0, dev_name(&pdev->dev), sport); if (ret) { dev_err(&pdev->dev, "failed to request irq: %d\n", ret); - return ret; + goto err_clk; } }
@@ -2494,7 +2483,12 @@ static int imx_uart_probe(struct platform_device *pdev)
platform_set_drvdata(pdev, sport);
- return uart_add_one_port(&imx_uart_uart_driver, &sport->port); + ret = uart_add_one_port(&imx_uart_uart_driver, &sport->port); + +err_clk: + clk_disable_unprepare(sport->clk_ipg); + + return ret; }
static int imx_uart_remove(struct platform_device *pdev) diff --git a/drivers/tty/serial/omap-serial.c b/drivers/tty/serial/omap-serial.c index 7d0d2718ef59..beb7896ebf8a 100644 --- a/drivers/tty/serial/omap-serial.c +++ b/drivers/tty/serial/omap-serial.c @@ -1512,6 +1512,13 @@ static struct omap_uart_port_info *of_get_uart_port_info(struct device *dev) return omap_up_info; }
+static const struct serial_rs485 serial_omap_rs485_supported = { + .flags = SER_RS485_ENABLED | SER_RS485_RTS_ON_SEND | SER_RS485_RTS_AFTER_SEND | + SER_RS485_RX_DURING_TX, + .delay_rts_before_send = 1, + .delay_rts_after_send = 1, +}; + static int serial_omap_probe_rs485(struct uart_omap_port *up, struct device *dev) { @@ -1526,6 +1533,9 @@ static int serial_omap_probe_rs485(struct uart_omap_port *up, if (!np) return 0;
+ up->port.rs485_config = serial_omap_config_rs485; + up->port.rs485_supported = serial_omap_rs485_supported; + ret = uart_get_rs485_mode(&up->port); if (ret) return ret; @@ -1560,13 +1570,6 @@ static int serial_omap_probe_rs485(struct uart_omap_port *up, return 0; }
-static const struct serial_rs485 serial_omap_rs485_supported = { - .flags = SER_RS485_ENABLED | SER_RS485_RTS_ON_SEND | SER_RS485_RTS_AFTER_SEND | - SER_RS485_RX_DURING_TX, - .delay_rts_before_send = 1, - .delay_rts_after_send = 1, -}; - static int serial_omap_probe(struct platform_device *pdev) { struct omap_uart_port_info *omap_up_info = dev_get_platdata(&pdev->dev); @@ -1634,17 +1637,11 @@ static int serial_omap_probe(struct platform_device *pdev) dev_info(up->port.dev, "no wakeirq for uart%d\n", up->port.line);
- ret = serial_omap_probe_rs485(up, &pdev->dev); - if (ret < 0) - goto err_rs485; - sprintf(up->name, "OMAP UART%d", up->port.line); up->port.mapbase = mem->start; up->port.membase = base; up->port.flags = omap_up_info->flags; up->port.uartclk = omap_up_info->uartclk; - up->port.rs485_config = serial_omap_config_rs485; - up->port.rs485_supported = serial_omap_rs485_supported; if (!up->port.uartclk) { up->port.uartclk = DEFAULT_CLK_SPEED; dev_warn(&pdev->dev, @@ -1652,6 +1649,10 @@ static int serial_omap_probe(struct platform_device *pdev) DEFAULT_CLK_SPEED); }
+ ret = serial_omap_probe_rs485(up, &pdev->dev); + if (ret < 0) + goto err_rs485; + up->latency = PM_QOS_CPU_LATENCY_DEFAULT_VALUE; up->calc_latency = PM_QOS_CPU_LATENCY_DEFAULT_VALUE; cpu_latency_qos_add_request(&up->pm_qos_request, up->latency); diff --git a/drivers/tty/serial/sc16is7xx.c b/drivers/tty/serial/sc16is7xx.c index b4b849415c50..db33790e6675 100644 --- a/drivers/tty/serial/sc16is7xx.c +++ b/drivers/tty/serial/sc16is7xx.c @@ -24,6 +24,7 @@ #include <linux/tty_flip.h> #include <linux/spi/spi.h> #include <linux/uaccess.h> +#include <linux/units.h> #include <uapi/linux/sched/types.h>
#define SC16IS7XX_NAME "sc16is7xx" @@ -1716,9 +1717,12 @@ static int sc16is7xx_spi_probe(struct spi_device *spi)
/* Setup SPI bus */ spi->bits_per_word = 8; - /* only supports mode 0 on SC16IS762 */ + /* For all variants, only mode 0 is supported */ + if ((spi->mode & SPI_MODE_X_MASK) != SPI_MODE_0) + return dev_err_probe(&spi->dev, -EINVAL, "Unsupported SPI mode\n"); + spi->mode = spi->mode ? : SPI_MODE_0; - spi->max_speed_hz = spi->max_speed_hz ? : 15000000; + spi->max_speed_hz = spi->max_speed_hz ? : 4 * HZ_PER_MHZ; ret = spi_setup(spi); if (ret) return ret; diff --git a/drivers/tty/serial/serial_core.c b/drivers/tty/serial/serial_core.c index d4e57f9017db..f0ed30d0a697 100644 --- a/drivers/tty/serial/serial_core.c +++ b/drivers/tty/serial/serial_core.c @@ -1353,19 +1353,27 @@ static void uart_sanitize_serial_rs485(struct uart_port *port, struct serial_rs4 return; }
+ rs485->flags &= supported_flags; + /* Pick sane settings if the user hasn't */ - if ((supported_flags & (SER_RS485_RTS_ON_SEND|SER_RS485_RTS_AFTER_SEND)) && - !(rs485->flags & SER_RS485_RTS_ON_SEND) == + if (!(rs485->flags & SER_RS485_RTS_ON_SEND) == !(rs485->flags & SER_RS485_RTS_AFTER_SEND)) { - dev_warn_ratelimited(port->dev, - "%s (%d): invalid RTS setting, using RTS_ON_SEND instead\n", - port->name, port->line); - rs485->flags |= SER_RS485_RTS_ON_SEND; - rs485->flags &= ~SER_RS485_RTS_AFTER_SEND; - supported_flags |= SER_RS485_RTS_ON_SEND|SER_RS485_RTS_AFTER_SEND; - } + if (supported_flags & SER_RS485_RTS_ON_SEND) { + rs485->flags |= SER_RS485_RTS_ON_SEND; + rs485->flags &= ~SER_RS485_RTS_AFTER_SEND;
- rs485->flags &= supported_flags; + dev_warn_ratelimited(port->dev, + "%s (%d): invalid RTS setting, using RTS_ON_SEND instead\n", + port->name, port->line); + } else { + rs485->flags |= SER_RS485_RTS_AFTER_SEND; + rs485->flags &= ~SER_RS485_RTS_ON_SEND; + + dev_warn_ratelimited(port->dev, + "%s (%d): invalid RTS setting, using RTS_AFTER_SEND instead\n", + port->name, port->line); + } + }
uart_sanitize_serial_rs485_delays(port, rs485);
@@ -1428,7 +1436,7 @@ static int uart_set_rs485_config(struct tty_struct *tty, struct uart_port *port, int ret; unsigned long flags;
- if (!port->rs485_config) + if (!(port->rs485_supported.flags & SER_RS485_ENABLED)) return -ENOTTY;
if (copy_from_user(&rs485, rs485_user, sizeof(*rs485_user))) @@ -3420,6 +3428,9 @@ int uart_get_rs485_mode(struct uart_port *port) u32 rs485_delay[2]; int ret;
+ if (!(port->rs485_supported.flags & SER_RS485_ENABLED)) + return 0; + ret = device_property_read_u32_array(dev, "rs485-rts-delay", rs485_delay, 2); if (!ret) { diff --git a/drivers/tty/tty.h b/drivers/tty/tty.h index c5ee21912755..91515e1ebc8d 100644 --- a/drivers/tty/tty.h +++ b/drivers/tty/tty.h @@ -63,7 +63,7 @@ int tty_check_change(struct tty_struct *tty); void __stop_tty(struct tty_struct *tty); void __start_tty(struct tty_struct *tty); void tty_write_unlock(struct tty_struct *tty); -int tty_write_lock(struct tty_struct *tty, int ndelay); +int tty_write_lock(struct tty_struct *tty, bool ndelay); void tty_vhangup_session(struct tty_struct *tty); void tty_open_proc_set_tty(struct file *filp, struct tty_struct *tty); int tty_signal_session_leader(struct tty_struct *tty, int exit_session); diff --git a/drivers/tty/tty_io.c b/drivers/tty/tty_io.c index 8fb6c6853556..aaf77a5616ff 100644 --- a/drivers/tty/tty_io.c +++ b/drivers/tty/tty_io.c @@ -939,7 +939,7 @@ void tty_write_unlock(struct tty_struct *tty) wake_up_interruptible_poll(&tty->write_wait, EPOLLOUT); }
-int tty_write_lock(struct tty_struct *tty, int ndelay) +int tty_write_lock(struct tty_struct *tty, bool ndelay) { if (!mutex_trylock(&tty->atomic_write_lock)) { if (ndelay) @@ -1153,7 +1153,7 @@ int tty_send_xchar(struct tty_struct *tty, char ch) return 0; }
- if (tty_write_lock(tty, 0) < 0) + if (tty_write_lock(tty, false) < 0) return -ERESTARTSYS;
down_read(&tty->termios_rwsem); @@ -2472,22 +2472,25 @@ static int send_break(struct tty_struct *tty, unsigned int duration) return 0;
if (tty->driver->flags & TTY_DRIVER_HARDWARE_BREAK) - retval = tty->ops->break_ctl(tty, duration); - else { - /* Do the work ourselves */ - if (tty_write_lock(tty, 0) < 0) - return -EINTR; - retval = tty->ops->break_ctl(tty, -1); - if (retval) - goto out; - if (!signal_pending(current)) - msleep_interruptible(duration); + return tty->ops->break_ctl(tty, duration); + + /* Do the work ourselves */ + if (tty_write_lock(tty, false) < 0) + return -EINTR; + + retval = tty->ops->break_ctl(tty, -1); + if (!retval) { + msleep_interruptible(duration); retval = tty->ops->break_ctl(tty, 0); -out: - tty_write_unlock(tty); - if (signal_pending(current)) - retval = -EINTR; + } else if (retval == -EOPNOTSUPP) { + /* some drivers can tell only dynamically */ + retval = 0; } + tty_write_unlock(tty); + + if (signal_pending(current)) + retval = -EINTR; + return retval; }
diff --git a/drivers/tty/tty_ioctl.c b/drivers/tty/tty_ioctl.c index ad1cf51ecd11..8767c504b95d 100644 --- a/drivers/tty/tty_ioctl.c +++ b/drivers/tty/tty_ioctl.c @@ -506,7 +506,7 @@ static int set_termios(struct tty_struct *tty, void __user *arg, int opt) if (retval < 0) return retval;
- if (tty_write_lock(tty, 0) < 0) + if (tty_write_lock(tty, false) < 0) goto retry_write_wait;
/* Racing writer? */ diff --git a/drivers/ufs/core/ufshcd.c b/drivers/ufs/core/ufshcd.c index dc38d1fa7787..474e94a69b18 100644 --- a/drivers/ufs/core/ufshcd.c +++ b/drivers/ufs/core/ufshcd.c @@ -8204,7 +8204,6 @@ static int ufshcd_add_lus(struct ufs_hba *hba) ufs_bsg_probe(hba); ufshpb_init(hba); scsi_scan_host(hba->host); - pm_runtime_put_sync(hba->dev);
out: return ret; @@ -8331,15 +8330,15 @@ static void ufshcd_async_scan(void *data, async_cookie_t cookie)
/* Probe and add UFS logical units */ ret = ufshcd_add_lus(hba); + out: + pm_runtime_put_sync(hba->dev); /* * If we failed to initialize the device or the device is not * present, turn off the power/clocks etc. */ - if (ret) { - pm_runtime_put_sync(hba->dev); + if (ret) ufshcd_hba_exit(hba); - } }
static const struct attribute_group *ufshcd_driver_groups[] = { diff --git a/drivers/usb/cdns3/cdns3-gadget.c b/drivers/usb/cdns3/cdns3-gadget.c index 69a44bd7e5d0..ccdd525bd7c8 100644 --- a/drivers/usb/cdns3/cdns3-gadget.c +++ b/drivers/usb/cdns3/cdns3-gadget.c @@ -1117,6 +1117,8 @@ static int cdns3_ep_run_transfer(struct cdns3_endpoint *priv_ep, dma_addr_t trb_dma; u32 togle_pcs = 1; int sg_iter = 0; + int num_trb_req; + int trb_burst; int num_trb; int address; u32 control; @@ -1125,15 +1127,13 @@ static int cdns3_ep_run_transfer(struct cdns3_endpoint *priv_ep, struct scatterlist *s = NULL; bool sg_supported = !!(request->num_mapped_sgs);
+ num_trb_req = sg_supported ? request->num_mapped_sgs : 1; + + /* ISO transfer require each SOF have a TD, each TD include some TRBs */ if (priv_ep->type == USB_ENDPOINT_XFER_ISOC) - num_trb = priv_ep->interval; + num_trb = priv_ep->interval * num_trb_req; else - num_trb = sg_supported ? request->num_mapped_sgs : 1; - - if (num_trb > priv_ep->free_trbs) { - priv_ep->flags |= EP_RING_FULL; - return -ENOBUFS; - } + num_trb = num_trb_req;
priv_req = to_cdns3_request(request); address = priv_ep->endpoint.desc->bEndpointAddress; @@ -1182,14 +1182,31 @@ static int cdns3_ep_run_transfer(struct cdns3_endpoint *priv_ep,
link_trb->control = cpu_to_le32(((priv_ep->pcs) ? TRB_CYCLE : 0) | TRB_TYPE(TRB_LINK) | TRB_TOGGLE | ch_bit); + + if (priv_ep->type == USB_ENDPOINT_XFER_ISOC) { + /* + * ISO require LINK TRB must be first one of TD. + * Fill LINK TRBs for left trb space to simply software process logic. + */ + while (priv_ep->enqueue) { + *trb = *link_trb; + trace_cdns3_prepare_trb(priv_ep, trb); + + cdns3_ep_inc_enq(priv_ep); + trb = priv_ep->trb_pool + priv_ep->enqueue; + priv_req->trb = trb; + } + } + } + + if (num_trb > priv_ep->free_trbs) { + priv_ep->flags |= EP_RING_FULL; + return -ENOBUFS; }
if (priv_dev->dev_ver <= DEV_VER_V2) togle_pcs = cdns3_wa1_update_guard(priv_ep, trb);
- if (sg_supported) - s = request->sg; - /* set incorrect Cycle Bit for first trb*/ control = priv_ep->pcs ? 0 : TRB_CYCLE; trb->length = 0; @@ -1207,6 +1224,9 @@ static int cdns3_ep_run_transfer(struct cdns3_endpoint *priv_ep, do { u32 length;
+ if (!(sg_iter % num_trb_req) && sg_supported) + s = request->sg; + /* fill TRB */ control |= TRB_TYPE(TRB_NORMAL); if (sg_supported) { @@ -1221,7 +1241,36 @@ static int cdns3_ep_run_transfer(struct cdns3_endpoint *priv_ep, total_tdl += DIV_ROUND_UP(length, priv_ep->endpoint.maxpacket);
- trb->length |= cpu_to_le32(TRB_BURST_LEN(priv_ep->trb_burst_size) | + trb_burst = priv_ep->trb_burst_size; + + /* + * Supposed DMA cross 4k bounder problem should be fixed at DEV_VER_V2, but still + * met problem when do ISO transfer if sg enabled. + * + * Data pattern likes below when sg enabled, package size is 1k and mult is 2 + * [UVC Header(8B) ] [data(3k - 8)] ... + * + * The received data at offset 0xd000 will get 0xc000 data, len 0x70. Error happen + * as below pattern: + * 0xd000: wrong + * 0xe000: wrong + * 0xf000: correct + * 0x10000: wrong + * 0x11000: wrong + * 0x12000: correct + * ... + * + * But it is still unclear about why error have not happen below 0xd000, it should + * cross 4k bounder. But anyway, the below code can fix this problem. + * + * To avoid DMA cross 4k bounder at ISO transfer, reduce burst len according to 16. + */ + if (priv_ep->type == USB_ENDPOINT_XFER_ISOC && priv_dev->dev_ver <= DEV_VER_V2) + if (ALIGN_DOWN(trb->buffer, SZ_4K) != + ALIGN_DOWN(trb->buffer + length, SZ_4K)) + trb_burst = 16; + + trb->length |= cpu_to_le32(TRB_BURST_LEN(trb_burst) | TRB_LEN(length)); pcs = priv_ep->pcs ? TRB_CYCLE : 0;
@@ -1248,7 +1297,7 @@ static int cdns3_ep_run_transfer(struct cdns3_endpoint *priv_ep, if (sg_supported) { trb->control |= cpu_to_le32(TRB_ISP); /* Don't set chain bit for last TRB */ - if (sg_iter < num_trb - 1) + if ((sg_iter % num_trb_req) < num_trb_req - 1) trb->control |= cpu_to_le32(TRB_CHAIN);
s = sg_next(s); @@ -1506,6 +1555,12 @@ static void cdns3_transfer_completed(struct cdns3_device *priv_dev,
/* The TRB was changed as link TRB, and the request was handled at ep_dequeue */ while (TRB_FIELD_TO_TYPE(le32_to_cpu(trb->control)) == TRB_LINK) { + + /* ISO ep_traddr may stop at LINK TRB */ + if (priv_ep->dequeue == cdns3_get_dma_pos(priv_dev, priv_ep) && + priv_ep->type == USB_ENDPOINT_XFER_ISOC) + break; + trace_cdns3_complete_trb(priv_ep, trb); cdns3_ep_inc_deq(priv_ep); trb = priv_ep->trb_pool + priv_ep->dequeue; @@ -1538,6 +1593,10 @@ static void cdns3_transfer_completed(struct cdns3_device *priv_dev, }
if (request_handled) { + /* TRBs are duplicated by priv_ep->interval time for ISO IN */ + if (priv_ep->type == USB_ENDPOINT_XFER_ISOC && priv_ep->dir) + request->actual /= priv_ep->interval; + cdns3_gadget_giveback(priv_ep, priv_req, 0); request_handled = false; transfer_end = false; @@ -2033,11 +2092,10 @@ int cdns3_ep_config(struct cdns3_endpoint *priv_ep, bool enable) bool is_iso_ep = (priv_ep->type == USB_ENDPOINT_XFER_ISOC); struct cdns3_device *priv_dev = priv_ep->cdns3_dev; u32 bEndpointAddress = priv_ep->num | priv_ep->dir; - u32 max_packet_size = 0; - u8 maxburst = 0; + u32 max_packet_size = priv_ep->wMaxPacketSize; + u8 maxburst = priv_ep->bMaxBurst; u32 ep_cfg = 0; u8 buffering; - u8 mult = 0; int ret;
buffering = priv_dev->ep_buf_size - 1; @@ -2059,8 +2117,7 @@ int cdns3_ep_config(struct cdns3_endpoint *priv_ep, bool enable) break; default: ep_cfg = EP_CFG_EPTYPE(USB_ENDPOINT_XFER_ISOC); - mult = priv_dev->ep_iso_burst - 1; - buffering = mult + 1; + buffering = (priv_ep->bMaxBurst + 1) * (priv_ep->mult + 1) - 1; }
switch (priv_dev->gadget.speed) { @@ -2071,17 +2128,8 @@ int cdns3_ep_config(struct cdns3_endpoint *priv_ep, bool enable) max_packet_size = is_iso_ep ? 1024 : 512; break; case USB_SPEED_SUPER: - /* It's limitation that driver assumes in driver. */ - mult = 0; - max_packet_size = 1024; - if (priv_ep->type == USB_ENDPOINT_XFER_ISOC) { - maxburst = priv_dev->ep_iso_burst - 1; - buffering = (mult + 1) * - (maxburst + 1); - - if (priv_ep->interval > 1) - buffering++; - } else { + if (priv_ep->type != USB_ENDPOINT_XFER_ISOC) { + max_packet_size = 1024; maxburst = priv_dev->ep_buf_size - 1; } break; @@ -2110,7 +2158,6 @@ int cdns3_ep_config(struct cdns3_endpoint *priv_ep, bool enable) if (priv_dev->dev_ver < DEV_VER_V2) priv_ep->trb_burst_size = 16;
- mult = min_t(u8, mult, EP_CFG_MULT_MAX); buffering = min_t(u8, buffering, EP_CFG_BUFFERING_MAX); maxburst = min_t(u8, maxburst, EP_CFG_MAXBURST_MAX);
@@ -2144,7 +2191,7 @@ int cdns3_ep_config(struct cdns3_endpoint *priv_ep, bool enable) }
ep_cfg |= EP_CFG_MAXPKTSIZE(max_packet_size) | - EP_CFG_MULT(mult) | + EP_CFG_MULT(priv_ep->mult) | /* must match EP setting */ EP_CFG_BUFFERING(buffering) | EP_CFG_MAXBURST(maxburst);
@@ -2234,6 +2281,13 @@ usb_ep *cdns3_gadget_match_ep(struct usb_gadget *gadget, priv_ep->type = usb_endpoint_type(desc); priv_ep->flags |= EP_CLAIMED; priv_ep->interval = desc->bInterval ? BIT(desc->bInterval - 1) : 0; + priv_ep->wMaxPacketSize = usb_endpoint_maxp(desc); + priv_ep->mult = USB_EP_MAXP_MULT(priv_ep->wMaxPacketSize); + priv_ep->wMaxPacketSize &= USB_ENDPOINT_MAXP_MASK; + if (priv_ep->type == USB_ENDPOINT_XFER_ISOC && comp_desc) { + priv_ep->mult = USB_SS_MULT(comp_desc->bmAttributes) - 1; + priv_ep->bMaxBurst = comp_desc->bMaxBurst; + }
spin_unlock_irqrestore(&priv_dev->lock, flags); return &priv_ep->endpoint; @@ -3015,22 +3069,40 @@ static int cdns3_gadget_check_config(struct usb_gadget *gadget) struct cdns3_endpoint *priv_ep; struct usb_ep *ep; int n_in = 0; + int iso = 0; + int out = 1; int total; + int n;
list_for_each_entry(ep, &gadget->ep_list, ep_list) { priv_ep = ep_to_cdns3_ep(ep); - if ((priv_ep->flags & EP_CLAIMED) && (ep->address & USB_DIR_IN)) - n_in++; + if (!(priv_ep->flags & EP_CLAIMED)) + continue; + + n = (priv_ep->mult + 1) * (priv_ep->bMaxBurst + 1); + if (ep->address & USB_DIR_IN) { + /* + * ISO transfer: DMA start move data when get ISO, only transfer + * data as min(TD size, iso). No benefit for allocate bigger + * internal memory than 'iso'. + */ + if (priv_ep->type == USB_ENDPOINT_XFER_ISOC) + iso += n; + else + n_in++; + } else { + if (priv_ep->type == USB_ENDPOINT_XFER_ISOC) + out = max_t(int, out, n); + } }
/* 2KB are reserved for EP0, 1KB for out*/ - total = 2 + n_in + 1; + total = 2 + n_in + out + iso;
if (total > priv_dev->onchip_buffers) return -ENOMEM;
- priv_dev->ep_buf_size = priv_dev->ep_iso_burst = - (priv_dev->onchip_buffers - 2) / (n_in + 1); + priv_dev->ep_buf_size = (priv_dev->onchip_buffers - 2 - iso) / (n_in + out);
return 0; } diff --git a/drivers/usb/cdns3/cdns3-gadget.h b/drivers/usb/cdns3/cdns3-gadget.h index fbe4a8e3aa89..086a7bb83897 100644 --- a/drivers/usb/cdns3/cdns3-gadget.h +++ b/drivers/usb/cdns3/cdns3-gadget.h @@ -1168,6 +1168,9 @@ struct cdns3_endpoint { u8 dir; u8 num; u8 type; + u8 mult; + u8 bMaxBurst; + u16 wMaxPacketSize; int interval;
int free_trbs; diff --git a/drivers/usb/chipidea/core.c b/drivers/usb/chipidea/core.c index b9227f41cf1c..763d6858a8e6 100644 --- a/drivers/usb/chipidea/core.c +++ b/drivers/usb/chipidea/core.c @@ -523,6 +523,13 @@ static irqreturn_t ci_irq_handler(int irq, void *data) u32 otgsc = 0;
if (ci->in_lpm) { + /* + * If we already have a wakeup irq pending there, + * let's just return to wait resume finished firstly. + */ + if (ci->wakeup_int) + return IRQ_HANDLED; + disable_irq_nosync(irq); ci->wakeup_int = true; pm_runtime_get(ci->dev); diff --git a/drivers/usb/class/cdc-acm.c b/drivers/usb/class/cdc-acm.c index 36bf051b345b..2a7eea4e251a 100644 --- a/drivers/usb/class/cdc-acm.c +++ b/drivers/usb/class/cdc-acm.c @@ -892,6 +892,9 @@ static int acm_tty_break_ctl(struct tty_struct *tty, int state) struct acm *acm = tty->driver_data; int retval;
+ if (!(acm->ctrl_caps & USB_CDC_CAP_BRK)) + return -EOPNOTSUPP; + retval = acm_send_break(acm, state ? 0xffff : 0); if (retval < 0) dev_dbg(&acm->control->dev, diff --git a/drivers/usb/dwc3/core.c b/drivers/usb/dwc3/core.c index 1f23c96fa94f..011a3909f9ad 100644 --- a/drivers/usb/dwc3/core.c +++ b/drivers/usb/dwc3/core.c @@ -277,48 +277,11 @@ int dwc3_core_soft_reset(struct dwc3 *dwc) /* * We're resetting only the device side because, if we're in host mode, * XHCI driver will reset the host block. If dwc3 was configured for - * host-only mode or current role is host, then we can return early. + * host-only mode, then we can return early. */ if (dwc->current_dr_role == DWC3_GCTL_PRTCAP_HOST) return 0;
- /* - * If the dr_mode is host and the dwc->current_dr_role is not the - * corresponding DWC3_GCTL_PRTCAP_HOST, then the dwc3_core_init_mode - * isn't executed yet. Ensure the phy is ready before the controller - * updates the GCTL.PRTCAPDIR or other settings by soft-resetting - * the phy. - * - * Note: GUSB3PIPECTL[n] and GUSB2PHYCFG[n] are port settings where n - * is port index. If this is a multiport host, then we need to reset - * all active ports. - */ - if (dwc->dr_mode == USB_DR_MODE_HOST) { - u32 usb3_port; - u32 usb2_port; - - usb3_port = dwc3_readl(dwc->regs, DWC3_GUSB3PIPECTL(0)); - usb3_port |= DWC3_GUSB3PIPECTL_PHYSOFTRST; - dwc3_writel(dwc->regs, DWC3_GUSB3PIPECTL(0), usb3_port); - - usb2_port = dwc3_readl(dwc->regs, DWC3_GUSB2PHYCFG(0)); - usb2_port |= DWC3_GUSB2PHYCFG_PHYSOFTRST; - dwc3_writel(dwc->regs, DWC3_GUSB2PHYCFG(0), usb2_port); - - /* Small delay for phy reset assertion */ - usleep_range(1000, 2000); - - usb3_port &= ~DWC3_GUSB3PIPECTL_PHYSOFTRST; - dwc3_writel(dwc->regs, DWC3_GUSB3PIPECTL(0), usb3_port); - - usb2_port &= ~DWC3_GUSB2PHYCFG_PHYSOFTRST; - dwc3_writel(dwc->regs, DWC3_GUSB2PHYCFG(0), usb2_port); - - /* Wait for clock synchronization */ - msleep(50); - return 0; - } - reg = dwc3_readl(dwc->regs, DWC3_DCTL); reg |= DWC3_DCTL_CSFTRST; reg &= ~DWC3_DCTL_RUN_STOP; diff --git a/drivers/usb/dwc3/ep0.c b/drivers/usb/dwc3/ep0.c index 61de693461da..ec3c33266547 100644 --- a/drivers/usb/dwc3/ep0.c +++ b/drivers/usb/dwc3/ep0.c @@ -236,7 +236,10 @@ void dwc3_ep0_stall_and_restart(struct dwc3 *dwc) struct dwc3_request *req;
req = next_request(&dep->pending_list); - dwc3_gadget_giveback(dep, req, -ECONNRESET); + if (!dwc->connected) + dwc3_gadget_giveback(dep, req, -ESHUTDOWN); + else + dwc3_gadget_giveback(dep, req, -ECONNRESET); }
dwc->eps[0]->trb_enqueue = 0; diff --git a/drivers/usb/host/xhci-mtk.c b/drivers/usb/host/xhci-mtk.c index a0921687444b..bb4f80627cdc 100644 --- a/drivers/usb/host/xhci-mtk.c +++ b/drivers/usb/host/xhci-mtk.c @@ -7,6 +7,7 @@ * Chunfeng Yun chunfeng.yun@mediatek.com */
+#include <linux/bitfield.h> #include <linux/dma-mapping.h> #include <linux/iopoll.h> #include <linux/kernel.h> @@ -73,6 +74,9 @@ #define FRMCNT_LEV1_RANG (0x12b << 8) #define FRMCNT_LEV1_RANG_MASK GENMASK(19, 8)
+#define HSCH_CFG1 0x960 +#define SCH3_RXFIFO_DEPTH_MASK GENMASK(21, 20) + #define SS_GEN2_EOF_CFG 0x990 #define SSG2EOF_OFFSET 0x3c
@@ -114,6 +118,8 @@ #define SSC_IP_SLEEP_EN BIT(4) #define SSC_SPM_INT_EN BIT(1)
+#define SCH_FIFO_TO_KB(x) ((x) >> 10) + enum ssusb_uwk_vers { SSUSB_UWK_V1 = 1, SSUSB_UWK_V2, @@ -165,6 +171,35 @@ static void xhci_mtk_set_frame_interval(struct xhci_hcd_mtk *mtk) writel(value, hcd->regs + SS_GEN2_EOF_CFG); }
+/* + * workaround: usb3.2 gen1 isoc rx hw issue + * host send out unexpected ACK afer device fininsh a burst transfer with + * a short packet. + */ +static void xhci_mtk_rxfifo_depth_set(struct xhci_hcd_mtk *mtk) +{ + struct usb_hcd *hcd = mtk->hcd; + u32 value; + + if (!mtk->rxfifo_depth) + return; + + value = readl(hcd->regs + HSCH_CFG1); + value &= ~SCH3_RXFIFO_DEPTH_MASK; + value |= FIELD_PREP(SCH3_RXFIFO_DEPTH_MASK, + SCH_FIFO_TO_KB(mtk->rxfifo_depth) - 1); + writel(value, hcd->regs + HSCH_CFG1); +} + +static void xhci_mtk_init_quirk(struct xhci_hcd_mtk *mtk) +{ + /* workaround only for mt8195 */ + xhci_mtk_set_frame_interval(mtk); + + /* workaround for SoCs using SSUSB about before IPM v1.6.0 */ + xhci_mtk_rxfifo_depth_set(mtk); +} + static int xhci_mtk_host_enable(struct xhci_hcd_mtk *mtk) { struct mu3c_ippc_regs __iomem *ippc = mtk->ippc_regs; @@ -453,8 +488,7 @@ static int xhci_mtk_setup(struct usb_hcd *hcd) if (ret) return ret;
- /* workaround only for mt8195 */ - xhci_mtk_set_frame_interval(mtk); + xhci_mtk_init_quirk(mtk); }
ret = xhci_gen_setup(hcd, xhci_mtk_quirks); @@ -531,6 +565,8 @@ static int xhci_mtk_probe(struct platform_device *pdev) of_property_read_u32(node, "mediatek,u2p-dis-msk", &mtk->u2p_dis_msk);
+ of_property_read_u32(node, "rx-fifo-depth", &mtk->rxfifo_depth); + ret = usb_wakeup_of_property_parse(mtk, node); if (ret) { dev_err(dev, "failed to parse uwk property\n"); diff --git a/drivers/usb/host/xhci-mtk.h b/drivers/usb/host/xhci-mtk.h index 1174a510dd38..2a6a47d0f09a 100644 --- a/drivers/usb/host/xhci-mtk.h +++ b/drivers/usb/host/xhci-mtk.h @@ -160,6 +160,8 @@ struct xhci_hcd_mtk { struct regmap *uwk; u32 uwk_reg_base; u32 uwk_vers; + /* quirk */ + u32 rxfifo_depth; };
static inline struct xhci_hcd_mtk *hcd_to_mtk(struct usb_hcd *hcd) diff --git a/drivers/usb/mon/mon_bin.c b/drivers/usb/mon/mon_bin.c index 094e812e9e69..35483217b1f6 100644 --- a/drivers/usb/mon/mon_bin.c +++ b/drivers/usb/mon/mon_bin.c @@ -1247,14 +1247,19 @@ static vm_fault_t mon_bin_vma_fault(struct vm_fault *vmf) struct mon_reader_bin *rp = vmf->vma->vm_private_data; unsigned long offset, chunk_idx; struct page *pageptr; + unsigned long flags;
+ spin_lock_irqsave(&rp->b_lock, flags); offset = vmf->pgoff << PAGE_SHIFT; - if (offset >= rp->b_size) + if (offset >= rp->b_size) { + spin_unlock_irqrestore(&rp->b_lock, flags); return VM_FAULT_SIGBUS; + } chunk_idx = offset / CHUNK_SIZE; pageptr = rp->b_vec[chunk_idx].pg; get_page(pageptr); vmf->page = pageptr; + spin_unlock_irqrestore(&rp->b_lock, flags); return 0; }
diff --git a/drivers/usb/phy/phy-mxs-usb.c b/drivers/usb/phy/phy-mxs-usb.c index 9299df53eb9d..160c9264339f 100644 --- a/drivers/usb/phy/phy-mxs-usb.c +++ b/drivers/usb/phy/phy-mxs-usb.c @@ -388,8 +388,7 @@ static void __mxs_phy_disconnect_line(struct mxs_phy *mxs_phy, bool disconnect)
static bool mxs_phy_is_otg_host(struct mxs_phy *mxs_phy) { - return IS_ENABLED(CONFIG_USB_OTG) && - mxs_phy->phy.last_event == USB_EVENT_ID; + return mxs_phy->phy.last_event == USB_EVENT_ID; }
static void mxs_phy_disconnect_line(struct mxs_phy *mxs_phy, bool on) diff --git a/drivers/usb/typec/class.c b/drivers/usb/typec/class.c index 49d6b2388b87..3da404d5178d 100644 --- a/drivers/usb/typec/class.c +++ b/drivers/usb/typec/class.c @@ -263,11 +263,13 @@ static void typec_altmode_put_partner(struct altmode *altmode) { struct altmode *partner = altmode->partner; struct typec_altmode *adev; + struct typec_altmode *partner_adev;
if (!partner) return;
adev = &altmode->adev; + partner_adev = &partner->adev;
if (is_typec_plug(adev->dev.parent)) { struct typec_plug *plug = to_typec_plug(adev->dev.parent); @@ -276,7 +278,7 @@ static void typec_altmode_put_partner(struct altmode *altmode) } else { partner->partner = NULL; } - put_device(&adev->dev); + put_device(&partner_adev->dev); }
/** diff --git a/drivers/vdpa/alibaba/eni_vdpa.c b/drivers/vdpa/alibaba/eni_vdpa.c index 5a09a09cca70..cce3d1837104 100644 --- a/drivers/vdpa/alibaba/eni_vdpa.c +++ b/drivers/vdpa/alibaba/eni_vdpa.c @@ -497,7 +497,7 @@ static int eni_vdpa_probe(struct pci_dev *pdev, const struct pci_device_id *id) if (!eni_vdpa->vring) { ret = -ENOMEM; ENI_ERR(pdev, "failed to allocate virtqueues\n"); - goto err; + goto err_remove_vp_legacy; }
for (i = 0; i < eni_vdpa->queues; i++) { @@ -509,11 +509,13 @@ static int eni_vdpa_probe(struct pci_dev *pdev, const struct pci_device_id *id) ret = vdpa_register_device(&eni_vdpa->vdpa, eni_vdpa->queues); if (ret) { ENI_ERR(pdev, "failed to register to vdpa bus\n"); - goto err; + goto err_remove_vp_legacy; }
return 0;
+err_remove_vp_legacy: + vp_legacy_remove(&eni_vdpa->ldev); err: put_device(&eni_vdpa->vdpa.dev); return ret; diff --git a/drivers/video/fbdev/core/fb_defio.c b/drivers/video/fbdev/core/fb_defio.c index a3cf1f764f29..49883c8012e6 100644 --- a/drivers/video/fbdev/core/fb_defio.c +++ b/drivers/video/fbdev/core/fb_defio.c @@ -132,11 +132,7 @@ int fb_deferred_io_fsync(struct file *file, loff_t start, loff_t end, int datasy return 0;
inode_lock(inode); - /* Kill off the delayed work */ - cancel_delayed_work_sync(&info->deferred_work); - - /* Run it immediately */ - schedule_delayed_work(&info->deferred_work, 0); + flush_delayed_work(&info->deferred_work); inode_unlock(inode);
return 0; @@ -321,7 +317,7 @@ static void fb_deferred_io_lastclose(struct fb_info *info) struct page *page; int i;
- cancel_delayed_work_sync(&info->deferred_work); + flush_delayed_work(&info->deferred_work);
/* clear out the mapping that we setup */ for (i = 0 ; i < info->fix.smem_len; i += PAGE_SIZE) { diff --git a/drivers/video/fbdev/imxfb.c b/drivers/video/fbdev/imxfb.c index 36ada87b49a4..32b8374abeca 100644 --- a/drivers/video/fbdev/imxfb.c +++ b/drivers/video/fbdev/imxfb.c @@ -42,6 +42,7 @@ #include <video/videomode.h>
#define PCR_TFT (1 << 31) +#define PCR_COLOR (1 << 30) #define PCR_BPIX_8 (3 << 25) #define PCR_BPIX_12 (4 << 25) #define PCR_BPIX_16 (5 << 25) @@ -150,6 +151,12 @@ enum imxfb_type { IMX21_FB, };
+enum imxfb_panel_type { + PANEL_TYPE_MONOCHROME, + PANEL_TYPE_CSTN, + PANEL_TYPE_TFT, +}; + struct imxfb_info { struct platform_device *pdev; void __iomem *regs; @@ -157,6 +164,7 @@ struct imxfb_info { struct clk *clk_ahb; struct clk *clk_per; enum imxfb_type devtype; + enum imxfb_panel_type panel_type; bool enabled;
/* @@ -444,6 +452,13 @@ static int imxfb_check_var(struct fb_var_screeninfo *var, struct fb_info *info) if (!is_imx1_fb(fbi) && imxfb_mode->aus_mode) fbi->lauscr = LAUSCR_AUS_MODE;
+ if (imxfb_mode->pcr & PCR_TFT) + fbi->panel_type = PANEL_TYPE_TFT; + else if (imxfb_mode->pcr & PCR_COLOR) + fbi->panel_type = PANEL_TYPE_CSTN; + else + fbi->panel_type = PANEL_TYPE_MONOCHROME; + /* * Copy the RGB parameters for this display * from the machine specific parameters. @@ -598,6 +613,7 @@ static int imxfb_activate_var(struct fb_var_screeninfo *var, struct fb_info *inf { struct imxfb_info *fbi = info->par; u32 ymax_mask = is_imx1_fb(fbi) ? YMAX_MASK_IMX1 : YMAX_MASK_IMX21; + u8 left_margin_low;
pr_debug("var: xres=%d hslen=%d lm=%d rm=%d\n", var->xres, var->hsync_len, @@ -606,6 +622,13 @@ static int imxfb_activate_var(struct fb_var_screeninfo *var, struct fb_info *inf var->yres, var->vsync_len, var->upper_margin, var->lower_margin);
+ if (fbi->panel_type == PANEL_TYPE_TFT) + left_margin_low = 3; + else if (fbi->panel_type == PANEL_TYPE_CSTN) + left_margin_low = 2; + else + left_margin_low = 0; + #if DEBUG_VAR if (var->xres < 16 || var->xres > 1024) printk(KERN_ERR "%s: invalid xres %d\n", @@ -613,7 +636,7 @@ static int imxfb_activate_var(struct fb_var_screeninfo *var, struct fb_info *inf if (var->hsync_len < 1 || var->hsync_len > 64) printk(KERN_ERR "%s: invalid hsync_len %d\n", info->fix.id, var->hsync_len); - if (var->left_margin < 3 || var->left_margin > 255) + if (var->left_margin < left_margin_low || var->left_margin > 255) printk(KERN_ERR "%s: invalid left_margin %d\n", info->fix.id, var->left_margin); if (var->right_margin < 1 || var->right_margin > 255) @@ -639,7 +662,7 @@ static int imxfb_activate_var(struct fb_var_screeninfo *var, struct fb_info *inf
writel(HCR_H_WIDTH(var->hsync_len - 1) | HCR_H_WAIT_1(var->right_margin - 1) | - HCR_H_WAIT_2(var->left_margin - 3), + HCR_H_WAIT_2(var->left_margin - left_margin_low), fbi->regs + LCDC_HCR);
writel(VCR_V_WIDTH(var->vsync_len) | diff --git a/drivers/watchdog/bcm2835_wdt.c b/drivers/watchdog/bcm2835_wdt.c index 94907176a0e4..55c0f7b0e8fb 100644 --- a/drivers/watchdog/bcm2835_wdt.c +++ b/drivers/watchdog/bcm2835_wdt.c @@ -42,6 +42,7 @@
#define SECS_TO_WDOG_TICKS(x) ((x) << 16) #define WDOG_TICKS_TO_SECS(x) ((x) >> 16) +#define WDOG_TICKS_TO_MSECS(x) ((x) * 1000 >> 16)
struct bcm2835_wdt { void __iomem *base; @@ -140,7 +141,7 @@ static struct watchdog_device bcm2835_wdt_wdd = { .info = &bcm2835_wdt_info, .ops = &bcm2835_wdt_ops, .min_timeout = 1, - .max_timeout = WDOG_TICKS_TO_SECS(PM_WDOG_TIME_SET), + .max_hw_heartbeat_ms = WDOG_TICKS_TO_MSECS(PM_WDOG_TIME_SET), .timeout = WDOG_TICKS_TO_SECS(PM_WDOG_TIME_SET), };
diff --git a/drivers/watchdog/hpwdt.c b/drivers/watchdog/hpwdt.c index f79f932bca14..79ed1626d8ea 100644 --- a/drivers/watchdog/hpwdt.c +++ b/drivers/watchdog/hpwdt.c @@ -178,7 +178,7 @@ static int hpwdt_pretimeout(unsigned int ulReason, struct pt_regs *regs) "3. OA Forward Progress Log\n" "4. iLO Event Log";
- if (ilo5 && ulReason == NMI_UNKNOWN && !mynmi) + if (ulReason == NMI_UNKNOWN && !mynmi) return NMI_DONE;
if (ilo5 && !pretimeout && !mynmi) diff --git a/drivers/watchdog/rti_wdt.c b/drivers/watchdog/rti_wdt.c index 6e9253761fc1..ea617c0f9747 100644 --- a/drivers/watchdog/rti_wdt.c +++ b/drivers/watchdog/rti_wdt.c @@ -70,6 +70,11 @@ static int rti_wdt_start(struct watchdog_device *wdd) { u32 timer_margin; struct rti_wdt_device *wdt = watchdog_get_drvdata(wdd); + int ret; + + ret = pm_runtime_resume_and_get(wdd->parent); + if (ret) + return ret;
/* set timeout period */ timer_margin = (u64)wdd->timeout * wdt->freq; @@ -295,6 +300,9 @@ static int rti_wdt_probe(struct platform_device *pdev) if (last_ping) watchdog_set_last_hw_keepalive(wdd, last_ping);
+ if (!watchdog_hw_running(wdd)) + pm_runtime_put_sync(&pdev->dev); + return 0;
err_iomap: @@ -309,7 +317,10 @@ static int rti_wdt_remove(struct platform_device *pdev) struct rti_wdt_device *wdt = platform_get_drvdata(pdev);
watchdog_unregister_device(&wdt->wdd); - pm_runtime_put(&pdev->dev); + + if (!pm_runtime_suspended(&pdev->dev)) + pm_runtime_put(&pdev->dev); + pm_runtime_disable(&pdev->dev);
return 0; diff --git a/drivers/watchdog/watchdog_dev.c b/drivers/watchdog/watchdog_dev.c index fdffa6859dde..81684d89dc98 100644 --- a/drivers/watchdog/watchdog_dev.c +++ b/drivers/watchdog/watchdog_dev.c @@ -1052,6 +1052,7 @@ static int watchdog_cdev_register(struct watchdog_device *wdd)
/* Fill in the data structures */ cdev_init(&wd_data->cdev, &watchdog_fops); + wd_data->cdev.owner = wdd->ops->owner;
/* Add the device */ err = cdev_device_add(&wd_data->cdev, &wd_data->dev); @@ -1066,8 +1067,6 @@ static int watchdog_cdev_register(struct watchdog_device *wdd) return err; }
- wd_data->cdev.owner = wdd->ops->owner; - /* Record time of most recent heartbeat as 'just before now'. */ wd_data->last_hw_keepalive = ktime_sub(ktime_get(), 1); watchdog_set_open_deadline(wd_data); diff --git a/fs/efivarfs/super.c b/fs/efivarfs/super.c index 6780fc81cc11..77c7615bba5e 100644 --- a/fs/efivarfs/super.c +++ b/fs/efivarfs/super.c @@ -13,6 +13,7 @@ #include <linux/ucs2_string.h> #include <linux/slab.h> #include <linux/magic.h> +#include <linux/printk.h>
#include "internal.h"
@@ -226,8 +227,19 @@ static int efivarfs_get_tree(struct fs_context *fc) return get_tree_single(fc, efivarfs_fill_super); }
+static int efivarfs_reconfigure(struct fs_context *fc) +{ + if (!efivar_supports_writes() && !(fc->sb_flags & SB_RDONLY)) { + pr_err("Firmware does not support SetVariableRT. Can not remount with rw\n"); + return -EINVAL; + } + + return 0; +} + static const struct fs_context_operations efivarfs_context_ops = { .get_tree = efivarfs_get_tree, + .reconfigure = efivarfs_reconfigure, };
static int efivarfs_init_fs_context(struct fs_context *fc) @@ -238,10 +250,13 @@ static int efivarfs_init_fs_context(struct fs_context *fc)
static void efivarfs_kill_sb(struct super_block *sb) { + struct efivarfs_fs_info *sfi = sb->s_fs_info; + kill_litter_super(sb);
/* Remove all entries and destroy */ efivar_entry_iter(efivarfs_destroy, &efivarfs_list, NULL); + kfree(sfi); }
static struct file_system_type efivarfs_type = { diff --git a/fs/erofs/zdata.c b/fs/erofs/zdata.c index 1b91ac5be961..cf9a2fa7f55d 100644 --- a/fs/erofs/zdata.c +++ b/fs/erofs/zdata.c @@ -1192,12 +1192,11 @@ static int z_erofs_decompress_pcluster(struct z_erofs_decompress_backend *be, put_page(page); } else { for (i = 0; i < pclusterpages; ++i) { - page = pcl->compressed_bvecs[i].page; + /* consider shortlived pages added when decompressing */ + page = be->compressed_pages[i];
if (erofs_page_is_managed(sbi, page)) continue; - - /* recycle all individual short-lived pages */ (void)z_erofs_put_shortlivedpage(be->pagepool, page); WRITE_ONCE(pcl->compressed_bvecs[i].page, NULL); } diff --git a/fs/f2fs/data.c b/fs/f2fs/data.c index 3666c1fd77a6..8b561af37974 100644 --- a/fs/f2fs/data.c +++ b/fs/f2fs/data.c @@ -2490,9 +2490,6 @@ int f2fs_encrypt_one_page(struct f2fs_io_info *fio)
page = fio->compressed_page ? fio->compressed_page : fio->page;
- /* wait for GCed page writeback via META_MAPPING */ - f2fs_wait_on_block_writeback(inode, fio->old_blkaddr); - if (fscrypt_inode_uses_inline_crypto(inode)) return 0;
@@ -2681,6 +2678,10 @@ int f2fs_do_write_data_page(struct f2fs_io_info *fio) goto out_writepage; }
+ /* wait for GCed page writeback via META_MAPPING */ + if (fio->post_read) + f2fs_wait_on_block_writeback(inode, fio->old_blkaddr); + /* * If current allocation needs SSR, * it had better in-place writes for updated data. diff --git a/fs/f2fs/file.c b/fs/f2fs/file.c index 9b9fb3c57ec6..fd22854dbeae 100644 --- a/fs/f2fs/file.c +++ b/fs/f2fs/file.c @@ -42,7 +42,7 @@ static vm_fault_t f2fs_filemap_fault(struct vm_fault *vmf) vm_fault_t ret;
ret = filemap_fault(vmf); - if (!ret) + if (ret & VM_FAULT_LOCKED) f2fs_update_iostat(F2FS_I_SB(inode), inode, APP_MAPPED_READ_IO, F2FS_BLKSIZE);
@@ -2821,6 +2821,11 @@ static int f2fs_move_file_range(struct file *file_in, loff_t pos_in, goto out; }
+ if (f2fs_compressed_file(src) || f2fs_compressed_file(dst)) { + ret = -EOPNOTSUPP; + goto out_unlock; + } + ret = -EINVAL; if (pos_in + len > src->i_size || pos_in + len < pos_in) goto out_unlock; diff --git a/fs/f2fs/namei.c b/fs/f2fs/namei.c index bd020a992c2e..328cd20b16a5 100644 --- a/fs/f2fs/namei.c +++ b/fs/f2fs/namei.c @@ -1099,7 +1099,7 @@ static int f2fs_rename(struct user_namespace *mnt_userns, struct inode *old_dir, }
if (old_dir_entry) { - if (old_dir != new_dir && !whiteout) + if (old_dir != new_dir) f2fs_set_link(old_inode, old_dir_entry, old_dir_page, new_dir); else diff --git a/fs/f2fs/node.c b/fs/f2fs/node.c index 6efccd7ccfe1..c6d0e0709632 100644 --- a/fs/f2fs/node.c +++ b/fs/f2fs/node.c @@ -2738,11 +2738,11 @@ int f2fs_recover_xattr_data(struct inode *inode, struct page *page) f2fs_update_inode_page(inode);
/* 3: update and set xattr node page dirty */ - if (page) + if (page) { memcpy(F2FS_NODE(xpage), F2FS_NODE(page), VALID_XATTR_BLOCK_SIZE); - - set_page_dirty(xpage); + set_page_dirty(xpage); + } f2fs_put_page(xpage, 1);
return 0; diff --git a/fs/f2fs/xattr.c b/fs/f2fs/xattr.c index 8816e13ca7c9..0631b383e21f 100644 --- a/fs/f2fs/xattr.c +++ b/fs/f2fs/xattr.c @@ -660,11 +660,14 @@ static int __f2fs_setxattr(struct inode *inode, int index, here = __find_xattr(base_addr, last_base_addr, NULL, index, len, name); if (!here) { if (!F2FS_I(inode)->i_xattr_nid) { + error = f2fs_recover_xattr_data(inode, NULL); f2fs_notice(F2FS_I_SB(inode), - "recover xattr in inode (%lu)", inode->i_ino); - f2fs_recover_xattr_data(inode, NULL); - kfree(base_addr); - goto retry; + "recover xattr in inode (%lu), error(%d)", + inode->i_ino, error); + if (!error) { + kfree(base_addr); + goto retry; + } } f2fs_err(F2FS_I_SB(inode), "set inode (%lu) has corrupted xattr", inode->i_ino); diff --git a/fs/gfs2/rgrp.c b/fs/gfs2/rgrp.c index f602fb844951..dcaaa32efc4a 100644 --- a/fs/gfs2/rgrp.c +++ b/fs/gfs2/rgrp.c @@ -2306,7 +2306,7 @@ void gfs2_rgrp_dump(struct seq_file *seq, struct gfs2_rgrpd *rgd, (unsigned long long)rgd->rd_addr, rgd->rd_flags, rgd->rd_free, rgd->rd_free_clone, rgd->rd_dinodes, rgd->rd_requested, rgd->rd_reserved, rgd->rd_extfail_pt); - if (rgd->rd_sbd->sd_args.ar_rgrplvb) { + if (rgd->rd_sbd->sd_args.ar_rgrplvb && rgd->rd_rgl) { struct gfs2_rgrp_lvb *rgl = rgd->rd_rgl;
gfs2_print_dbg(seq, "%s L: f:%02x b:%u i:%u\n", fs_id_buf, diff --git a/fs/namespace.c b/fs/namespace.c index e04a9e9e3f14..29a8d90dd107 100644 --- a/fs/namespace.c +++ b/fs/namespace.c @@ -2693,7 +2693,12 @@ static int do_remount(struct path *path, int ms_flags, int sb_flags, if (IS_ERR(fc)) return PTR_ERR(fc);
+ /* + * Indicate to the filesystem that the remount request is coming + * from the legacy mount system call. + */ fc->oldapi = true; + err = parse_monolithic_mount_data(fc, data); if (!err) { down_write(&sb->s_umount); @@ -3027,6 +3032,12 @@ static int do_new_mount(struct path *path, const char *fstype, int sb_flags, if (IS_ERR(fc)) return PTR_ERR(fc);
+ /* + * Indicate to the filesystem that the mount request is coming + * from the legacy mount system call. + */ + fc->oldapi = true; + if (subtype) err = vfs_parse_fs_string(fc, "subtype", subtype, strlen(subtype)); diff --git a/fs/nfs/blocklayout/blocklayout.c b/fs/nfs/blocklayout/blocklayout.c index 943aeea1eb16..6be13e0ec170 100644 --- a/fs/nfs/blocklayout/blocklayout.c +++ b/fs/nfs/blocklayout/blocklayout.c @@ -580,6 +580,8 @@ bl_find_get_deviceid(struct nfs_server *server, nfs4_delete_deviceid(node->ld, node->nfs_client, id); goto retry; } + + nfs4_put_deviceid_node(node); return ERR_PTR(-ENODEV); }
@@ -893,10 +895,9 @@ bl_pg_init_write(struct nfs_pageio_descriptor *pgio, struct nfs_page *req) }
if (pgio->pg_dreq == NULL) - wb_size = pnfs_num_cont_bytes(pgio->pg_inode, - req->wb_index); + wb_size = pnfs_num_cont_bytes(pgio->pg_inode, req->wb_index); else - wb_size = nfs_dreq_bytes_left(pgio->pg_dreq); + wb_size = nfs_dreq_bytes_left(pgio->pg_dreq, req_offset(req));
pnfs_generic_pg_init_write(pgio, req, wb_size);
diff --git a/fs/nfs/direct.c b/fs/nfs/direct.c index 3bb530d4bb5c..8fdb65e1b14a 100644 --- a/fs/nfs/direct.c +++ b/fs/nfs/direct.c @@ -195,9 +195,10 @@ static void nfs_direct_req_release(struct nfs_direct_req *dreq) kref_put(&dreq->kref, nfs_direct_req_free); }
-ssize_t nfs_dreq_bytes_left(struct nfs_direct_req *dreq) +ssize_t nfs_dreq_bytes_left(struct nfs_direct_req *dreq, loff_t offset) { - return dreq->bytes_left; + loff_t start = offset - dreq->io_start; + return dreq->max_count - start; } EXPORT_SYMBOL_GPL(nfs_dreq_bytes_left);
diff --git a/fs/nfs/internal.h b/fs/nfs/internal.h index 4b07a0508f9d..35a8ae46b6c3 100644 --- a/fs/nfs/internal.h +++ b/fs/nfs/internal.h @@ -640,7 +640,7 @@ extern int nfs_sillyrename(struct inode *dir, struct dentry *dentry); /* direct.c */ void nfs_init_cinfo_from_dreq(struct nfs_commit_info *cinfo, struct nfs_direct_req *dreq); -extern ssize_t nfs_dreq_bytes_left(struct nfs_direct_req *dreq); +extern ssize_t nfs_dreq_bytes_left(struct nfs_direct_req *dreq, loff_t offset);
/* nfs4proc.c */ extern struct nfs_client *nfs4_init_client(struct nfs_client *clp, diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c index 85a952143e9f..ec3f0103e1a7 100644 --- a/fs/nfs/nfs4proc.c +++ b/fs/nfs/nfs4proc.c @@ -170,6 +170,7 @@ static int nfs4_map_errors(int err) case -NFS4ERR_RESOURCE: case -NFS4ERR_LAYOUTTRYLATER: case -NFS4ERR_RECALLCONFLICT: + case -NFS4ERR_RETURNCONFLICT: return -EREMOTEIO; case -NFS4ERR_WRONGSEC: case -NFS4ERR_WRONG_CRED: @@ -558,6 +559,7 @@ static int nfs4_do_handle_exception(struct nfs_server *server, case -NFS4ERR_GRACE: case -NFS4ERR_LAYOUTTRYLATER: case -NFS4ERR_RECALLCONFLICT: + case -NFS4ERR_RETURNCONFLICT: exception->delay = 1; return 0;
@@ -9667,6 +9669,7 @@ nfs4_layoutget_handle_exception(struct rpc_task *task, status = -EBUSY; break; case -NFS4ERR_RECALLCONFLICT: + case -NFS4ERR_RETURNCONFLICT: status = -ERECALLCONFLICT; break; case -NFS4ERR_DELEG_REVOKED: diff --git a/fs/nfs/pnfs.c b/fs/nfs/pnfs.c index 1ffb1068216b..4448ff829cbb 100644 --- a/fs/nfs/pnfs.c +++ b/fs/nfs/pnfs.c @@ -2729,7 +2729,8 @@ pnfs_generic_pg_init_read(struct nfs_pageio_descriptor *pgio, struct nfs_page *r if (pgio->pg_dreq == NULL) rd_size = i_size_read(pgio->pg_inode) - req_offset(req); else - rd_size = nfs_dreq_bytes_left(pgio->pg_dreq); + rd_size = nfs_dreq_bytes_left(pgio->pg_dreq, + req_offset(req));
pgio->pg_lseg = pnfs_update_layout(pgio->pg_inode, nfs_req_openctx(req), diff --git a/fs/pstore/ram_core.c b/fs/pstore/ram_core.c index 1e755d093d92..f479e0755a24 100644 --- a/fs/pstore/ram_core.c +++ b/fs/pstore/ram_core.c @@ -190,7 +190,7 @@ static int persistent_ram_init_ecc(struct persistent_ram_zone *prz, { int numerr; struct persistent_ram_buffer *buffer = prz->buffer; - int ecc_blocks; + size_t ecc_blocks; size_t ecc_total;
if (!ecc_info || !ecc_info->ecc_size) diff --git a/fs/smb/server/asn1.c b/fs/smb/server/asn1.c index 4a4b2b03ff33..b931a99ab9c8 100644 --- a/fs/smb/server/asn1.c +++ b/fs/smb/server/asn1.c @@ -214,10 +214,15 @@ static int ksmbd_neg_token_alloc(void *context, size_t hdrlen, { struct ksmbd_conn *conn = context;
+ if (!vlen) + return -EINVAL; + conn->mechToken = kmemdup_nul(value, vlen, GFP_KERNEL); if (!conn->mechToken) return -ENOMEM;
+ conn->mechTokenLen = (unsigned int)vlen; + return 0; }
diff --git a/fs/smb/server/connection.c b/fs/smb/server/connection.c index b6fa1e285c40..7977827c6541 100644 --- a/fs/smb/server/connection.c +++ b/fs/smb/server/connection.c @@ -415,13 +415,7 @@ static void stop_sessions(void) again: down_read(&conn_list_lock); list_for_each_entry(conn, &conn_list, conns_list) { - struct task_struct *task; - t = conn->transport; - task = t->handler; - if (task) - ksmbd_debug(CONN, "Stop session handler %s/%d\n", - task->comm, task_pid_nr(task)); ksmbd_conn_set_exiting(conn); if (t->ops->shutdown) { up_read(&conn_list_lock); diff --git a/fs/smb/server/connection.h b/fs/smb/server/connection.h index 3c005246a32e..0e04cf8b1d89 100644 --- a/fs/smb/server/connection.h +++ b/fs/smb/server/connection.h @@ -88,6 +88,7 @@ struct ksmbd_conn { __u16 dialect;
char *mechToken; + unsigned int mechTokenLen;
struct ksmbd_conn_ops *conn_ops;
@@ -134,7 +135,6 @@ struct ksmbd_transport_ops { struct ksmbd_transport { struct ksmbd_conn *conn; struct ksmbd_transport_ops *ops; - struct task_struct *handler; };
#define KSMBD_TCP_RECV_TIMEOUT (7 * HZ) diff --git a/fs/smb/server/oplock.c b/fs/smb/server/oplock.c index af0f6914eca4..f1831e26adad 100644 --- a/fs/smb/server/oplock.c +++ b/fs/smb/server/oplock.c @@ -1191,6 +1191,12 @@ int smb_grant_oplock(struct ksmbd_work *work, int req_op_level, u64 pid, bool prev_op_has_lease; __le32 prev_op_state = 0;
+ /* Only v2 leases handle the directory */ + if (S_ISDIR(file_inode(fp->filp)->i_mode)) { + if (!lctx || lctx->version != 2) + return 0; + } + opinfo = alloc_opinfo(work, pid, tid); if (!opinfo) return -ENOMEM; diff --git a/fs/smb/server/smb2pdu.c b/fs/smb/server/smb2pdu.c index 46070951d163..6826b562073e 100644 --- a/fs/smb/server/smb2pdu.c +++ b/fs/smb/server/smb2pdu.c @@ -1412,7 +1412,10 @@ static struct ksmbd_user *session_user(struct ksmbd_conn *conn, char *name; unsigned int name_off, name_len, secbuf_len;
- secbuf_len = le16_to_cpu(req->SecurityBufferLength); + if (conn->use_spnego && conn->mechToken) + secbuf_len = conn->mechTokenLen; + else + secbuf_len = le16_to_cpu(req->SecurityBufferLength); if (secbuf_len < sizeof(struct authenticate_message)) { ksmbd_debug(SMB, "blob len %d too small\n", secbuf_len); return NULL; @@ -1503,7 +1506,10 @@ static int ntlm_authenticate(struct ksmbd_work *work, struct authenticate_message *authblob;
authblob = user_authblob(conn, req); - sz = le16_to_cpu(req->SecurityBufferLength); + if (conn->use_spnego && conn->mechToken) + sz = conn->mechTokenLen; + else + sz = le16_to_cpu(req->SecurityBufferLength); rc = ksmbd_decode_ntlmssp_auth_blob(authblob, sz, conn, sess); if (rc) { set_user_flag(sess->user, KSMBD_USER_FLAG_BAD_PASSWORD); @@ -1776,8 +1782,7 @@ int smb2_sess_setup(struct ksmbd_work *work)
negblob_off = le16_to_cpu(req->SecurityBufferOffset); negblob_len = le16_to_cpu(req->SecurityBufferLength); - if (negblob_off < offsetof(struct smb2_sess_setup_req, Buffer) || - negblob_len < offsetof(struct negotiate_message, NegotiateFlags)) { + if (negblob_off < offsetof(struct smb2_sess_setup_req, Buffer)) { rc = -EINVAL; goto out_err; } @@ -1786,8 +1791,15 @@ int smb2_sess_setup(struct ksmbd_work *work) negblob_off);
if (decode_negotiation_token(conn, negblob, negblob_len) == 0) { - if (conn->mechToken) + if (conn->mechToken) { negblob = (struct negotiate_message *)conn->mechToken; + negblob_len = conn->mechTokenLen; + } + } + + if (negblob_len < offsetof(struct negotiate_message, NegotiateFlags)) { + rc = -EINVAL; + goto out_err; }
if (server_conf.auth_mechs & conn->auth_mechs) { diff --git a/fs/smb/server/smb_common.c b/fs/smb/server/smb_common.c index d160363c09eb..e90a1e8c1951 100644 --- a/fs/smb/server/smb_common.c +++ b/fs/smb/server/smb_common.c @@ -158,8 +158,12 @@ int ksmbd_verify_smb_message(struct ksmbd_work *work) */ bool ksmbd_smb_request(struct ksmbd_conn *conn) { - __le32 *proto = (__le32 *)smb2_get_msg(conn->request_buf); + __le32 *proto;
+ if (conn->request_buf[0] != 0) + return false; + + proto = (__le32 *)smb2_get_msg(conn->request_buf); if (*proto == SMB2_COMPRESSION_TRANSFORM_ID) { pr_err_ratelimited("smb2 compression not support yet"); return false; diff --git a/fs/smb/server/transport_rdma.c b/fs/smb/server/transport_rdma.c index c5629a68c8b7..8faa25c6e129 100644 --- a/fs/smb/server/transport_rdma.c +++ b/fs/smb/server/transport_rdma.c @@ -2039,6 +2039,7 @@ static bool rdma_frwr_is_supported(struct ib_device_attr *attrs) static int smb_direct_handle_connect_request(struct rdma_cm_id *new_cm_id) { struct smb_direct_transport *t; + struct task_struct *handler; int ret;
if (!rdma_frwr_is_supported(&new_cm_id->device->attrs)) { @@ -2056,11 +2057,11 @@ static int smb_direct_handle_connect_request(struct rdma_cm_id *new_cm_id) if (ret) goto out_err;
- KSMBD_TRANS(t)->handler = kthread_run(ksmbd_conn_handler_loop, - KSMBD_TRANS(t)->conn, "ksmbd:r%u", - smb_direct_port); - if (IS_ERR(KSMBD_TRANS(t)->handler)) { - ret = PTR_ERR(KSMBD_TRANS(t)->handler); + handler = kthread_run(ksmbd_conn_handler_loop, + KSMBD_TRANS(t)->conn, "ksmbd:r%u", + smb_direct_port); + if (IS_ERR(handler)) { + ret = PTR_ERR(handler); pr_err("Can't start thread\n"); goto out_err; } diff --git a/fs/smb/server/transport_tcp.c b/fs/smb/server/transport_tcp.c index eff7a1d793f0..9d4222154dcc 100644 --- a/fs/smb/server/transport_tcp.c +++ b/fs/smb/server/transport_tcp.c @@ -185,6 +185,7 @@ static int ksmbd_tcp_new_connection(struct socket *client_sk) struct sockaddr *csin; int rc = 0; struct tcp_transport *t; + struct task_struct *handler;
t = alloc_transport(client_sk); if (!t) { @@ -199,13 +200,13 @@ static int ksmbd_tcp_new_connection(struct socket *client_sk) goto out_error; }
- KSMBD_TRANS(t)->handler = kthread_run(ksmbd_conn_handler_loop, - KSMBD_TRANS(t)->conn, - "ksmbd:%u", - ksmbd_tcp_get_port(csin)); - if (IS_ERR(KSMBD_TRANS(t)->handler)) { + handler = kthread_run(ksmbd_conn_handler_loop, + KSMBD_TRANS(t)->conn, + "ksmbd:%u", + ksmbd_tcp_get_port(csin)); + if (IS_ERR(handler)) { pr_err("cannot start conn thread\n"); - rc = PTR_ERR(KSMBD_TRANS(t)->handler); + rc = PTR_ERR(handler); free_transport(t); } return rc; diff --git a/include/crypto/if_alg.h b/include/crypto/if_alg.h index a5db86670bdf..a406e281ae57 100644 --- a/include/crypto/if_alg.h +++ b/include/crypto/if_alg.h @@ -138,6 +138,7 @@ struct af_alg_async_req { * recvmsg is invoked. * @init: True if metadata has been sent. * @len: Length of memory allocated for this data structure. + * @inflight: Non-zero when AIO requests are in flight. */ struct af_alg_ctx { struct list_head tsgl_list; @@ -156,6 +157,8 @@ struct af_alg_ctx { bool init;
unsigned int len; + + unsigned int inflight; };
int af_alg_register_type(const struct af_alg_type *type); diff --git a/include/drm/drm_bridge.h b/include/drm/drm_bridge.h index 6b656ea23b96..a76f4103d48b 100644 --- a/include/drm/drm_bridge.h +++ b/include/drm/drm_bridge.h @@ -191,7 +191,7 @@ struct drm_bridge_funcs { * or &drm_encoder_helper_funcs.dpms hook. * * The bridge must assume that the display pipe (i.e. clocks and timing - * singals) feeding it is no longer running when this callback is + * signals) feeding it is no longer running when this callback is * called. * * The @post_disable callback is optional. diff --git a/include/dt-bindings/clock/qcom,videocc-sm8150.h b/include/dt-bindings/clock/qcom,videocc-sm8150.h index e24ee840cfdb..c557b78dc572 100644 --- a/include/dt-bindings/clock/qcom,videocc-sm8150.h +++ b/include/dt-bindings/clock/qcom,videocc-sm8150.h @@ -16,6 +16,10 @@
/* VIDEO_CC Resets */ #define VIDEO_CC_MVSC_CORE_CLK_BCR 0 +#define VIDEO_CC_INTERFACE_BCR 1 +#define VIDEO_CC_MVS0_BCR 2 +#define VIDEO_CC_MVS1_BCR 3 +#define VIDEO_CC_MVSC_BCR 4
/* VIDEO_CC GDSCRs */ #define VENUS_GDSC 0 diff --git a/include/linux/bio.h b/include/linux/bio.h index 2c5806997bbf..2b9fc5edf49d 100644 --- a/include/linux/bio.h +++ b/include/linux/bio.h @@ -279,6 +279,11 @@ static inline void bio_first_folio(struct folio_iter *fi, struct bio *bio, { struct bio_vec *bvec = bio_first_bvec_all(bio) + i;
+ if (unlikely(i >= bio->bi_vcnt)) { + fi->folio = NULL; + return; + } + fi->folio = page_folio(bvec->bv_page); fi->offset = bvec->bv_offset + PAGE_SIZE * (bvec->bv_page - &fi->folio->page); @@ -296,10 +301,8 @@ static inline void bio_next_folio(struct folio_iter *fi, struct bio *bio) fi->offset = 0; fi->length = min(folio_size(fi->folio), fi->_seg_count); fi->_next = folio_next(fi->folio); - } else if (fi->_i + 1 < bio->bi_vcnt) { - bio_first_folio(fi, bio, fi->_i + 1); } else { - fi->folio = NULL; + bio_first_folio(fi, bio, fi->_i + 1); } }
diff --git a/include/linux/blkdev.h b/include/linux/blkdev.h index 07a7eeef47d3..e255674a9ee7 100644 --- a/include/linux/blkdev.h +++ b/include/linux/blkdev.h @@ -1109,11 +1109,12 @@ static inline bool bdev_is_partition(struct block_device *bdev) enum blk_default_limits { BLK_MAX_SEGMENTS = 128, BLK_SAFE_MAX_SECTORS = 255, - BLK_DEF_MAX_SECTORS = 2560, BLK_MAX_SEGMENT_SIZE = 65536, BLK_SEG_BOUNDARY_MASK = 0xFFFFFFFFUL, };
+#define BLK_DEF_MAX_SECTORS 2560u + static inline unsigned long queue_segment_boundary(const struct request_queue *q) { return q->limits.seg_boundary_mask; diff --git a/include/linux/bpf.h b/include/linux/bpf.h index ba22cf4f5fc0..c04a61ffac8a 100644 --- a/include/linux/bpf.h +++ b/include/linux/bpf.h @@ -102,7 +102,11 @@ struct bpf_map_ops { /* funcs called by prog_array and perf_event_array map */ void *(*map_fd_get_ptr)(struct bpf_map *map, struct file *map_file, int fd); - void (*map_fd_put_ptr)(void *ptr); + /* If need_defer is true, the implementation should guarantee that + * the to-be-put element is still alive before the bpf program, which + * may manipulate it, exists. + */ + void (*map_fd_put_ptr)(struct bpf_map *map, void *ptr, bool need_defer); int (*map_gen_lookup)(struct bpf_map *map, struct bpf_insn *insn_buf); u32 (*map_fd_sys_lookup_elem)(void *ptr); void (*map_seq_show_elem)(struct bpf_map *map, void *key, @@ -233,7 +237,11 @@ struct bpf_map { */ atomic64_t refcnt ____cacheline_aligned; atomic64_t usercnt; - struct work_struct work; + /* rcu is used before freeing and work is only used during freeing */ + union { + struct work_struct work; + struct rcu_head rcu; + }; struct mutex freeze_mutex; atomic64_t writecnt; /* 'Ownership' of program-containing map is claimed by the first program @@ -249,6 +257,8 @@ struct bpf_map { } owner; bool bypass_spec_v1; bool frozen; /* write-once; write-protected by freeze_mutex */ + bool free_after_mult_rcu_gp; + s64 __percpu *elem_count; };
static inline bool map_value_has_spin_lock(const struct bpf_map *map) @@ -1791,6 +1801,35 @@ bpf_map_alloc_percpu(const struct bpf_map *map, size_t size, size_t align, } #endif
+static inline int +bpf_map_init_elem_count(struct bpf_map *map) +{ + size_t size = sizeof(*map->elem_count), align = size; + gfp_t flags = GFP_USER | __GFP_NOWARN; + + map->elem_count = bpf_map_alloc_percpu(map, size, align, flags); + if (!map->elem_count) + return -ENOMEM; + + return 0; +} + +static inline void +bpf_map_free_elem_count(struct bpf_map *map) +{ + free_percpu(map->elem_count); +} + +static inline void bpf_map_inc_elem_count(struct bpf_map *map) +{ + this_cpu_inc(*map->elem_count); +} + +static inline void bpf_map_dec_elem_count(struct bpf_map *map) +{ + this_cpu_dec(*map->elem_count); +} + extern int sysctl_unprivileged_bpf_disabled;
static inline bool bpf_allow_ptr_leaks(void) diff --git a/include/linux/clk-provider.h b/include/linux/clk-provider.h index 15e336281d1f..94fcfefb52f3 100644 --- a/include/linux/clk-provider.h +++ b/include/linux/clk-provider.h @@ -446,8 +446,8 @@ struct clk *clk_register_fixed_rate(struct device *dev, const char *name, */ #define clk_hw_register_fixed_rate_with_accuracy_parent_hw(dev, name, \ parent_hw, flags, fixed_rate, fixed_accuracy) \ - __clk_hw_register_fixed_rate((dev), NULL, (name), NULL, (parent_hw) \ - NULL, NULL, (flags), (fixed_rate), \ + __clk_hw_register_fixed_rate((dev), NULL, (name), NULL, (parent_hw), \ + NULL, (flags), (fixed_rate), \ (fixed_accuracy), 0, false) /** * clk_hw_register_fixed_rate_with_accuracy_parent_data - register fixed-rate diff --git a/include/linux/hisi_acc_qm.h b/include/linux/hisi_acc_qm.h index 41203ce27d64..b566ae420449 100644 --- a/include/linux/hisi_acc_qm.h +++ b/include/linux/hisi_acc_qm.h @@ -161,6 +161,11 @@ enum qm_cap_bits { QM_SUPPORT_RPM, };
+struct qm_dev_alg { + u64 alg_msk; + const char *alg; +}; + struct dfx_diff_registers { u32 *regs; u32 reg_offset; @@ -266,6 +271,16 @@ struct hisi_qm_cap_info { u32 v3_val; };
+struct hisi_qm_cap_record { + u32 type; + u32 cap_val; +}; + +struct hisi_qm_cap_tables { + struct hisi_qm_cap_record *qm_cap_table; + struct hisi_qm_cap_record *dev_cap_table; +}; + struct hisi_qm_list { struct mutex lock; struct list_head list; @@ -337,7 +352,6 @@ struct hisi_qm { struct work_struct rst_work; struct work_struct cmd_process;
- const char *algs; bool use_sva; bool is_frozen;
@@ -348,6 +362,8 @@ struct hisi_qm { struct qm_shaper_factor *factor; u32 mb_qos; u32 type_rate; + + struct hisi_qm_cap_tables cap_tables; };
struct hisi_qp_status { @@ -521,6 +537,8 @@ void hisi_qm_regs_dump(struct seq_file *s, struct debugfs_regset32 *regset); u32 hisi_qm_get_hw_info(struct hisi_qm *qm, const struct hisi_qm_cap_info *info_table, u32 index, bool is_read); +int hisi_qm_set_algs(struct hisi_qm *qm, u64 alg_msk, const struct qm_dev_alg *dev_algs, + u32 dev_algs_size);
/* Used by VFIO ACC live migration driver */ struct pci_driver *hisi_sec_get_pf_driver(void); diff --git a/include/linux/iio/adc/adi-axi-adc.h b/include/linux/iio/adc/adi-axi-adc.h index 52620e5b8052..b7904992d561 100644 --- a/include/linux/iio/adc/adi-axi-adc.h +++ b/include/linux/iio/adc/adi-axi-adc.h @@ -41,6 +41,7 @@ struct adi_axi_adc_chip_info { * @reg_access IIO debugfs_reg_access hook for the client ADC * @read_raw IIO read_raw hook for the client ADC * @write_raw IIO write_raw hook for the client ADC + * @read_avail IIO read_avail hook for the client ADC */ struct adi_axi_adc_conv { const struct adi_axi_adc_chip_info *chip_info; @@ -54,6 +55,9 @@ struct adi_axi_adc_conv { int (*write_raw)(struct adi_axi_adc_conv *conv, struct iio_chan_spec const *chan, int val, int val2, long mask); + int (*read_avail)(struct adi_axi_adc_conv *conv, + struct iio_chan_spec const *chan, + const int **val, int *type, int *length, long mask); };
struct adi_axi_adc_conv *devm_adi_axi_adc_conv_register(struct device *dev, diff --git a/include/linux/netfilter_bridge.h b/include/linux/netfilter_bridge.h index f980edfdd278..743475ca7e9d 100644 --- a/include/linux/netfilter_bridge.h +++ b/include/linux/netfilter_bridge.h @@ -42,7 +42,7 @@ static inline int nf_bridge_get_physinif(const struct sk_buff *skb) if (!nf_bridge) return 0;
- return nf_bridge->physindev ? nf_bridge->physindev->ifindex : 0; + return nf_bridge->physinif; }
static inline int nf_bridge_get_physoutif(const struct sk_buff *skb) @@ -56,11 +56,11 @@ static inline int nf_bridge_get_physoutif(const struct sk_buff *skb) }
static inline struct net_device * -nf_bridge_get_physindev(const struct sk_buff *skb) +nf_bridge_get_physindev(const struct sk_buff *skb, struct net *net) { const struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb);
- return nf_bridge ? nf_bridge->physindev : NULL; + return nf_bridge ? dev_get_by_index_rcu(net, nf_bridge->physinif) : NULL; }
static inline struct net_device * diff --git a/include/linux/of.h b/include/linux/of.h index 6b79ef9a6541..1c5301e10442 100644 --- a/include/linux/of.h +++ b/include/linux/of.h @@ -1155,7 +1155,8 @@ static inline int of_property_read_string_index(const struct device_node *np, * @np: device node from which the property value is to be read. * @propname: name of the property to be searched. * - * Search for a property in a device node. + * Search for a boolean property in a device node. Usage on non-boolean + * property types is deprecated. * * Return: true if the property exists false otherwise. */ @@ -1167,6 +1168,20 @@ static inline bool of_property_read_bool(const struct device_node *np, return prop ? true : false; }
+/** + * of_property_present - Test if a property is present in a node + * @np: device node to search for the property. + * @propname: name of the property to be searched. + * + * Test for a property present in a device node. + * + * Return: true if the property exists false otherwise. + */ +static inline bool of_property_present(const struct device_node *np, const char *propname) +{ + return of_property_read_bool(np, propname); +} + /** * of_property_read_u8_array - Find and read an array of u8 from a property. * diff --git a/include/linux/rcupdate.h b/include/linux/rcupdate.h index e9e61cd27ef6..46bd9a331fd5 100644 --- a/include/linux/rcupdate.h +++ b/include/linux/rcupdate.h @@ -242,6 +242,18 @@ static inline void exit_tasks_rcu_stop(void) { } static inline void exit_tasks_rcu_finish(void) { } #endif /* #else #ifdef CONFIG_TASKS_RCU_GENERIC */
+/** + * rcu_trace_implies_rcu_gp - does an RCU Tasks Trace grace period imply an RCU grace period? + * + * As an accident of implementation, an RCU Tasks Trace grace period also + * acts as an RCU grace period. However, this could change at any time. + * Code relying on this accident must call this function to verify that + * this accident is still happening. + * + * You have been warned! + */ +static inline bool rcu_trace_implies_rcu_gp(void) { return true; } + /** * cond_resched_tasks_rcu_qs - Report potential quiescent states to RCU * diff --git a/include/linux/skbuff.h b/include/linux/skbuff.h index 2feee144fc0e..c30d419ebf54 100644 --- a/include/linux/skbuff.h +++ b/include/linux/skbuff.h @@ -301,7 +301,7 @@ struct nf_bridge_info { u8 bridged_dnat:1; u8 sabotage_in_done:1; __u16 frag_max_size; - struct net_device *physindev; + int physinif;
/* always valid & non-NULL from FORWARD on, for physdev match */ struct net_device *physoutdev; diff --git a/include/net/bluetooth/hci_core.h b/include/net/bluetooth/hci_core.h index 5f8a534b6574..09c978f3d95d 100644 --- a/include/net/bluetooth/hci_core.h +++ b/include/net/bluetooth/hci_core.h @@ -942,7 +942,6 @@ void hci_inquiry_cache_flush(struct hci_dev *hdev); /* ----- HCI Connections ----- */ enum { HCI_CONN_AUTH_PEND, - HCI_CONN_REAUTH_PEND, HCI_CONN_ENCRYPT_PEND, HCI_CONN_RSWITCH_PEND, HCI_CONN_MODE_CHANGE_PEND, diff --git a/include/uapi/linux/bpf.h b/include/uapi/linux/bpf.h index 92dbe89dafbf..201dc77ebbd7 100644 --- a/include/uapi/linux/bpf.h +++ b/include/uapi/linux/bpf.h @@ -4353,6 +4353,8 @@ union bpf_attr { * long bpf_get_task_stack(struct task_struct *task, void *buf, u32 size, u64 flags) * Description * Return a user or a kernel stack in bpf program provided buffer. + * Note: the user stack will only be populated if the *task* is + * the current task; all other tasks will return -EOPNOTSUPP. * To achieve this, the helper needs *task*, which is a valid * pointer to **struct task_struct**. To store the stacktrace, the * bpf program provides *buf* with a nonnegative *size*. @@ -4364,6 +4366,7 @@ union bpf_attr { * * **BPF_F_USER_STACK** * Collect a user space stack instead of a kernel stack. + * The *task* must be the current task. * **BPF_F_USER_BUILD_ID** * Collect buildid+offset instead of ips for user stack, * only valid if **BPF_F_USER_STACK** is also specified. diff --git a/init/do_mounts.c b/init/do_mounts.c index 811e94daf0a8..2d705b9c8400 100644 --- a/init/do_mounts.c +++ b/init/do_mounts.c @@ -665,7 +665,10 @@ struct file_system_type rootfs_fs_type = {
void __init init_rootfs(void) { - if (IS_ENABLED(CONFIG_TMPFS) && !saved_root_name[0] && - (!root_fs_names || strstr(root_fs_names, "tmpfs"))) - is_tmpfs = true; + if (IS_ENABLED(CONFIG_TMPFS)) { + if (!saved_root_name[0] && !root_fs_names) + is_tmpfs = true; + else if (root_fs_names && !!strstr(root_fs_names, "tmpfs")) + is_tmpfs = true; + } } diff --git a/io_uring/rw.c b/io_uring/rw.c index 0133db648d8e..038e6b13a749 100644 --- a/io_uring/rw.c +++ b/io_uring/rw.c @@ -534,15 +534,19 @@ static inline int io_rw_prep_async(struct io_kiocb *req, int rw) struct iovec *iov; int ret;
+ iorw->bytes_done = 0; + iorw->free_iovec = NULL; + /* submission path, ->uring_lock should already be taken */ ret = io_import_iovec(rw, req, &iov, &iorw->s, 0); if (unlikely(ret < 0)) return ret;
- iorw->bytes_done = 0; - iorw->free_iovec = iov; - if (iov) + if (iov) { + iorw->free_iovec = iov; req->flags |= REQ_F_NEED_CLEANUP; + } + return 0; }
diff --git a/kernel/bpf/arraymap.c b/kernel/bpf/arraymap.c index 00f23febb9a7..c04e69f34e4d 100644 --- a/kernel/bpf/arraymap.c +++ b/kernel/bpf/arraymap.c @@ -852,7 +852,7 @@ int bpf_fd_array_map_update_elem(struct bpf_map *map, struct file *map_file, }
if (old_ptr) - map->ops->map_fd_put_ptr(old_ptr); + map->ops->map_fd_put_ptr(map, old_ptr, true); return 0; }
@@ -875,7 +875,7 @@ static int fd_array_map_delete_elem(struct bpf_map *map, void *key) }
if (old_ptr) { - map->ops->map_fd_put_ptr(old_ptr); + map->ops->map_fd_put_ptr(map, old_ptr, true); return 0; } else { return -ENOENT; @@ -898,8 +898,9 @@ static void *prog_fd_array_get_ptr(struct bpf_map *map, return prog; }
-static void prog_fd_array_put_ptr(void *ptr) +static void prog_fd_array_put_ptr(struct bpf_map *map, void *ptr, bool need_defer) { + /* bpf_prog is freed after one RCU or tasks trace grace period */ bpf_prog_put(ptr); }
@@ -1185,8 +1186,9 @@ static void *perf_event_fd_array_get_ptr(struct bpf_map *map, return ee; }
-static void perf_event_fd_array_put_ptr(void *ptr) +static void perf_event_fd_array_put_ptr(struct bpf_map *map, void *ptr, bool need_defer) { + /* bpf_perf_event is freed after one RCU grace period */ bpf_event_entry_free_rcu(ptr); }
@@ -1239,7 +1241,7 @@ static void *cgroup_fd_array_get_ptr(struct bpf_map *map, return cgroup_get_from_fd(fd); }
-static void cgroup_fd_array_put_ptr(void *ptr) +static void cgroup_fd_array_put_ptr(struct bpf_map *map, void *ptr, bool need_defer) { /* cgroup_put free cgrp after a rcu grace period */ cgroup_put(ptr); diff --git a/kernel/bpf/hashtab.c b/kernel/bpf/hashtab.c index ce0051eee746..88c71de0a0a9 100644 --- a/kernel/bpf/hashtab.c +++ b/kernel/bpf/hashtab.c @@ -880,7 +880,7 @@ static void htab_put_fd_value(struct bpf_htab *htab, struct htab_elem *l)
if (map->ops->map_fd_put_ptr) { ptr = fd_htab_map_get_ptr(map, l); - map->ops->map_fd_put_ptr(ptr); + map->ops->map_fd_put_ptr(map, ptr, true); } }
@@ -2424,7 +2424,7 @@ static void fd_htab_map_free(struct bpf_map *map) hlist_nulls_for_each_entry_safe(l, n, head, hash_node) { void *ptr = fd_htab_map_get_ptr(map, l);
- map->ops->map_fd_put_ptr(ptr); + map->ops->map_fd_put_ptr(map, ptr, false); } }
@@ -2465,7 +2465,7 @@ int bpf_fd_htab_map_update_elem(struct bpf_map *map, struct file *map_file,
ret = htab_map_update_elem(map, key, &ptr, map_flags); if (ret) - map->ops->map_fd_put_ptr(ptr); + map->ops->map_fd_put_ptr(map, ptr, false);
return ret; } diff --git a/kernel/bpf/lpm_trie.c b/kernel/bpf/lpm_trie.c index d833496e9e42..ce3a091d52e8 100644 --- a/kernel/bpf/lpm_trie.c +++ b/kernel/bpf/lpm_trie.c @@ -231,6 +231,9 @@ static void *trie_lookup_elem(struct bpf_map *map, void *_key) struct lpm_trie_node *node, *found = NULL; struct bpf_lpm_trie_key *key = _key;
+ if (key->prefixlen > trie->max_prefixlen) + return NULL; + /* Start walking the trie from the root node ... */
for (node = rcu_dereference_check(trie->root, rcu_read_lock_bh_held()); diff --git a/kernel/bpf/map_in_map.c b/kernel/bpf/map_in_map.c index 8e87f69aae60..141f3332038c 100644 --- a/kernel/bpf/map_in_map.c +++ b/kernel/bpf/map_in_map.c @@ -115,12 +115,17 @@ void *bpf_map_fd_get_ptr(struct bpf_map *map, return inner_map; }
-void bpf_map_fd_put_ptr(void *ptr) +void bpf_map_fd_put_ptr(struct bpf_map *map, void *ptr, bool need_defer) { - /* ptr->ops->map_free() has to go through one - * rcu grace period by itself. + struct bpf_map *inner_map = ptr; + + /* The inner map may still be used by both non-sleepable and sleepable + * bpf program, so free it after one RCU grace period and one tasks + * trace RCU grace period. */ - bpf_map_put(ptr); + if (need_defer) + WRITE_ONCE(inner_map->free_after_mult_rcu_gp, true); + bpf_map_put(inner_map); }
u32 bpf_map_fd_sys_lookup_elem(void *ptr) diff --git a/kernel/bpf/map_in_map.h b/kernel/bpf/map_in_map.h index bcb7534afb3c..7d61602354de 100644 --- a/kernel/bpf/map_in_map.h +++ b/kernel/bpf/map_in_map.h @@ -13,7 +13,7 @@ struct bpf_map *bpf_map_meta_alloc(int inner_map_ufd); void bpf_map_meta_free(struct bpf_map *map_meta); void *bpf_map_fd_get_ptr(struct bpf_map *map, struct file *map_file, int ufd); -void bpf_map_fd_put_ptr(void *ptr); +void bpf_map_fd_put_ptr(struct bpf_map *map, void *ptr, bool need_defer); u32 bpf_map_fd_sys_lookup_elem(void *ptr);
#endif diff --git a/kernel/bpf/stackmap.c b/kernel/bpf/stackmap.c index aecea7451b61..f86db3cf7212 100644 --- a/kernel/bpf/stackmap.c +++ b/kernel/bpf/stackmap.c @@ -391,6 +391,7 @@ static long __bpf_get_stack(struct pt_regs *regs, struct task_struct *task, { u32 trace_nr, copy_len, elem_size, num_elem, max_depth; bool user_build_id = flags & BPF_F_USER_BUILD_ID; + bool crosstask = task && task != current; u32 skip = flags & BPF_F_SKIP_FIELD_MASK; bool user = flags & BPF_F_USER_STACK; struct perf_callchain_entry *trace; @@ -413,6 +414,14 @@ static long __bpf_get_stack(struct pt_regs *regs, struct task_struct *task, if (task && user && !user_mode(regs)) goto err_fault;
+ /* get_perf_callchain does not support crosstask user stack walking + * but returns an empty stack instead of NULL. + */ + if (crosstask && user) { + err = -EOPNOTSUPP; + goto clear; + } + num_elem = size / elem_size; max_depth = num_elem + skip; if (sysctl_perf_event_max_stack < max_depth) @@ -424,7 +433,7 @@ static long __bpf_get_stack(struct pt_regs *regs, struct task_struct *task, trace = get_callchain_entry_for_task(task, max_depth); else trace = get_perf_callchain(regs, 0, kernel, user, max_depth, - false, false); + crosstask, false); if (unlikely(!trace)) goto err_fault;
diff --git a/kernel/bpf/syscall.c b/kernel/bpf/syscall.c index 0c8b7733573e..8d0c38a8dcf2 100644 --- a/kernel/bpf/syscall.c +++ b/kernel/bpf/syscall.c @@ -628,6 +628,28 @@ static void bpf_map_put_uref(struct bpf_map *map) } }
+static void bpf_map_free_in_work(struct bpf_map *map) +{ + INIT_WORK(&map->work, bpf_map_free_deferred); + /* Avoid spawning kworkers, since they all might contend + * for the same mutex like slab_mutex. + */ + queue_work(system_unbound_wq, &map->work); +} + +static void bpf_map_free_rcu_gp(struct rcu_head *rcu) +{ + bpf_map_free_in_work(container_of(rcu, struct bpf_map, rcu)); +} + +static void bpf_map_free_mult_rcu_gp(struct rcu_head *rcu) +{ + if (rcu_trace_implies_rcu_gp()) + bpf_map_free_rcu_gp(rcu); + else + call_rcu(rcu, bpf_map_free_rcu_gp); +} + /* decrement map refcnt and schedule it for freeing via workqueue * (unrelying map implementation ops->map_free() might sleep) */ @@ -637,11 +659,11 @@ static void __bpf_map_put(struct bpf_map *map, bool do_idr_lock) /* bpf_map_free_id() must be called first */ bpf_map_free_id(map, do_idr_lock); btf_put(map->btf); - INIT_WORK(&map->work, bpf_map_free_deferred); - /* Avoid spawning kworkers, since they all might contend - * for the same mutex like slab_mutex. - */ - queue_work(system_unbound_wq, &map->work); + + if (READ_ONCE(map->free_after_mult_rcu_gp)) + call_rcu_tasks_trace(&map->rcu, bpf_map_free_mult_rcu_gp); + else + bpf_map_free_in_work(map); } }
@@ -3036,6 +3058,10 @@ static int bpf_tracing_prog_attach(struct bpf_prog *prog, * * - if prog->aux->dst_trampoline and tgt_prog is NULL, the program * was detached and is going for re-attachment. + * + * - if prog->aux->dst_trampoline is NULL and tgt_prog and prog->aux->attach_btf + * are NULL, then program was already attached and user did not provide + * tgt_prog_fd so we have no way to find out or create trampoline */ if (!prog->aux->dst_trampoline && !tgt_prog) { /* @@ -3049,6 +3075,11 @@ static int bpf_tracing_prog_attach(struct bpf_prog *prog, err = -EINVAL; goto out_unlock; } + /* We can allow re-attach only if we have valid attach_btf. */ + if (!prog->aux->attach_btf) { + err = -EINVAL; + goto out_unlock; + } btf_id = prog->aux->attach_btf_id; key = bpf_trampoline_compute_key(NULL, prog->aux->attach_btf, btf_id); } diff --git a/kernel/bpf/verifier.c b/kernel/bpf/verifier.c index 142e10d49fd8..23b6d57b5eef 100644 --- a/kernel/bpf/verifier.c +++ b/kernel/bpf/verifier.c @@ -3284,7 +3284,7 @@ static int check_stack_write_fixed_off(struct bpf_verifier_env *env, * so it's aligned access and [off, off + size) are within stack limits */ if (!env->allow_ptr_leaks && - state->stack[spi].slot_type[0] == STACK_SPILL && + is_spilled_reg(&state->stack[spi]) && size != BPF_REG_SIZE) { verbose(env, "attempt to corrupt spilled pointer on stack\n"); return -EACCES; @@ -4950,10 +4950,7 @@ static int check_stack_access_within_bounds(
if (tnum_is_const(reg->var_off)) { min_off = reg->var_off.value + off; - if (access_size > 0) - max_off = min_off + access_size - 1; - else - max_off = min_off; + max_off = min_off + access_size; } else { if (reg->smax_value >= BPF_MAX_VAR_OFF || reg->smin_value <= -BPF_MAX_VAR_OFF) { @@ -4962,15 +4959,12 @@ static int check_stack_access_within_bounds( return -EACCES; } min_off = reg->smin_value + off; - if (access_size > 0) - max_off = reg->smax_value + off + access_size - 1; - else - max_off = min_off; + max_off = reg->smax_value + off + access_size; }
err = check_stack_slot_within_bounds(min_off, state, type); - if (!err) - err = check_stack_slot_within_bounds(max_off, state, type); + if (!err && max_off > 0) + err = -EINVAL; /* out of stack access into non-negative offsets */
if (err) { if (tnum_is_const(reg->var_off)) { @@ -7284,6 +7278,13 @@ static int prepare_func_exit(struct bpf_verifier_env *env, int *insn_idx) verbose(env, "R0 not a scalar value\n"); return -EACCES; } + + /* we are going to rely on register's precise value */ + err = mark_reg_read(env, r0, r0->parent, REG_LIVE_READ64); + err = err ?: mark_chain_precision(env, BPF_REG_0); + if (err) + return err; + if (!tnum_in(range, r0->var_off)) { verbose_invalid_scalar(env, r0, &range, "callback return", "R0"); return -EINVAL; @@ -8540,6 +8541,10 @@ static int adjust_ptr_min_max_vals(struct bpf_verifier_env *env, }
switch (base_type(ptr_reg->type)) { + case PTR_TO_FLOW_KEYS: + if (known) + break; + fallthrough; case CONST_PTR_TO_MAP: /* smin_val represents the known value */ if (known && smin_val == 0 && opcode == BPF_ADD) diff --git a/kernel/debug/kdb/kdb_main.c b/kernel/debug/kdb/kdb_main.c index 438b868cbfa9..35aa2e98a92a 100644 --- a/kernel/debug/kdb/kdb_main.c +++ b/kernel/debug/kdb/kdb_main.c @@ -1349,8 +1349,6 @@ static int kdb_local(kdb_reason_t reason, int error, struct pt_regs *regs, /* PROMPT can only be set if we have MEM_READ permission. */ snprintf(kdb_prompt_str, CMD_BUFLEN, kdbgetenv("PROMPT"), raw_smp_processor_id()); - if (defcmd_in_progress) - strncat(kdb_prompt_str, "[defcmd]", CMD_BUFLEN);
/* * Fetch command from keyboard diff --git a/kernel/dma/coherent.c b/kernel/dma/coherent.c index c21abc77c53e..ff5683a57f77 100644 --- a/kernel/dma/coherent.c +++ b/kernel/dma/coherent.c @@ -132,8 +132,10 @@ int dma_declare_coherent_memory(struct device *dev, phys_addr_t phys_addr,
void dma_release_coherent_memory(struct device *dev) { - if (dev) + if (dev) { _dma_release_coherent_memory(dev->dma_mem); + dev->dma_mem = NULL; + } }
static void *__dma_alloc_from_coherent(struct device *dev, diff --git a/kernel/rcu/tasks.h b/kernel/rcu/tasks.h index c1f18c63b9b1..b5d5b6cf093a 100644 --- a/kernel/rcu/tasks.h +++ b/kernel/rcu/tasks.h @@ -1570,6 +1570,8 @@ static void rcu_tasks_trace_postscan(struct list_head *hop) { // Wait for late-stage exiting tasks to finish exiting. // These might have passed the call to exit_tasks_rcu_finish(). + + // If you remove the following line, update rcu_trace_implies_rcu_gp()!!! synchronize_rcu(); // Any tasks that exit after this point will set // TRC_NEED_QS_CHECKED in ->trc_reader_special.b.need_qs. diff --git a/kernel/time/tick-sched.c b/kernel/time/tick-sched.c index 798e1841d286..1a5d02224d46 100644 --- a/kernel/time/tick-sched.c +++ b/kernel/time/tick-sched.c @@ -1556,13 +1556,18 @@ void tick_setup_sched_timer(void) void tick_cancel_sched_timer(int cpu) { struct tick_sched *ts = &per_cpu(tick_cpu_sched, cpu); + ktime_t idle_sleeptime, iowait_sleeptime;
# ifdef CONFIG_HIGH_RES_TIMERS if (ts->sched_timer.base) hrtimer_cancel(&ts->sched_timer); # endif
+ idle_sleeptime = ts->idle_sleeptime; + iowait_sleeptime = ts->iowait_sleeptime; memset(ts, 0, sizeof(*ts)); + ts->idle_sleeptime = idle_sleeptime; + ts->iowait_sleeptime = iowait_sleeptime; } #endif
diff --git a/lib/kunit/debugfs.c b/lib/kunit/debugfs.c index b08bb1fba106..de5e71458358 100644 --- a/lib/kunit/debugfs.c +++ b/lib/kunit/debugfs.c @@ -52,12 +52,14 @@ static void debugfs_print_result(struct seq_file *seq, static int debugfs_print_results(struct seq_file *seq, void *v) { struct kunit_suite *suite = (struct kunit_suite *)seq->private; - enum kunit_status success = kunit_suite_has_succeeded(suite); + enum kunit_status success; struct kunit_case *test_case;
if (!suite) return 0;
+ success = kunit_suite_has_succeeded(suite); + /* Print KTAP header so the debugfs log can be parsed as valid KTAP. */ seq_puts(seq, "KTAP version 1\n"); seq_puts(seq, "1..1\n"); diff --git a/net/bluetooth/hci_conn.c b/net/bluetooth/hci_conn.c index 55e0ecd88543..12d36875358b 100644 --- a/net/bluetooth/hci_conn.c +++ b/net/bluetooth/hci_conn.c @@ -2314,12 +2314,10 @@ static int hci_conn_auth(struct hci_conn *conn, __u8 sec_level, __u8 auth_type) hci_send_cmd(conn->hdev, HCI_OP_AUTH_REQUESTED, sizeof(cp), &cp);
- /* If we're already encrypted set the REAUTH_PEND flag, - * otherwise set the ENCRYPT_PEND. + /* Set the ENCRYPT_PEND to trigger encryption after + * authentication. */ - if (test_bit(HCI_CONN_ENCRYPT, &conn->flags)) - set_bit(HCI_CONN_REAUTH_PEND, &conn->flags); - else + if (!test_bit(HCI_CONN_ENCRYPT, &conn->flags)) set_bit(HCI_CONN_ENCRYPT_PEND, &conn->flags); }
diff --git a/net/bluetooth/hci_debugfs.c b/net/bluetooth/hci_debugfs.c index 3f401ec5bb0c..6124b3425f35 100644 --- a/net/bluetooth/hci_debugfs.c +++ b/net/bluetooth/hci_debugfs.c @@ -1045,10 +1045,12 @@ static int min_key_size_set(void *data, u64 val) { struct hci_dev *hdev = data;
- if (val > hdev->le_max_key_size || val < SMP_MIN_ENC_KEY_SIZE) + hci_dev_lock(hdev); + if (val > hdev->le_max_key_size || val < SMP_MIN_ENC_KEY_SIZE) { + hci_dev_unlock(hdev); return -EINVAL; + }
- hci_dev_lock(hdev); hdev->le_min_key_size = val; hci_dev_unlock(hdev);
@@ -1073,10 +1075,12 @@ static int max_key_size_set(void *data, u64 val) { struct hci_dev *hdev = data;
- if (val > SMP_MAX_ENC_KEY_SIZE || val < hdev->le_min_key_size) + hci_dev_lock(hdev); + if (val > SMP_MAX_ENC_KEY_SIZE || val < hdev->le_min_key_size) { + hci_dev_unlock(hdev); return -EINVAL; + }
- hci_dev_lock(hdev); hdev->le_max_key_size = val; hci_dev_unlock(hdev);
diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c index dcb13c64e8e7..56ecc5f97b91 100644 --- a/net/bluetooth/hci_event.c +++ b/net/bluetooth/hci_event.c @@ -3511,14 +3511,8 @@ static void hci_auth_complete_evt(struct hci_dev *hdev, void *data,
if (!ev->status) { clear_bit(HCI_CONN_AUTH_FAILURE, &conn->flags); - - if (!hci_conn_ssp_enabled(conn) && - test_bit(HCI_CONN_REAUTH_PEND, &conn->flags)) { - bt_dev_info(hdev, "re-auth of legacy device is not possible."); - } else { - set_bit(HCI_CONN_AUTH, &conn->flags); - conn->sec_level = conn->pending_sec_level; - } + set_bit(HCI_CONN_AUTH, &conn->flags); + conn->sec_level = conn->pending_sec_level; } else { if (ev->status == HCI_ERROR_PIN_OR_KEY_MISSING) set_bit(HCI_CONN_AUTH_FAILURE, &conn->flags); @@ -3527,7 +3521,6 @@ static void hci_auth_complete_evt(struct hci_dev *hdev, void *data, }
clear_bit(HCI_CONN_AUTH_PEND, &conn->flags); - clear_bit(HCI_CONN_REAUTH_PEND, &conn->flags);
if (conn->state == BT_CONFIG) { if (!ev->status && hci_conn_ssp_enabled(conn)) { diff --git a/net/bridge/br_netfilter_hooks.c b/net/bridge/br_netfilter_hooks.c index 01d690d9fe5f..202ad43e35d6 100644 --- a/net/bridge/br_netfilter_hooks.c +++ b/net/bridge/br_netfilter_hooks.c @@ -279,8 +279,17 @@ int br_nf_pre_routing_finish_bridge(struct net *net, struct sock *sk, struct sk_
if ((READ_ONCE(neigh->nud_state) & NUD_CONNECTED) && READ_ONCE(neigh->hh.hh_len)) { + struct net_device *br_indev; + + br_indev = nf_bridge_get_physindev(skb, net); + if (!br_indev) { + neigh_release(neigh); + goto free_skb; + } + neigh_hh_bridge(&neigh->hh, skb); - skb->dev = nf_bridge->physindev; + skb->dev = br_indev; + ret = br_handle_frame_finish(net, sk, skb); } else { /* the neighbour function below overwrites the complete @@ -352,12 +361,18 @@ br_nf_ipv4_daddr_was_changed(const struct sk_buff *skb, */ static int br_nf_pre_routing_finish(struct net *net, struct sock *sk, struct sk_buff *skb) { - struct net_device *dev = skb->dev; + struct net_device *dev = skb->dev, *br_indev; struct iphdr *iph = ip_hdr(skb); struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb); struct rtable *rt; int err;
+ br_indev = nf_bridge_get_physindev(skb, net); + if (!br_indev) { + kfree_skb(skb); + return 0; + } + nf_bridge->frag_max_size = IPCB(skb)->frag_max_size;
if (nf_bridge->pkt_otherhost) { @@ -397,7 +412,7 @@ static int br_nf_pre_routing_finish(struct net *net, struct sock *sk, struct sk_ } else { if (skb_dst(skb)->dev == dev) { bridged_dnat: - skb->dev = nf_bridge->physindev; + skb->dev = br_indev; nf_bridge_update_protocol(skb); nf_bridge_push_encap_header(skb); br_nf_hook_thresh(NF_BR_PRE_ROUTING, @@ -410,7 +425,7 @@ static int br_nf_pre_routing_finish(struct net *net, struct sock *sk, struct sk_ skb->pkt_type = PACKET_HOST; } } else { - rt = bridge_parent_rtable(nf_bridge->physindev); + rt = bridge_parent_rtable(br_indev); if (!rt) { kfree_skb(skb); return 0; @@ -419,7 +434,7 @@ static int br_nf_pre_routing_finish(struct net *net, struct sock *sk, struct sk_ skb_dst_set_noref(skb, &rt->dst); }
- skb->dev = nf_bridge->physindev; + skb->dev = br_indev; nf_bridge_update_protocol(skb); nf_bridge_push_encap_header(skb); br_nf_hook_thresh(NF_BR_PRE_ROUTING, net, sk, skb, skb->dev, NULL, @@ -456,7 +471,7 @@ struct net_device *setup_pre_routing(struct sk_buff *skb, const struct net *net) }
nf_bridge->in_prerouting = 1; - nf_bridge->physindev = skb->dev; + nf_bridge->physinif = skb->dev->ifindex; skb->dev = brnf_get_logical_dev(skb, skb->dev, net);
if (skb->protocol == htons(ETH_P_8021Q)) @@ -553,7 +568,11 @@ static int br_nf_forward_finish(struct net *net, struct sock *sk, struct sk_buff if (skb->protocol == htons(ETH_P_IPV6)) nf_bridge->frag_max_size = IP6CB(skb)->frag_max_size;
- in = nf_bridge->physindev; + in = nf_bridge_get_physindev(skb, net); + if (!in) { + kfree_skb(skb); + return 0; + } if (nf_bridge->pkt_otherhost) { skb->pkt_type = PACKET_OTHERHOST; nf_bridge->pkt_otherhost = false; @@ -897,6 +916,13 @@ static unsigned int ip_sabotage_in(void *priv, static void br_nf_pre_routing_finish_bridge_slow(struct sk_buff *skb) { struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb); + struct net_device *br_indev; + + br_indev = nf_bridge_get_physindev(skb, dev_net(skb->dev)); + if (!br_indev) { + kfree_skb(skb); + return; + }
skb_pull(skb, ETH_HLEN); nf_bridge->bridged_dnat = 0; @@ -906,7 +932,7 @@ static void br_nf_pre_routing_finish_bridge_slow(struct sk_buff *skb) skb_copy_to_linear_data_offset(skb, -(ETH_HLEN - ETH_ALEN), nf_bridge->neigh_header, ETH_HLEN - ETH_ALEN); - skb->dev = nf_bridge->physindev; + skb->dev = br_indev;
nf_bridge->physoutdev = NULL; br_handle_frame_finish(dev_net(skb->dev), NULL, skb); diff --git a/net/bridge/br_netfilter_ipv6.c b/net/bridge/br_netfilter_ipv6.c index 6b07f30675bb..cd24ab9bb136 100644 --- a/net/bridge/br_netfilter_ipv6.c +++ b/net/bridge/br_netfilter_ipv6.c @@ -161,9 +161,15 @@ static int br_nf_pre_routing_finish_ipv6(struct net *net, struct sock *sk, struc { struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb); struct rtable *rt; - struct net_device *dev = skb->dev; + struct net_device *dev = skb->dev, *br_indev; const struct nf_ipv6_ops *v6ops = nf_get_ipv6_ops();
+ br_indev = nf_bridge_get_physindev(skb, net); + if (!br_indev) { + kfree_skb(skb); + return 0; + } + nf_bridge->frag_max_size = IP6CB(skb)->frag_max_size;
if (nf_bridge->pkt_otherhost) { @@ -181,7 +187,7 @@ static int br_nf_pre_routing_finish_ipv6(struct net *net, struct sock *sk, struc }
if (skb_dst(skb)->dev == dev) { - skb->dev = nf_bridge->physindev; + skb->dev = br_indev; nf_bridge_update_protocol(skb); nf_bridge_push_encap_header(skb); br_nf_hook_thresh(NF_BR_PRE_ROUTING, @@ -192,7 +198,7 @@ static int br_nf_pre_routing_finish_ipv6(struct net *net, struct sock *sk, struc ether_addr_copy(eth_hdr(skb)->h_dest, dev->dev_addr); skb->pkt_type = PACKET_HOST; } else { - rt = bridge_parent_rtable(nf_bridge->physindev); + rt = bridge_parent_rtable(br_indev); if (!rt) { kfree_skb(skb); return 0; @@ -201,7 +207,7 @@ static int br_nf_pre_routing_finish_ipv6(struct net *net, struct sock *sk, struc skb_dst_set_noref(skb, &rt->dst); }
- skb->dev = nf_bridge->physindev; + skb->dev = br_indev; nf_bridge_update_protocol(skb); nf_bridge_push_encap_header(skb); br_nf_hook_thresh(NF_BR_PRE_ROUTING, net, sk, skb, diff --git a/net/core/rtnetlink.c b/net/core/rtnetlink.c index 854b3fd66b1b..7cf1e42d7f93 100644 --- a/net/core/rtnetlink.c +++ b/net/core/rtnetlink.c @@ -2797,13 +2797,6 @@ static int do_setlink(const struct sk_buff *skb, call_netdevice_notifiers(NETDEV_CHANGEADDR, dev); }
- if (tb[IFLA_MASTER]) { - err = do_set_master(dev, nla_get_u32(tb[IFLA_MASTER]), extack); - if (err) - goto errout; - status |= DO_SETLINK_MODIFIED; - } - if (ifm->ifi_flags || ifm->ifi_change) { err = dev_change_flags(dev, rtnl_dev_combine_flags(dev, ifm), extack); @@ -2811,6 +2804,13 @@ static int do_setlink(const struct sk_buff *skb, goto errout; }
+ if (tb[IFLA_MASTER]) { + err = do_set_master(dev, nla_get_u32(tb[IFLA_MASTER]), extack); + if (err) + goto errout; + status |= DO_SETLINK_MODIFIED; + } + if (tb[IFLA_CARRIER]) { err = dev_change_carrier(dev, nla_get_u8(tb[IFLA_CARRIER])); if (err) diff --git a/net/dns_resolver/dns_key.c b/net/dns_resolver/dns_key.c index 8324e9f97066..26a9d8434c23 100644 --- a/net/dns_resolver/dns_key.c +++ b/net/dns_resolver/dns_key.c @@ -104,7 +104,7 @@ dns_resolver_preparse(struct key_preparsed_payload *prep) const struct dns_server_list_v1_header *v1;
/* It may be a server list. */ - if (datalen <= sizeof(*v1)) + if (datalen < sizeof(*v1)) return -EINVAL;
v1 = (const struct dns_server_list_v1_header *)data; diff --git a/net/ethtool/features.c b/net/ethtool/features.c index 55d449a2d3fc..090e493f592e 100644 --- a/net/ethtool/features.c +++ b/net/ethtool/features.c @@ -234,17 +234,20 @@ int ethnl_set_features(struct sk_buff *skb, struct genl_info *info) dev = req_info.dev;
rtnl_lock(); + ret = ethnl_ops_begin(dev); + if (ret < 0) + goto out_rtnl; ethnl_features_to_bitmap(old_active, dev->features); ethnl_features_to_bitmap(old_wanted, dev->wanted_features); ret = ethnl_parse_bitset(req_wanted, req_mask, NETDEV_FEATURE_COUNT, tb[ETHTOOL_A_FEATURES_WANTED], netdev_features_strings, info->extack); if (ret < 0) - goto out_rtnl; + goto out_ops; if (ethnl_bitmap_to_features(req_mask) & ~NETIF_F_ETHTOOL_BITS) { GENL_SET_ERR_MSG(info, "attempt to change non-ethtool features"); ret = -EINVAL; - goto out_rtnl; + goto out_ops; }
/* set req_wanted bits not in req_mask from old_wanted */ @@ -281,6 +284,8 @@ int ethnl_set_features(struct sk_buff *skb, struct genl_info *info) if (mod) netdev_features_change(dev);
+out_ops: + ethnl_ops_complete(dev); out_rtnl: rtnl_unlock(); ethnl_parse_header_dev_put(&req_info); diff --git a/net/ipv4/af_inet.c b/net/ipv4/af_inet.c index 347c3768df6e..c13b8ed63f87 100644 --- a/net/ipv4/af_inet.c +++ b/net/ipv4/af_inet.c @@ -1642,6 +1642,7 @@ int inet_recv_error(struct sock *sk, struct msghdr *msg, int len, int *addr_len) #endif return -EINVAL; } +EXPORT_SYMBOL(inet_recv_error);
int inet_gro_complete(struct sk_buff *skb, int nhoff) { diff --git a/net/ipv4/ipmr.c b/net/ipv4/ipmr.c index e04544ac4b45..b807197475a5 100644 --- a/net/ipv4/ipmr.c +++ b/net/ipv4/ipmr.c @@ -1025,6 +1025,10 @@ static int ipmr_cache_report(const struct mr_table *mrt, struct sk_buff *skb; int ret;
+ mroute_sk = rcu_dereference(mrt->mroute_sk); + if (!mroute_sk) + return -EINVAL; + if (assert == IGMPMSG_WHOLEPKT || assert == IGMPMSG_WRVIFWHOLE) skb = skb_realloc_headroom(pkt, sizeof(struct iphdr)); else @@ -1069,7 +1073,8 @@ static int ipmr_cache_report(const struct mr_table *mrt, msg = (struct igmpmsg *)skb_network_header(skb); msg->im_vif = vifi; msg->im_vif_hi = vifi >> 8; - skb_dst_set(skb, dst_clone(skb_dst(pkt))); + ipv4_pktinfo_prepare(mroute_sk, pkt); + memcpy(skb->cb, pkt->cb, sizeof(skb->cb)); /* Add our header */ igmp = skb_put(skb, sizeof(struct igmphdr)); igmp->type = assert; @@ -1079,12 +1084,6 @@ static int ipmr_cache_report(const struct mr_table *mrt, skb->transport_header = skb->network_header; }
- mroute_sk = rcu_dereference(mrt->mroute_sk); - if (!mroute_sk) { - kfree_skb(skb); - return -EINVAL; - } - igmpmsg_netlink_event(mrt, skb);
/* Deliver to mrouted */ diff --git a/net/ipv4/netfilter/nf_reject_ipv4.c b/net/ipv4/netfilter/nf_reject_ipv4.c index d640adcaf1b1..4073762996e2 100644 --- a/net/ipv4/netfilter/nf_reject_ipv4.c +++ b/net/ipv4/netfilter/nf_reject_ipv4.c @@ -239,7 +239,6 @@ static int nf_reject_fill_skb_dst(struct sk_buff *skb_in) void nf_send_reset(struct net *net, struct sock *sk, struct sk_buff *oldskb, int hook) { - struct net_device *br_indev __maybe_unused; struct sk_buff *nskb; struct iphdr *niph; const struct tcphdr *oth; @@ -288,9 +287,13 @@ void nf_send_reset(struct net *net, struct sock *sk, struct sk_buff *oldskb, * build the eth header using the original destination's MAC as the * source, and send the RST packet directly. */ - br_indev = nf_bridge_get_physindev(oldskb); - if (br_indev) { + if (nf_bridge_info_exists(oldskb)) { struct ethhdr *oeth = eth_hdr(oldskb); + struct net_device *br_indev; + + br_indev = nf_bridge_get_physindev(oldskb, net); + if (!br_indev) + goto free_nskb;
nskb->dev = br_indev; niph->tot_len = htons(nskb->len); diff --git a/net/ipv4/udp.c b/net/ipv4/udp.c index 5672d9a86c5d..11c0e1c66642 100644 --- a/net/ipv4/udp.c +++ b/net/ipv4/udp.c @@ -823,7 +823,7 @@ void udp_flush_pending_frames(struct sock *sk)
if (up->pending) { up->len = 0; - up->pending = 0; + WRITE_ONCE(up->pending, 0); ip_flush_pending_frames(sk); } } @@ -1010,7 +1010,7 @@ int udp_push_pending_frames(struct sock *sk)
out: up->len = 0; - up->pending = 0; + WRITE_ONCE(up->pending, 0); return err; } EXPORT_SYMBOL(udp_push_pending_frames); @@ -1086,7 +1086,7 @@ int udp_sendmsg(struct sock *sk, struct msghdr *msg, size_t len) getfrag = is_udplite ? udplite_getfrag : ip_generic_getfrag;
fl4 = &inet->cork.fl.u.ip4; - if (up->pending) { + if (READ_ONCE(up->pending)) { /* * There are pending frames. * The socket lock must be held while it's corked. @@ -1287,7 +1287,7 @@ int udp_sendmsg(struct sock *sk, struct msghdr *msg, size_t len) fl4->saddr = saddr; fl4->fl4_dport = dport; fl4->fl4_sport = inet->inet_sport; - up->pending = AF_INET; + WRITE_ONCE(up->pending, AF_INET);
do_append_data: up->len += ulen; @@ -1299,7 +1299,7 @@ int udp_sendmsg(struct sock *sk, struct msghdr *msg, size_t len) else if (!corkreq) err = udp_push_pending_frames(sk); else if (unlikely(skb_queue_empty(&sk->sk_write_queue))) - up->pending = 0; + WRITE_ONCE(up->pending, 0); release_sock(sk);
out: @@ -1337,7 +1337,7 @@ void udp_splice_eof(struct socket *sock) struct sock *sk = sock->sk; struct udp_sock *up = udp_sk(sk);
- if (!up->pending || udp_test_bit(CORK, sk)) + if (!READ_ONCE(up->pending) || udp_test_bit(CORK, sk)) return;
lock_sock(sk); diff --git a/net/ipv6/ip6_tunnel.c b/net/ipv6/ip6_tunnel.c index afc922c88d17..9125e92d9917 100644 --- a/net/ipv6/ip6_tunnel.c +++ b/net/ipv6/ip6_tunnel.c @@ -399,7 +399,7 @@ __u16 ip6_tnl_parse_tlv_enc_lim(struct sk_buff *skb, __u8 *raw) const struct ipv6hdr *ipv6h = (const struct ipv6hdr *)raw; unsigned int nhoff = raw - skb->data; unsigned int off = nhoff + sizeof(*ipv6h); - u8 next, nexthdr = ipv6h->nexthdr; + u8 nexthdr = ipv6h->nexthdr;
while (ipv6_ext_hdr(nexthdr) && nexthdr != NEXTHDR_NONE) { struct ipv6_opt_hdr *hdr; @@ -410,25 +410,25 @@ __u16 ip6_tnl_parse_tlv_enc_lim(struct sk_buff *skb, __u8 *raw)
hdr = (struct ipv6_opt_hdr *)(skb->data + off); if (nexthdr == NEXTHDR_FRAGMENT) { - struct frag_hdr *frag_hdr = (struct frag_hdr *) hdr; - if (frag_hdr->frag_off) - break; optlen = 8; } else if (nexthdr == NEXTHDR_AUTH) { optlen = ipv6_authlen(hdr); } else { optlen = ipv6_optlen(hdr); } - /* cache hdr->nexthdr, since pskb_may_pull() might - * invalidate hdr - */ - next = hdr->nexthdr; - if (nexthdr == NEXTHDR_DEST) { - u16 i = 2;
- /* Remember : hdr is no longer valid at this point. */ - if (!pskb_may_pull(skb, off + optlen)) + if (!pskb_may_pull(skb, off + optlen)) + break; + + hdr = (struct ipv6_opt_hdr *)(skb->data + off); + if (nexthdr == NEXTHDR_FRAGMENT) { + struct frag_hdr *frag_hdr = (struct frag_hdr *)hdr; + + if (frag_hdr->frag_off) break; + } + if (nexthdr == NEXTHDR_DEST) { + u16 i = 2;
while (1) { struct ipv6_tlv_tnl_enc_lim *tel; @@ -449,7 +449,7 @@ __u16 ip6_tnl_parse_tlv_enc_lim(struct sk_buff *skb, __u8 *raw) i++; } } - nexthdr = next; + nexthdr = hdr->nexthdr; off += optlen; } return 0; diff --git a/net/ipv6/mcast.c b/net/ipv6/mcast.c index 7860383295d8..566f3b7b957e 100644 --- a/net/ipv6/mcast.c +++ b/net/ipv6/mcast.c @@ -2725,8 +2725,12 @@ void ipv6_mc_down(struct inet6_dev *idev) synchronize_net(); mld_query_stop_work(idev); mld_report_stop_work(idev); + + mutex_lock(&idev->mc_lock); mld_ifc_stop_work(idev); mld_gq_stop_work(idev); + mutex_unlock(&idev->mc_lock); + mld_dad_stop_work(idev); }
diff --git a/net/ipv6/netfilter/nf_reject_ipv6.c b/net/ipv6/netfilter/nf_reject_ipv6.c index f61d4f18e1cf..433d98bbe33f 100644 --- a/net/ipv6/netfilter/nf_reject_ipv6.c +++ b/net/ipv6/netfilter/nf_reject_ipv6.c @@ -278,7 +278,6 @@ static int nf_reject6_fill_skb_dst(struct sk_buff *skb_in) void nf_send_reset6(struct net *net, struct sock *sk, struct sk_buff *oldskb, int hook) { - struct net_device *br_indev __maybe_unused; struct sk_buff *nskb; struct tcphdr _otcph; const struct tcphdr *otcph; @@ -353,9 +352,15 @@ void nf_send_reset6(struct net *net, struct sock *sk, struct sk_buff *oldskb, * build the eth header using the original destination's MAC as the * source, and send the RST packet directly. */ - br_indev = nf_bridge_get_physindev(oldskb); - if (br_indev) { + if (nf_bridge_info_exists(oldskb)) { struct ethhdr *oeth = eth_hdr(oldskb); + struct net_device *br_indev; + + br_indev = nf_bridge_get_physindev(oldskb, net); + if (!br_indev) { + kfree_skb(nskb); + return; + }
nskb->dev = br_indev; nskb->protocol = htons(ETH_P_IPV6); diff --git a/net/ipv6/udp.c b/net/ipv6/udp.c index 961106eda69d..c2c02dea6c38 100644 --- a/net/ipv6/udp.c +++ b/net/ipv6/udp.c @@ -1152,7 +1152,7 @@ static void udp_v6_flush_pending_frames(struct sock *sk) udp_flush_pending_frames(sk); else if (up->pending) { up->len = 0; - up->pending = 0; + WRITE_ONCE(up->pending, 0); ip6_flush_pending_frames(sk); } } @@ -1330,7 +1330,7 @@ static int udp_v6_push_pending_frames(struct sock *sk) &inet_sk(sk)->cork.base); out: up->len = 0; - up->pending = 0; + WRITE_ONCE(up->pending, 0); return err; }
@@ -1387,7 +1387,7 @@ int udpv6_sendmsg(struct sock *sk, struct msghdr *msg, size_t len) default: return -EINVAL; } - } else if (!up->pending) { + } else if (!READ_ONCE(up->pending)) { if (sk->sk_state != TCP_ESTABLISHED) return -EDESTADDRREQ; daddr = &sk->sk_v6_daddr; @@ -1418,8 +1418,8 @@ int udpv6_sendmsg(struct sock *sk, struct msghdr *msg, size_t len) return -EMSGSIZE;
getfrag = is_udplite ? udplite_getfrag : ip_generic_getfrag; - if (up->pending) { - if (up->pending == AF_INET) + if (READ_ONCE(up->pending)) { + if (READ_ONCE(up->pending) == AF_INET) return udp_sendmsg(sk, msg, len); /* * There are pending frames. @@ -1609,7 +1609,7 @@ int udpv6_sendmsg(struct sock *sk, struct msghdr *msg, size_t len) goto out; }
- up->pending = AF_INET6; + WRITE_ONCE(up->pending, AF_INET6);
do_append_data: if (ipc6.dontfrag < 0) @@ -1623,7 +1623,7 @@ int udpv6_sendmsg(struct sock *sk, struct msghdr *msg, size_t len) else if (!corkreq) err = udp_v6_push_pending_frames(sk); else if (unlikely(skb_queue_empty(&sk->sk_write_queue))) - up->pending = 0; + WRITE_ONCE(up->pending, 0);
if (err > 0) err = np->recverr ? net_xmit_errno(err) : 0; @@ -1663,7 +1663,7 @@ static void udpv6_splice_eof(struct socket *sock) struct sock *sk = sock->sk; struct udp_sock *up = udp_sk(sk);
- if (!up->pending || udp_test_bit(CORK, sk)) + if (!READ_ONCE(up->pending) || udp_test_bit(CORK, sk)) return;
lock_sock(sk); diff --git a/net/mptcp/options.c b/net/mptcp/options.c index 74027bb5b429..a718ebcb5bc6 100644 --- a/net/mptcp/options.c +++ b/net/mptcp/options.c @@ -118,8 +118,8 @@ static void mptcp_parse_option(const struct sk_buff *skb, break;
case MPTCPOPT_MP_JOIN: - mp_opt->suboptions |= OPTIONS_MPTCP_MPJ; if (opsize == TCPOLEN_MPTCP_MPJ_SYN) { + mp_opt->suboptions |= OPTION_MPTCP_MPJ_SYN; mp_opt->backup = *ptr++ & MPTCPOPT_BACKUP; mp_opt->join_id = *ptr++; mp_opt->token = get_unaligned_be32(ptr); @@ -130,6 +130,7 @@ static void mptcp_parse_option(const struct sk_buff *skb, mp_opt->backup, mp_opt->join_id, mp_opt->token, mp_opt->nonce); } else if (opsize == TCPOLEN_MPTCP_MPJ_SYNACK) { + mp_opt->suboptions |= OPTION_MPTCP_MPJ_SYNACK; mp_opt->backup = *ptr++ & MPTCPOPT_BACKUP; mp_opt->join_id = *ptr++; mp_opt->thmac = get_unaligned_be64(ptr); @@ -140,11 +141,10 @@ static void mptcp_parse_option(const struct sk_buff *skb, mp_opt->backup, mp_opt->join_id, mp_opt->thmac, mp_opt->nonce); } else if (opsize == TCPOLEN_MPTCP_MPJ_ACK) { + mp_opt->suboptions |= OPTION_MPTCP_MPJ_ACK; ptr += 2; memcpy(mp_opt->hmac, ptr, MPTCPOPT_HMAC_LEN); pr_debug("MP_JOIN hmac"); - } else { - mp_opt->suboptions &= ~OPTIONS_MPTCP_MPJ; } break;
diff --git a/net/mptcp/subflow.c b/net/mptcp/subflow.c index 8ed7769cae83..45d20e20cfc0 100644 --- a/net/mptcp/subflow.c +++ b/net/mptcp/subflow.c @@ -156,8 +156,8 @@ static int subflow_check_req(struct request_sock *req,
mptcp_get_options(skb, &mp_opt);
- opt_mp_capable = !!(mp_opt.suboptions & OPTIONS_MPTCP_MPC); - opt_mp_join = !!(mp_opt.suboptions & OPTIONS_MPTCP_MPJ); + opt_mp_capable = !!(mp_opt.suboptions & OPTION_MPTCP_MPC_SYN); + opt_mp_join = !!(mp_opt.suboptions & OPTION_MPTCP_MPJ_SYN); if (opt_mp_capable) { SUBFLOW_REQ_INC_STATS(req, MPTCP_MIB_MPCAPABLEPASSIVE);
@@ -253,8 +253,8 @@ int mptcp_subflow_init_cookie_req(struct request_sock *req, subflow_init_req(req, sk_listener); mptcp_get_options(skb, &mp_opt);
- opt_mp_capable = !!(mp_opt.suboptions & OPTIONS_MPTCP_MPC); - opt_mp_join = !!(mp_opt.suboptions & OPTIONS_MPTCP_MPJ); + opt_mp_capable = !!(mp_opt.suboptions & OPTION_MPTCP_MPC_ACK); + opt_mp_join = !!(mp_opt.suboptions & OPTION_MPTCP_MPJ_ACK); if (opt_mp_capable && opt_mp_join) return -EINVAL;
@@ -415,7 +415,7 @@ static void subflow_finish_connect(struct sock *sk, const struct sk_buff *skb)
mptcp_get_options(skb, &mp_opt); if (subflow->request_mptcp) { - if (!(mp_opt.suboptions & OPTIONS_MPTCP_MPC)) { + if (!(mp_opt.suboptions & OPTION_MPTCP_MPC_SYNACK)) { MPTCP_INC_STATS(sock_net(sk), MPTCP_MIB_MPCAPABLEACTIVEFALLBACK); mptcp_do_fallback(sk); @@ -438,7 +438,7 @@ static void subflow_finish_connect(struct sock *sk, const struct sk_buff *skb) } else if (subflow->request_join) { u8 hmac[SHA256_DIGEST_SIZE];
- if (!(mp_opt.suboptions & OPTIONS_MPTCP_MPJ)) { + if (!(mp_opt.suboptions & OPTION_MPTCP_MPJ_SYNACK)) { subflow->reset_reason = MPTCP_RST_EMPTCP; goto do_reset; } @@ -713,12 +713,13 @@ static struct sock *subflow_syn_recv_sock(const struct sock *sk, * options. */ mptcp_get_options(skb, &mp_opt); - if (!(mp_opt.suboptions & OPTIONS_MPTCP_MPC)) + if (!(mp_opt.suboptions & + (OPTION_MPTCP_MPC_SYN | OPTION_MPTCP_MPC_ACK))) fallback = true;
} else if (subflow_req->mp_join) { mptcp_get_options(skb, &mp_opt); - if (!(mp_opt.suboptions & OPTIONS_MPTCP_MPJ) || + if (!(mp_opt.suboptions & OPTION_MPTCP_MPJ_ACK) || !subflow_hmac_valid(req, &mp_opt) || !mptcp_can_accept_new_subflow(subflow_req->msk)) { SUBFLOW_REQ_INC_STATS(req, MPTCP_MIB_JOINACKMAC); diff --git a/net/ncsi/internal.h b/net/ncsi/internal.h index 03757e76bb6b..374412ed780b 100644 --- a/net/ncsi/internal.h +++ b/net/ncsi/internal.h @@ -105,8 +105,11 @@ enum {
struct ncsi_channel_version { - u32 version; /* Supported BCD encoded NCSI version */ - u32 alpha2; /* Supported BCD encoded NCSI version */ + u8 major; /* NCSI version major */ + u8 minor; /* NCSI version minor */ + u8 update; /* NCSI version update */ + char alpha1; /* NCSI version alpha1 */ + char alpha2; /* NCSI version alpha2 */ u8 fw_name[12]; /* Firmware name string */ u32 fw_version; /* Firmware version */ u16 pci_ids[4]; /* PCI identification */ diff --git a/net/ncsi/ncsi-netlink.c b/net/ncsi/ncsi-netlink.c index d27f4eccce6d..fe681680b5d9 100644 --- a/net/ncsi/ncsi-netlink.c +++ b/net/ncsi/ncsi-netlink.c @@ -71,8 +71,8 @@ static int ncsi_write_channel_info(struct sk_buff *skb, if (nc == nc->package->preferred_channel) nla_put_flag(skb, NCSI_CHANNEL_ATTR_FORCED);
- nla_put_u32(skb, NCSI_CHANNEL_ATTR_VERSION_MAJOR, nc->version.version); - nla_put_u32(skb, NCSI_CHANNEL_ATTR_VERSION_MINOR, nc->version.alpha2); + nla_put_u32(skb, NCSI_CHANNEL_ATTR_VERSION_MAJOR, nc->version.major); + nla_put_u32(skb, NCSI_CHANNEL_ATTR_VERSION_MINOR, nc->version.minor); nla_put_string(skb, NCSI_CHANNEL_ATTR_VERSION_STR, nc->version.fw_name);
vid_nest = nla_nest_start_noflag(skb, NCSI_CHANNEL_ATTR_VLAN_LIST); diff --git a/net/ncsi/ncsi-pkt.h b/net/ncsi/ncsi-pkt.h index ba66c7dc3a21..c9d1da34dc4d 100644 --- a/net/ncsi/ncsi-pkt.h +++ b/net/ncsi/ncsi-pkt.h @@ -197,9 +197,12 @@ struct ncsi_rsp_gls_pkt { /* Get Version ID */ struct ncsi_rsp_gvi_pkt { struct ncsi_rsp_pkt_hdr rsp; /* Response header */ - __be32 ncsi_version; /* NCSI version */ + unsigned char major; /* NCSI version major */ + unsigned char minor; /* NCSI version minor */ + unsigned char update; /* NCSI version update */ + unsigned char alpha1; /* NCSI version alpha1 */ unsigned char reserved[3]; /* Reserved */ - unsigned char alpha2; /* NCSI version */ + unsigned char alpha2; /* NCSI version alpha2 */ unsigned char fw_name[12]; /* f/w name string */ __be32 fw_version; /* f/w version */ __be16 pci_ids[4]; /* PCI IDs */ diff --git a/net/ncsi/ncsi-rsp.c b/net/ncsi/ncsi-rsp.c index 069c2659074b..480e80e3c283 100644 --- a/net/ncsi/ncsi-rsp.c +++ b/net/ncsi/ncsi-rsp.c @@ -19,6 +19,19 @@ #include "ncsi-pkt.h" #include "ncsi-netlink.h"
+/* Nibbles within [0xA, 0xF] add zero "0" to the returned value. + * Optional fields (encoded as 0xFF) will default to zero. + */ +static u8 decode_bcd_u8(u8 x) +{ + int lo = x & 0xF; + int hi = x >> 4; + + lo = lo < 0xA ? lo : 0; + hi = hi < 0xA ? hi : 0; + return lo + hi * 10; +} + static int ncsi_validate_rsp_pkt(struct ncsi_request *nr, unsigned short payload) { @@ -755,9 +768,18 @@ static int ncsi_rsp_handler_gvi(struct ncsi_request *nr) if (!nc) return -ENODEV;
- /* Update to channel's version info */ + /* Update channel's version info + * + * Major, minor, and update fields are supposed to be + * unsigned integers encoded as packed BCD. + * + * Alpha1 and alpha2 are ISO/IEC 8859-1 characters. + */ ncv = &nc->version; - ncv->version = ntohl(rsp->ncsi_version); + ncv->major = decode_bcd_u8(rsp->major); + ncv->minor = decode_bcd_u8(rsp->minor); + ncv->update = decode_bcd_u8(rsp->update); + ncv->alpha1 = rsp->alpha1; ncv->alpha2 = rsp->alpha2; memcpy(ncv->fw_name, rsp->fw_name, 12); ncv->fw_version = ntohl(rsp->fw_version); diff --git a/net/netfilter/ipset/ip_set_hash_netiface.c b/net/netfilter/ipset/ip_set_hash_netiface.c index 031073286236..bf1a3851ba5a 100644 --- a/net/netfilter/ipset/ip_set_hash_netiface.c +++ b/net/netfilter/ipset/ip_set_hash_netiface.c @@ -138,9 +138,9 @@ hash_netiface4_data_next(struct hash_netiface4_elem *next, #include "ip_set_hash_gen.h"
#if IS_ENABLED(CONFIG_BRIDGE_NETFILTER) -static const char *get_physindev_name(const struct sk_buff *skb) +static const char *get_physindev_name(const struct sk_buff *skb, struct net *net) { - struct net_device *dev = nf_bridge_get_physindev(skb); + struct net_device *dev = nf_bridge_get_physindev(skb, net);
return dev ? dev->name : NULL; } @@ -177,7 +177,7 @@ hash_netiface4_kadt(struct ip_set *set, const struct sk_buff *skb,
if (opt->cmdflags & IPSET_FLAG_PHYSDEV) { #if IS_ENABLED(CONFIG_BRIDGE_NETFILTER) - const char *eiface = SRCDIR ? get_physindev_name(skb) : + const char *eiface = SRCDIR ? get_physindev_name(skb, xt_net(par)) : get_physoutdev_name(skb);
if (!eiface) @@ -395,7 +395,7 @@ hash_netiface6_kadt(struct ip_set *set, const struct sk_buff *skb,
if (opt->cmdflags & IPSET_FLAG_PHYSDEV) { #if IS_ENABLED(CONFIG_BRIDGE_NETFILTER) - const char *eiface = SRCDIR ? get_physindev_name(skb) : + const char *eiface = SRCDIR ? get_physindev_name(skb, xt_net(par)) : get_physoutdev_name(skb);
if (!eiface) diff --git a/net/netfilter/ipvs/ip_vs_xmit.c b/net/netfilter/ipvs/ip_vs_xmit.c index b452eb3ddcec..d40a4ca2b27f 100644 --- a/net/netfilter/ipvs/ip_vs_xmit.c +++ b/net/netfilter/ipvs/ip_vs_xmit.c @@ -271,7 +271,7 @@ static inline bool decrement_ttl(struct netns_ipvs *ipvs, skb->dev = dst->dev; icmpv6_send(skb, ICMPV6_TIME_EXCEED, ICMPV6_EXC_HOPLIMIT, 0); - __IP6_INC_STATS(net, idev, IPSTATS_MIB_INHDRERRORS); + IP6_INC_STATS(net, idev, IPSTATS_MIB_INHDRERRORS);
return false; } @@ -286,7 +286,7 @@ static inline bool decrement_ttl(struct netns_ipvs *ipvs, { if (ip_hdr(skb)->ttl <= 1) { /* Tell the sender its packet died... */ - __IP_INC_STATS(net, IPSTATS_MIB_INHDRERRORS); + IP_INC_STATS(net, IPSTATS_MIB_INHDRERRORS); icmp_send(skb, ICMP_TIME_EXCEEDED, ICMP_EXC_TTL, 0); return false; } diff --git a/net/netfilter/nf_log_syslog.c b/net/netfilter/nf_log_syslog.c index c66689ad2b49..58402226045e 100644 --- a/net/netfilter/nf_log_syslog.c +++ b/net/netfilter/nf_log_syslog.c @@ -111,7 +111,8 @@ nf_log_dump_packet_common(struct nf_log_buf *m, u8 pf, unsigned int hooknum, const struct sk_buff *skb, const struct net_device *in, const struct net_device *out, - const struct nf_loginfo *loginfo, const char *prefix) + const struct nf_loginfo *loginfo, const char *prefix, + struct net *net) { const struct net_device *physoutdev __maybe_unused; const struct net_device *physindev __maybe_unused; @@ -121,7 +122,7 @@ nf_log_dump_packet_common(struct nf_log_buf *m, u8 pf, in ? in->name : "", out ? out->name : ""); #if IS_ENABLED(CONFIG_BRIDGE_NETFILTER) - physindev = nf_bridge_get_physindev(skb); + physindev = nf_bridge_get_physindev(skb, net); if (physindev && in != physindev) nf_log_buf_add(m, "PHYSIN=%s ", physindev->name); physoutdev = nf_bridge_get_physoutdev(skb); @@ -148,7 +149,7 @@ static void nf_log_arp_packet(struct net *net, u_int8_t pf, loginfo = &default_loginfo;
nf_log_dump_packet_common(m, pf, hooknum, skb, in, out, loginfo, - prefix); + prefix, net); dump_arp_packet(m, loginfo, skb, skb_network_offset(skb));
nf_log_buf_close(m); @@ -845,7 +846,7 @@ static void nf_log_ip_packet(struct net *net, u_int8_t pf, loginfo = &default_loginfo;
nf_log_dump_packet_common(m, pf, hooknum, skb, in, - out, loginfo, prefix); + out, loginfo, prefix, net);
if (in) dump_mac_header(m, loginfo, skb); @@ -880,7 +881,7 @@ static void nf_log_ip6_packet(struct net *net, u_int8_t pf, loginfo = &default_loginfo;
nf_log_dump_packet_common(m, pf, hooknum, skb, in, out, - loginfo, prefix); + loginfo, prefix, net);
if (in) dump_mac_header(m, loginfo, skb); @@ -916,7 +917,7 @@ static void nf_log_unknown_packet(struct net *net, u_int8_t pf, loginfo = &default_loginfo;
nf_log_dump_packet_common(m, pf, hooknum, skb, in, out, loginfo, - prefix); + prefix, net);
dump_mac_header(m, loginfo, skb);
diff --git a/net/netfilter/nf_queue.c b/net/netfilter/nf_queue.c index 63d1516816b1..e2f334f70281 100644 --- a/net/netfilter/nf_queue.c +++ b/net/netfilter/nf_queue.c @@ -82,11 +82,9 @@ static void __nf_queue_entry_init_physdevs(struct nf_queue_entry *entry) { #if IS_ENABLED(CONFIG_BRIDGE_NETFILTER) const struct sk_buff *skb = entry->skb; - struct nf_bridge_info *nf_bridge;
- nf_bridge = nf_bridge_info_get(skb); - if (nf_bridge) { - entry->physin = nf_bridge_get_physindev(skb); + if (nf_bridge_info_exists(skb)) { + entry->physin = nf_bridge_get_physindev(skb, entry->state.net); entry->physout = nf_bridge_get_physoutdev(skb); } else { entry->physin = NULL; diff --git a/net/netfilter/nf_tables_api.c b/net/netfilter/nf_tables_api.c index 3d6ebb9877a4..2702294ac46c 100644 --- a/net/netfilter/nf_tables_api.c +++ b/net/netfilter/nf_tables_api.c @@ -4523,8 +4523,8 @@ static int nft_set_desc_concat_parse(const struct nlattr *attr, static int nft_set_desc_concat(struct nft_set_desc *desc, const struct nlattr *nla) { + u32 num_regs = 0, key_num_regs = 0; struct nlattr *attr; - u32 num_regs = 0; int rem, err, i;
nla_for_each_nested(attr, nla, rem) { @@ -4539,6 +4539,10 @@ static int nft_set_desc_concat(struct nft_set_desc *desc, for (i = 0; i < desc->field_count; i++) num_regs += DIV_ROUND_UP(desc->field_len[i], sizeof(u32));
+ key_num_regs = DIV_ROUND_UP(desc->klen, sizeof(u32)); + if (key_num_regs != num_regs) + return -EINVAL; + if (num_regs > NFT_REG32_COUNT) return -E2BIG;
@@ -4753,16 +4757,28 @@ static int nf_tables_newset(struct sk_buff *skb, const struct nfnl_info *info, }
desc.policy = NFT_SET_POL_PERFORMANCE; - if (nla[NFTA_SET_POLICY] != NULL) + if (nla[NFTA_SET_POLICY] != NULL) { desc.policy = ntohl(nla_get_be32(nla[NFTA_SET_POLICY])); + switch (desc.policy) { + case NFT_SET_POL_PERFORMANCE: + case NFT_SET_POL_MEMORY: + break; + default: + return -EOPNOTSUPP; + } + }
if (nla[NFTA_SET_DESC] != NULL) { err = nf_tables_set_desc_parse(&desc, nla[NFTA_SET_DESC]); if (err < 0) return err;
- if (desc.field_count > 1 && !(flags & NFT_SET_CONCAT)) + if (desc.field_count > 1) { + if (!(flags & NFT_SET_CONCAT)) + return -EINVAL; + } else if (flags & NFT_SET_CONCAT) { return -EINVAL; + } } else if (flags & NFT_SET_CONCAT) { return -EINVAL; } @@ -5406,7 +5422,7 @@ static int nf_tables_dump_setelem(const struct nft_ctx *ctx, const struct nft_set_ext *ext = nft_set_elem_ext(set, elem->priv); struct nft_set_dump_args *args;
- if (nft_set_elem_expired(ext)) + if (nft_set_elem_expired(ext) || nft_set_elem_is_dead(ext)) return 0;
args = container_of(iter, struct nft_set_dump_args, iter); @@ -6152,7 +6168,7 @@ static int nft_setelem_catchall_deactivate(const struct net *net,
list_for_each_entry(catchall, &set->catchall_list, list) { ext = nft_set_elem_ext(set, catchall->elem); - if (!nft_is_active(net, ext)) + if (!nft_is_active_next(net, ext)) continue;
kfree(elem->priv); @@ -9937,6 +9953,7 @@ static int __nf_tables_abort(struct net *net, enum nfnl_abort_action action) nft_trans_destroy(trans); break; } + nft_trans_set(trans)->dead = 1; list_del_rcu(&nft_trans_set(trans)->list); break; case NFT_MSG_DELSET: diff --git a/net/netfilter/nfnetlink_log.c b/net/netfilter/nfnetlink_log.c index c5ff699e3046..200a82a8f943 100644 --- a/net/netfilter/nfnetlink_log.c +++ b/net/netfilter/nfnetlink_log.c @@ -499,7 +499,7 @@ __build_packet_message(struct nfnl_log_net *log, htonl(br_port_get_rcu(indev)->br->dev->ifindex))) goto nla_put_failure; } else { - struct net_device *physindev; + int physinif;
/* Case 2: indev is bridge group, we need to look for * physical device (when called from ipv4) */ @@ -507,10 +507,10 @@ __build_packet_message(struct nfnl_log_net *log, htonl(indev->ifindex))) goto nla_put_failure;
- physindev = nf_bridge_get_physindev(skb); - if (physindev && + physinif = nf_bridge_get_physinif(skb); + if (physinif && nla_put_be32(inst->skb, NFULA_IFINDEX_PHYSINDEV, - htonl(physindev->ifindex))) + htonl(physinif))) goto nla_put_failure; } #endif diff --git a/net/netfilter/nft_limit.c b/net/netfilter/nft_limit.c index 981addb2d051..75c05ef885a9 100644 --- a/net/netfilter/nft_limit.c +++ b/net/netfilter/nft_limit.c @@ -58,6 +58,7 @@ static inline bool nft_limit_eval(struct nft_limit_priv *priv, u64 cost) static int nft_limit_init(struct nft_limit_priv *priv, const struct nlattr * const tb[], bool pkts) { + bool invert = false; u64 unit, tokens;
if (tb[NFTA_LIMIT_RATE] == NULL || @@ -90,19 +91,23 @@ static int nft_limit_init(struct nft_limit_priv *priv, priv->rate); }
+ if (tb[NFTA_LIMIT_FLAGS]) { + u32 flags = ntohl(nla_get_be32(tb[NFTA_LIMIT_FLAGS])); + + if (flags & ~NFT_LIMIT_F_INV) + return -EOPNOTSUPP; + + if (flags & NFT_LIMIT_F_INV) + invert = true; + } + priv->limit = kmalloc(sizeof(*priv->limit), GFP_KERNEL_ACCOUNT); if (!priv->limit) return -ENOMEM;
priv->limit->tokens = tokens; priv->tokens_max = priv->limit->tokens; - - if (tb[NFTA_LIMIT_FLAGS]) { - u32 flags = ntohl(nla_get_be32(tb[NFTA_LIMIT_FLAGS])); - - if (flags & NFT_LIMIT_F_INV) - priv->invert = true; - } + priv->invert = invert; priv->limit->last = ktime_get_ns(); spin_lock_init(&priv->limit->lock);
diff --git a/net/netfilter/xt_physdev.c b/net/netfilter/xt_physdev.c index ec6ed6fda96c..343e65f377d4 100644 --- a/net/netfilter/xt_physdev.c +++ b/net/netfilter/xt_physdev.c @@ -59,7 +59,7 @@ physdev_mt(const struct sk_buff *skb, struct xt_action_param *par) (!!outdev ^ !(info->invert & XT_PHYSDEV_OP_BRIDGED))) return false;
- physdev = nf_bridge_get_physindev(skb); + physdev = nf_bridge_get_physindev(skb, xt_net(par)); indev = physdev ? physdev->name : NULL;
if ((info->bitmask & XT_PHYSDEV_OP_ISIN && diff --git a/net/netlabel/netlabel_calipso.c b/net/netlabel/netlabel_calipso.c index f1d5b8465217..a07c2216d28b 100644 --- a/net/netlabel/netlabel_calipso.c +++ b/net/netlabel/netlabel_calipso.c @@ -54,6 +54,28 @@ static const struct nla_policy calipso_genl_policy[NLBL_CALIPSO_A_MAX + 1] = { [NLBL_CALIPSO_A_MTYPE] = { .type = NLA_U32 }, };
+static const struct netlbl_calipso_ops *calipso_ops; + +/** + * netlbl_calipso_ops_register - Register the CALIPSO operations + * @ops: ops to register + * + * Description: + * Register the CALIPSO packet engine operations. + * + */ +const struct netlbl_calipso_ops * +netlbl_calipso_ops_register(const struct netlbl_calipso_ops *ops) +{ + return xchg(&calipso_ops, ops); +} +EXPORT_SYMBOL(netlbl_calipso_ops_register); + +static const struct netlbl_calipso_ops *netlbl_calipso_ops_get(void) +{ + return READ_ONCE(calipso_ops); +} + /* NetLabel Command Handlers */ /** @@ -96,15 +118,18 @@ static int netlbl_calipso_add_pass(struct genl_info *info, * */ static int netlbl_calipso_add(struct sk_buff *skb, struct genl_info *info) - { int ret_val = -EINVAL; struct netlbl_audit audit_info; + const struct netlbl_calipso_ops *ops = netlbl_calipso_ops_get();
if (!info->attrs[NLBL_CALIPSO_A_DOI] || !info->attrs[NLBL_CALIPSO_A_MTYPE]) return -EINVAL;
+ if (!ops) + return -EOPNOTSUPP; + netlbl_netlink_auditinfo(&audit_info); switch (nla_get_u32(info->attrs[NLBL_CALIPSO_A_MTYPE])) { case CALIPSO_MAP_PASS: @@ -363,28 +388,6 @@ int __init netlbl_calipso_genl_init(void) return genl_register_family(&netlbl_calipso_gnl_family); }
-static const struct netlbl_calipso_ops *calipso_ops; - -/** - * netlbl_calipso_ops_register - Register the CALIPSO operations - * @ops: ops to register - * - * Description: - * Register the CALIPSO packet engine operations. - * - */ -const struct netlbl_calipso_ops * -netlbl_calipso_ops_register(const struct netlbl_calipso_ops *ops) -{ - return xchg(&calipso_ops, ops); -} -EXPORT_SYMBOL(netlbl_calipso_ops_register); - -static const struct netlbl_calipso_ops *netlbl_calipso_ops_get(void) -{ - return READ_ONCE(calipso_ops); -} - /** * calipso_doi_add - Add a new DOI to the CALIPSO protocol engine * @doi_def: the DOI structure diff --git a/net/sched/act_ct.c b/net/sched/act_ct.c index d6d33f854050..84e15116f18c 100644 --- a/net/sched/act_ct.c +++ b/net/sched/act_ct.c @@ -863,7 +863,6 @@ static int tcf_ct_handle_fragments(struct net *net, struct sk_buff *skb, if (err || !frag) return err;
- skb_get(skb); mru = tc_skb_cb(skb)->mru;
if (family == NFPROTO_IPV4) { @@ -1150,12 +1149,8 @@ static int tcf_ct_act(struct sk_buff *skb, const struct tc_action *a, nh_ofs = skb_network_offset(skb); skb_pull_rcsum(skb, nh_ofs); err = tcf_ct_handle_fragments(net, skb, family, p->zone, &defrag); - if (err == -EINPROGRESS) { - retval = TC_ACT_STOLEN; - goto out_clear; - } if (err) - goto drop; + goto out_frag;
err = tcf_ct_skb_network_trim(skb, family); if (err) @@ -1226,6 +1221,11 @@ static int tcf_ct_act(struct sk_buff *skb, const struct tc_action *a, qdisc_skb_cb(skb)->pkt_len = skb->len; return retval;
+out_frag: + if (err != -EINPROGRESS) + tcf_action_inc_drop_qstats(&c->common); + return TC_ACT_CONSUMED; + drop: tcf_action_inc_drop_qstats(&c->common); return TC_ACT_SHOT; diff --git a/net/sctp/socket.c b/net/sctp/socket.c index e25dc1709131..237a6b04adf6 100644 --- a/net/sctp/socket.c +++ b/net/sctp/socket.c @@ -2098,6 +2098,13 @@ static int sctp_recvmsg(struct sock *sk, struct msghdr *msg, size_t len, pr_debug("%s: sk:%p, msghdr:%p, len:%zd, flags:0x%x, addr_len:%p)\n", __func__, sk, msg, len, flags, addr_len);
+ if (unlikely(flags & MSG_ERRQUEUE)) + return inet_recv_error(sk, msg, len, addr_len); + + if (sk_can_busy_loop(sk) && + skb_queue_empty_lockless(&sk->sk_receive_queue)) + sk_busy_loop(sk, flags & MSG_DONTWAIT); + lock_sock(sk);
if (sctp_style(sk, TCP) && !sctp_sstate(sk, ESTABLISHED) && @@ -9038,12 +9045,6 @@ struct sk_buff *sctp_skb_recv_datagram(struct sock *sk, int flags, int *err) if (sk->sk_shutdown & RCV_SHUTDOWN) break;
- if (sk_can_busy_loop(sk)) { - sk_busy_loop(sk, flags & MSG_DONTWAIT); - - if (!skb_queue_empty_lockless(&sk->sk_receive_queue)) - continue; - }
/* User doesn't want to wait. */ error = -EAGAIN; diff --git a/net/sunrpc/xprtmultipath.c b/net/sunrpc/xprtmultipath.c index 701250b305db..74ee2271251e 100644 --- a/net/sunrpc/xprtmultipath.c +++ b/net/sunrpc/xprtmultipath.c @@ -284,7 +284,7 @@ struct rpc_xprt *_xprt_switch_find_current_entry(struct list_head *head, if (cur == pos) found = true; if (found && ((find_active && xprt_is_active(pos)) || - (!find_active && xprt_is_active(pos)))) + (!find_active && !xprt_is_active(pos)))) return pos; } return NULL; diff --git a/net/unix/unix_bpf.c b/net/unix/unix_bpf.c index 7ea7c3a0d0d0..bd84785bf8d6 100644 --- a/net/unix/unix_bpf.c +++ b/net/unix/unix_bpf.c @@ -161,15 +161,30 @@ int unix_stream_bpf_update_proto(struct sock *sk, struct sk_psock *psock, bool r { struct sock *sk_pair;
+ /* Restore does not decrement the sk_pair reference yet because we must + * keep the a reference to the socket until after an RCU grace period + * and any pending sends have completed. + */ if (restore) { sk->sk_write_space = psock->saved_write_space; sock_replace_proto(sk, psock->sk_proto); return 0; }
- sk_pair = unix_peer(sk); - sock_hold(sk_pair); - psock->sk_pair = sk_pair; + /* psock_update_sk_prot can be called multiple times if psock is + * added to multiple maps and/or slots in the same map. There is + * also an edge case where replacing a psock with itself can trigger + * an extra psock_update_sk_prot during the insert process. So it + * must be safe to do multiple calls. Here we need to ensure we don't + * increment the refcnt through sock_hold many times. There will only + * be a single matching destroy operation. + */ + if (!psock->sk_pair) { + sk_pair = unix_peer(sk); + sock_hold(sk_pair); + psock->sk_pair = sk_pair; + } + unix_stream_bpf_check_needs_rebuild(psock->sk_proto); sock_replace_proto(sk, &unix_stream_bpf_prot); return 0; diff --git a/net/vmw_vsock/virtio_transport_common.c b/net/vmw_vsock/virtio_transport_common.c index 2e25890ca52d..9983b833b55d 100644 --- a/net/vmw_vsock/virtio_transport_common.c +++ b/net/vmw_vsock/virtio_transport_common.c @@ -366,6 +366,8 @@ virtio_transport_stream_do_dequeue(struct vsock_sock *vsk, struct virtio_vsock_sock *vvs = vsk->trans; size_t bytes, total = 0; struct sk_buff *skb; + u32 fwd_cnt_delta; + bool low_rx_bytes; int err = -EFAULT; u32 free_space;
@@ -400,7 +402,10 @@ virtio_transport_stream_do_dequeue(struct vsock_sock *vsk, } }
- free_space = vvs->buf_alloc - (vvs->fwd_cnt - vvs->last_fwd_cnt); + fwd_cnt_delta = vvs->fwd_cnt - vvs->last_fwd_cnt; + free_space = vvs->buf_alloc - fwd_cnt_delta; + low_rx_bytes = (vvs->rx_bytes < + sock_rcvlowat(sk_vsock(vsk), 0, INT_MAX));
spin_unlock_bh(&vvs->rx_lock);
@@ -410,9 +415,11 @@ virtio_transport_stream_do_dequeue(struct vsock_sock *vsk, * too high causes extra messages. Too low causes transmitter * stalls. As stalls are in theory more expensive than extra * messages, we set the limit to a high value. TODO: experiment - * with different values. + * with different values. Also send credit update message when + * number of bytes in rx queue is not enough to wake up reader. */ - if (free_space < VIRTIO_VSOCK_MAX_PKT_BUF_SIZE) + if (fwd_cnt_delta && + (free_space < VIRTIO_VSOCK_MAX_PKT_BUF_SIZE || low_rx_bytes)) virtio_transport_send_credit_update(vsk);
return total; diff --git a/scripts/Makefile.compiler b/scripts/Makefile.compiler index 158c57f2acfd..87589a7ba27f 100644 --- a/scripts/Makefile.compiler +++ b/scripts/Makefile.compiler @@ -72,7 +72,3 @@ clang-min-version = $(shell [ $(CONFIG_CLANG_VERSION)0 -ge $(1)0 ] && echo y) # ld-option # Usage: KBUILD_LDFLAGS += $(call ld-option, -X, -Y) ld-option = $(call try-run, $(LD) $(KBUILD_LDFLAGS) $(1) -v,$(1),$(2),$(3)) - -# ld-ifversion -# Usage: $(call ld-ifversion, -ge, 22252, y) -ld-ifversion = $(shell [ $(CONFIG_LD_VERSION)0 $(1) $(2)0 ] && echo $(3) || echo $(4)) diff --git a/security/apparmor/policy_unpack.c b/security/apparmor/policy_unpack.c index 7012fd82f1bb..633e778ec369 100644 --- a/security/apparmor/policy_unpack.c +++ b/security/apparmor/policy_unpack.c @@ -674,6 +674,10 @@ static struct aa_profile *unpack_profile(struct aa_ext *e, char **ns_name)
tmpname = aa_splitn_fqname(name, strlen(name), &tmpns, &ns_len); if (tmpns) { + if (!tmpname) { + info = "empty profile name"; + goto fail; + } *ns_name = kstrndup(tmpns, ns_len, GFP_KERNEL); if (!*ns_name) { info = "out of memory"; diff --git a/security/selinux/hooks.c b/security/selinux/hooks.c index d88c399b0e86..d45e9fa74e62 100644 --- a/security/selinux/hooks.c +++ b/security/selinux/hooks.c @@ -4690,6 +4690,13 @@ static int selinux_socket_bind(struct socket *sock, struct sockaddr *address, in return -EINVAL; addr4 = (struct sockaddr_in *)address; if (family_sa == AF_UNSPEC) { + if (family == PF_INET6) { + /* Length check from inet6_bind_sk() */ + if (addrlen < SIN6_LEN_RFC2133) + return -EINVAL; + /* Family check from __inet6_bind() */ + goto err_af; + } /* see __inet_bind(), we only want to allow * AF_UNSPEC if the address is INADDR_ANY */ diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index 5efb3adee48d..62f213704492 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -9626,6 +9626,7 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { SND_PCI_QUIRK(0x103c, 0x87f5, "HP", ALC287_FIXUP_HP_GPIO_LED), SND_PCI_QUIRK(0x103c, 0x87f6, "HP Spectre x360 14", ALC245_FIXUP_HP_X360_AMP), SND_PCI_QUIRK(0x103c, 0x87f7, "HP Spectre x360 14", ALC245_FIXUP_HP_X360_AMP), + SND_PCI_QUIRK(0x103c, 0x87fe, "HP Laptop 15s-fq2xxx", ALC236_FIXUP_HP_MUTE_LED_COEFBIT2), SND_PCI_QUIRK(0x103c, 0x8805, "HP ProBook 650 G8 Notebook PC", ALC236_FIXUP_HP_GPIO_LED), SND_PCI_QUIRK(0x103c, 0x880d, "HP EliteBook 830 G8 Notebook PC", ALC285_FIXUP_HP_GPIO_LED), SND_PCI_QUIRK(0x103c, 0x8811, "HP Spectre x360 15-eb1xxx", ALC285_FIXUP_HP_SPECTRE_X360_EB1), @@ -9720,6 +9721,7 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { SND_PCI_QUIRK(0x103c, 0x8c71, "HP EliteBook 845 G11", ALC287_FIXUP_CS35L41_I2C_2_HP_GPIO_LED), SND_PCI_QUIRK(0x103c, 0x8c72, "HP EliteBook 865 G11", ALC287_FIXUP_CS35L41_I2C_2_HP_GPIO_LED), SND_PCI_QUIRK(0x103c, 0x8c96, "HP", ALC236_FIXUP_HP_MUTE_LED_MICMUTE_VREF), + SND_PCI_QUIRK(0x103c, 0x8c97, "HP ZBook", ALC236_FIXUP_HP_MUTE_LED_MICMUTE_VREF), SND_PCI_QUIRK(0x103c, 0x8ca4, "HP ZBook Fury", ALC245_FIXUP_CS35L41_SPI_2_HP_GPIO_LED), SND_PCI_QUIRK(0x103c, 0x8ca7, "HP ZBook Fury", ALC245_FIXUP_CS35L41_SPI_2_HP_GPIO_LED), SND_PCI_QUIRK(0x103c, 0x8cf5, "HP ZBook Studio 16", ALC245_FIXUP_CS35L41_SPI_4_HP_GPIO_LED), @@ -9978,6 +9980,7 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { SND_PCI_QUIRK(0x17aa, 0x3176, "ThinkCentre Station", ALC283_FIXUP_HEADSET_MIC), SND_PCI_QUIRK(0x17aa, 0x3178, "ThinkCentre Station", ALC283_FIXUP_HEADSET_MIC), SND_PCI_QUIRK(0x17aa, 0x31af, "ThinkCentre Station", ALC623_FIXUP_LENOVO_THINKSTATION_P340), + SND_PCI_QUIRK(0x17aa, 0x334b, "Lenovo ThinkCentre M70 Gen5", ALC283_FIXUP_HEADSET_MIC), SND_PCI_QUIRK(0x17aa, 0x3801, "Lenovo Yoga9 14IAP7", ALC287_FIXUP_YOGA9_14IAP7_BASS_SPK_PIN), SND_PCI_QUIRK(0x17aa, 0x3802, "Lenovo Yoga DuetITL 2021", ALC287_FIXUP_YOGA7_14ITL_SPEAKERS), SND_PCI_QUIRK(0x17aa, 0x3813, "Legion 7i 15IMHG05", ALC287_FIXUP_LEGION_15IMHG05_SPEAKERS), diff --git a/sound/pci/oxygen/oxygen_mixer.c b/sound/pci/oxygen/oxygen_mixer.c index 46705ec77b48..eb3aca16359c 100644 --- a/sound/pci/oxygen/oxygen_mixer.c +++ b/sound/pci/oxygen/oxygen_mixer.c @@ -718,7 +718,7 @@ static int ac97_fp_rec_volume_put(struct snd_kcontrol *ctl, oldreg = oxygen_read_ac97(chip, 1, AC97_REC_GAIN); newreg = oldreg & ~0x0707; newreg = newreg | (value->value.integer.value[0] & 7); - newreg = newreg | ((value->value.integer.value[0] & 7) << 8); + newreg = newreg | ((value->value.integer.value[1] & 7) << 8); change = newreg != oldreg; if (change) oxygen_write_ac97(chip, 1, AC97_REC_GAIN, newreg); diff --git a/sound/soc/codecs/cs35l33.c b/sound/soc/codecs/cs35l33.c index 15e79168d256..c3b7046fd29b 100644 --- a/sound/soc/codecs/cs35l33.c +++ b/sound/soc/codecs/cs35l33.c @@ -22,13 +22,11 @@ #include <sound/soc-dapm.h> #include <sound/initval.h> #include <sound/tlv.h> -#include <linux/gpio.h> #include <linux/gpio/consumer.h> #include <sound/cs35l33.h> #include <linux/pm_runtime.h> #include <linux/regulator/consumer.h> #include <linux/regulator/machine.h> -#include <linux/of_gpio.h> #include <linux/of.h> #include <linux/of_device.h> #include <linux/of_irq.h> @@ -1167,7 +1165,7 @@ static int cs35l33_i2c_probe(struct i2c_client *i2c_client)
/* We could issue !RST or skip it based on AMP topology */ cs35l33->reset_gpio = devm_gpiod_get_optional(&i2c_client->dev, - "reset-gpios", GPIOD_OUT_HIGH); + "reset", GPIOD_OUT_HIGH); if (IS_ERR(cs35l33->reset_gpio)) { dev_err(&i2c_client->dev, "%s ERROR: Can't get reset GPIO\n", __func__); diff --git a/sound/soc/codecs/cs35l34.c b/sound/soc/codecs/cs35l34.c index b3f98023e6a7..57d125c03fad 100644 --- a/sound/soc/codecs/cs35l34.c +++ b/sound/soc/codecs/cs35l34.c @@ -20,14 +20,12 @@ #include <linux/regulator/machine.h> #include <linux/pm_runtime.h> #include <linux/of_device.h> -#include <linux/of_gpio.h> #include <linux/of_irq.h> #include <sound/core.h> #include <sound/pcm.h> #include <sound/pcm_params.h> #include <sound/soc.h> #include <sound/soc-dapm.h> -#include <linux/gpio.h> #include <linux/gpio/consumer.h> #include <sound/initval.h> #include <sound/tlv.h> @@ -1061,7 +1059,7 @@ static int cs35l34_i2c_probe(struct i2c_client *i2c_client) dev_err(&i2c_client->dev, "Failed to request IRQ: %d\n", ret);
cs35l34->reset_gpio = devm_gpiod_get_optional(&i2c_client->dev, - "reset-gpios", GPIOD_OUT_LOW); + "reset", GPIOD_OUT_LOW); if (IS_ERR(cs35l34->reset_gpio)) { ret = PTR_ERR(cs35l34->reset_gpio); goto err_regulator; diff --git a/sound/soc/codecs/rt5645.c b/sound/soc/codecs/rt5645.c index 60518ee5a86e..fd3dca08460b 100644 --- a/sound/soc/codecs/rt5645.c +++ b/sound/soc/codecs/rt5645.c @@ -3827,14 +3827,6 @@ static const struct dmi_system_id dmi_platform_data[] = { }, .driver_data = (void *)&ecs_ef20_platform_data, }, - { - .ident = "EF20EA", - .callback = cht_rt5645_ef20_quirk_cb, - .matches = { - DMI_MATCH(DMI_PRODUCT_NAME, "EF20EA"), - }, - .driver_data = (void *)&ecs_ef20_platform_data, - }, { } };
diff --git a/sound/soc/intel/common/soc-acpi-intel-glk-match.c b/sound/soc/intel/common/soc-acpi-intel-glk-match.c index 387e73100884..8911c90bbaf6 100644 --- a/sound/soc/intel/common/soc-acpi-intel-glk-match.c +++ b/sound/soc/intel/common/soc-acpi-intel-glk-match.c @@ -19,6 +19,11 @@ static const struct snd_soc_acpi_codecs glk_codecs = { .codecs = {"MX98357A"} };
+static const struct snd_soc_acpi_codecs glk_rt5682_rt5682s_hp = { + .num_codecs = 2, + .codecs = {"10EC5682", "RTL5682"}, +}; + struct snd_soc_acpi_mach snd_soc_acpi_intel_glk_machines[] = { { .id = "INT343A", @@ -35,20 +40,13 @@ struct snd_soc_acpi_mach snd_soc_acpi_intel_glk_machines[] = { .sof_tplg_filename = "sof-glk-da7219.tplg", }, { - .id = "10EC5682", + .comp_ids = &glk_rt5682_rt5682s_hp, .drv_name = "glk_rt5682_mx98357a", .fw_filename = "intel/dsp_fw_glk.bin", .machine_quirk = snd_soc_acpi_codec_list, .quirk_data = &glk_codecs, .sof_tplg_filename = "sof-glk-rt5682.tplg", }, - { - .id = "RTL5682", - .drv_name = "glk_rt5682_max98357a", - .machine_quirk = snd_soc_acpi_codec_list, - .quirk_data = &glk_codecs, - .sof_tplg_filename = "sof-glk-rt5682.tplg", - }, { .id = "10134242", .drv_name = "glk_cs4242_mx98357a", diff --git a/sound/soc/mediatek/common/mtk-dsp-sof-common.c b/sound/soc/mediatek/common/mtk-dsp-sof-common.c index 8b1b623207be..d4d1d3b9572a 100644 --- a/sound/soc/mediatek/common/mtk-dsp-sof-common.c +++ b/sound/soc/mediatek/common/mtk-dsp-sof-common.c @@ -24,7 +24,7 @@ int mtk_sof_dai_link_fixup(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai_link *sof_dai_link = NULL; const struct sof_conn_stream *conn = &sof_priv->conn_streams[i];
- if (strcmp(rtd->dai_link->name, conn->normal_link)) + if (conn->normal_link && strcmp(rtd->dai_link->name, conn->normal_link)) continue;
for_each_card_rtds(card, runtime) { diff --git a/sound/usb/mixer_scarlett_gen2.c b/sound/usb/mixer_scarlett_gen2.c index 9d11bb08667e..1bcb05c73e0a 100644 --- a/sound/usb/mixer_scarlett_gen2.c +++ b/sound/usb/mixer_scarlett_gen2.c @@ -1337,9 +1337,11 @@ static void scarlett2_config_save(struct usb_mixer_interface *mixer) { __le32 req = cpu_to_le32(SCARLETT2_USB_CONFIG_SAVE);
- scarlett2_usb(mixer, SCARLETT2_USB_DATA_CMD, - &req, sizeof(u32), - NULL, 0); + int err = scarlett2_usb(mixer, SCARLETT2_USB_DATA_CMD, + &req, sizeof(u32), + NULL, 0); + if (err < 0) + usb_audio_err(mixer->chip, "config save failed: %d\n", err); }
/* Delayed work to save config */ @@ -1388,7 +1390,10 @@ static int scarlett2_usb_set_config( size = 1; offset = config_item->offset;
- scarlett2_usb_get(mixer, offset, &tmp, 1); + err = scarlett2_usb_get(mixer, offset, &tmp, 1); + if (err < 0) + return err; + if (value) tmp |= (1 << index); else @@ -1793,14 +1798,20 @@ static int scarlett2_sync_ctl_get(struct snd_kcontrol *kctl, struct usb_mixer_elem_info *elem = kctl->private_data; struct usb_mixer_interface *mixer = elem->head.mixer; struct scarlett2_data *private = mixer->private_data; + int err = 0;
mutex_lock(&private->data_mutex); - if (private->sync_updated) - scarlett2_update_sync(mixer); + + if (private->sync_updated) { + err = scarlett2_update_sync(mixer); + if (err < 0) + goto unlock; + } ucontrol->value.enumerated.item[0] = private->sync; - mutex_unlock(&private->data_mutex);
- return 0; +unlock: + mutex_unlock(&private->data_mutex); + return err; }
static const struct snd_kcontrol_new scarlett2_sync_ctl = { @@ -1883,22 +1894,35 @@ static int scarlett2_master_volume_ctl_get(struct snd_kcontrol *kctl, struct usb_mixer_elem_info *elem = kctl->private_data; struct usb_mixer_interface *mixer = elem->head.mixer; struct scarlett2_data *private = mixer->private_data; + int err = 0;
mutex_lock(&private->data_mutex); - if (private->vol_updated) - scarlett2_update_volumes(mixer); - mutex_unlock(&private->data_mutex);
+ if (private->vol_updated) { + err = scarlett2_update_volumes(mixer); + if (err < 0) + goto unlock; + } ucontrol->value.integer.value[0] = private->master_vol; - return 0; + +unlock: + mutex_unlock(&private->data_mutex); + return err; }
static int line_out_remap(struct scarlett2_data *private, int index) { const struct scarlett2_device_info *info = private->info; + const int (*port_count)[SCARLETT2_PORT_DIRNS] = info->port_count; + int line_out_count = + port_count[SCARLETT2_PORT_TYPE_ANALOGUE][SCARLETT2_PORT_OUT];
if (!info->line_out_remap_enable) return index; + + if (index >= line_out_count) + return index; + return info->line_out_remap[index]; }
@@ -1909,14 +1933,20 @@ static int scarlett2_volume_ctl_get(struct snd_kcontrol *kctl, struct usb_mixer_interface *mixer = elem->head.mixer; struct scarlett2_data *private = mixer->private_data; int index = line_out_remap(private, elem->control); + int err = 0;
mutex_lock(&private->data_mutex); - if (private->vol_updated) - scarlett2_update_volumes(mixer); - mutex_unlock(&private->data_mutex);
+ if (private->vol_updated) { + err = scarlett2_update_volumes(mixer); + if (err < 0) + goto unlock; + } ucontrol->value.integer.value[0] = private->vol[index]; - return 0; + +unlock: + mutex_unlock(&private->data_mutex); + return err; }
static int scarlett2_volume_ctl_put(struct snd_kcontrol *kctl, @@ -1983,14 +2013,20 @@ static int scarlett2_mute_ctl_get(struct snd_kcontrol *kctl, struct usb_mixer_interface *mixer = elem->head.mixer; struct scarlett2_data *private = mixer->private_data; int index = line_out_remap(private, elem->control); + int err = 0;
mutex_lock(&private->data_mutex); - if (private->vol_updated) - scarlett2_update_volumes(mixer); - mutex_unlock(&private->data_mutex);
+ if (private->vol_updated) { + err = scarlett2_update_volumes(mixer); + if (err < 0) + goto unlock; + } ucontrol->value.integer.value[0] = private->mute_switch[index]; - return 0; + +unlock: + mutex_unlock(&private->data_mutex); + return err; }
static int scarlett2_mute_ctl_put(struct snd_kcontrol *kctl, @@ -2236,14 +2272,20 @@ static int scarlett2_level_enum_ctl_get(struct snd_kcontrol *kctl, const struct scarlett2_device_info *info = private->info;
int index = elem->control + info->level_input_first; + int err = 0;
mutex_lock(&private->data_mutex); - if (private->input_other_updated) - scarlett2_update_input_other(mixer); + + if (private->input_other_updated) { + err = scarlett2_update_input_other(mixer); + if (err < 0) + goto unlock; + } ucontrol->value.enumerated.item[0] = private->level_switch[index]; - mutex_unlock(&private->data_mutex);
- return 0; +unlock: + mutex_unlock(&private->data_mutex); + return err; }
static int scarlett2_level_enum_ctl_put(struct snd_kcontrol *kctl, @@ -2294,15 +2336,21 @@ static int scarlett2_pad_ctl_get(struct snd_kcontrol *kctl, struct usb_mixer_elem_info *elem = kctl->private_data; struct usb_mixer_interface *mixer = elem->head.mixer; struct scarlett2_data *private = mixer->private_data; + int err = 0;
mutex_lock(&private->data_mutex); - if (private->input_other_updated) - scarlett2_update_input_other(mixer); + + if (private->input_other_updated) { + err = scarlett2_update_input_other(mixer); + if (err < 0) + goto unlock; + } ucontrol->value.integer.value[0] = private->pad_switch[elem->control]; - mutex_unlock(&private->data_mutex);
- return 0; +unlock: + mutex_unlock(&private->data_mutex); + return err; }
static int scarlett2_pad_ctl_put(struct snd_kcontrol *kctl, @@ -2352,14 +2400,20 @@ static int scarlett2_air_ctl_get(struct snd_kcontrol *kctl, struct usb_mixer_elem_info *elem = kctl->private_data; struct usb_mixer_interface *mixer = elem->head.mixer; struct scarlett2_data *private = mixer->private_data; + int err = 0;
mutex_lock(&private->data_mutex); - if (private->input_other_updated) - scarlett2_update_input_other(mixer); + + if (private->input_other_updated) { + err = scarlett2_update_input_other(mixer); + if (err < 0) + goto unlock; + } ucontrol->value.integer.value[0] = private->air_switch[elem->control]; - mutex_unlock(&private->data_mutex);
- return 0; +unlock: + mutex_unlock(&private->data_mutex); + return err; }
static int scarlett2_air_ctl_put(struct snd_kcontrol *kctl, @@ -2409,15 +2463,21 @@ static int scarlett2_phantom_ctl_get(struct snd_kcontrol *kctl, struct usb_mixer_elem_info *elem = kctl->private_data; struct usb_mixer_interface *mixer = elem->head.mixer; struct scarlett2_data *private = mixer->private_data; + int err = 0;
mutex_lock(&private->data_mutex); - if (private->input_other_updated) - scarlett2_update_input_other(mixer); + + if (private->input_other_updated) { + err = scarlett2_update_input_other(mixer); + if (err < 0) + goto unlock; + } ucontrol->value.integer.value[0] = private->phantom_switch[elem->control]; - mutex_unlock(&private->data_mutex);
- return 0; +unlock: + mutex_unlock(&private->data_mutex); + return err; }
static int scarlett2_phantom_ctl_put(struct snd_kcontrol *kctl, @@ -2589,14 +2649,20 @@ static int scarlett2_direct_monitor_ctl_get( struct usb_mixer_elem_info *elem = kctl->private_data; struct usb_mixer_interface *mixer = elem->head.mixer; struct scarlett2_data *private = elem->head.mixer->private_data; + int err = 0;
mutex_lock(&private->data_mutex); - if (private->monitor_other_updated) - scarlett2_update_monitor_other(mixer); + + if (private->monitor_other_updated) { + err = scarlett2_update_monitor_other(mixer); + if (err < 0) + goto unlock; + } ucontrol->value.enumerated.item[0] = private->direct_monitor_switch; - mutex_unlock(&private->data_mutex);
- return 0; +unlock: + mutex_unlock(&private->data_mutex); + return err; }
static int scarlett2_direct_monitor_ctl_put( @@ -2696,14 +2762,20 @@ static int scarlett2_speaker_switch_enum_ctl_get( struct usb_mixer_elem_info *elem = kctl->private_data; struct usb_mixer_interface *mixer = elem->head.mixer; struct scarlett2_data *private = mixer->private_data; + int err = 0;
mutex_lock(&private->data_mutex); - if (private->monitor_other_updated) - scarlett2_update_monitor_other(mixer); + + if (private->monitor_other_updated) { + err = scarlett2_update_monitor_other(mixer); + if (err < 0) + goto unlock; + } ucontrol->value.enumerated.item[0] = private->speaker_switching_switch; - mutex_unlock(&private->data_mutex);
- return 0; +unlock: + mutex_unlock(&private->data_mutex); + return err; }
/* when speaker switching gets enabled, switch the main/alt speakers @@ -2851,14 +2923,20 @@ static int scarlett2_talkback_enum_ctl_get( struct usb_mixer_elem_info *elem = kctl->private_data; struct usb_mixer_interface *mixer = elem->head.mixer; struct scarlett2_data *private = mixer->private_data; + int err = 0;
mutex_lock(&private->data_mutex); - if (private->monitor_other_updated) - scarlett2_update_monitor_other(mixer); + + if (private->monitor_other_updated) { + err = scarlett2_update_monitor_other(mixer); + if (err < 0) + goto unlock; + } ucontrol->value.enumerated.item[0] = private->talkback_switch; - mutex_unlock(&private->data_mutex);
- return 0; +unlock: + mutex_unlock(&private->data_mutex); + return err; }
static int scarlett2_talkback_enum_ctl_put( @@ -3006,14 +3084,20 @@ static int scarlett2_dim_mute_ctl_get(struct snd_kcontrol *kctl, struct usb_mixer_elem_info *elem = kctl->private_data; struct usb_mixer_interface *mixer = elem->head.mixer; struct scarlett2_data *private = mixer->private_data; + int err = 0;
mutex_lock(&private->data_mutex); - if (private->vol_updated) - scarlett2_update_volumes(mixer); - mutex_unlock(&private->data_mutex);
+ if (private->vol_updated) { + err = scarlett2_update_volumes(mixer); + if (err < 0) + goto unlock; + } ucontrol->value.integer.value[0] = private->dim_mute[elem->control]; - return 0; + +unlock: + mutex_unlock(&private->data_mutex); + return err; }
static int scarlett2_dim_mute_ctl_put(struct snd_kcontrol *kctl, @@ -3277,7 +3361,8 @@ static int scarlett2_mixer_ctl_put(struct snd_kcontrol *kctl, mutex_lock(&private->data_mutex);
oval = private->mix[index]; - val = ucontrol->value.integer.value[0]; + val = clamp(ucontrol->value.integer.value[0], + 0L, (long)SCARLETT2_MIXER_MAX_VALUE); num_mixer_in = port_count[SCARLETT2_PORT_TYPE_MIX][SCARLETT2_PORT_OUT]; mix_num = index / num_mixer_in;
@@ -3383,22 +3468,21 @@ static int scarlett2_mux_src_enum_ctl_get(struct snd_kcontrol *kctl, struct usb_mixer_elem_info *elem = kctl->private_data; struct usb_mixer_interface *mixer = elem->head.mixer; struct scarlett2_data *private = mixer->private_data; - const struct scarlett2_device_info *info = private->info; - const int (*port_count)[SCARLETT2_PORT_DIRNS] = info->port_count; - int line_out_count = - port_count[SCARLETT2_PORT_TYPE_ANALOGUE][SCARLETT2_PORT_OUT]; - int index = elem->control; - - if (index < line_out_count) - index = line_out_remap(private, index); + int index = line_out_remap(private, elem->control); + int err = 0;
mutex_lock(&private->data_mutex); - if (private->mux_updated) - scarlett2_usb_get_mux(mixer); + + if (private->mux_updated) { + err = scarlett2_usb_get_mux(mixer); + if (err < 0) + goto unlock; + } ucontrol->value.enumerated.item[0] = private->mux[index]; - mutex_unlock(&private->data_mutex);
- return 0; +unlock: + mutex_unlock(&private->data_mutex); + return err; }
static int scarlett2_mux_src_enum_ctl_put(struct snd_kcontrol *kctl, @@ -3407,16 +3491,9 @@ static int scarlett2_mux_src_enum_ctl_put(struct snd_kcontrol *kctl, struct usb_mixer_elem_info *elem = kctl->private_data; struct usb_mixer_interface *mixer = elem->head.mixer; struct scarlett2_data *private = mixer->private_data; - const struct scarlett2_device_info *info = private->info; - const int (*port_count)[SCARLETT2_PORT_DIRNS] = info->port_count; - int line_out_count = - port_count[SCARLETT2_PORT_TYPE_ANALOGUE][SCARLETT2_PORT_OUT]; - int index = elem->control; + int index = line_out_remap(private, elem->control); int oval, val, err = 0;
- if (index < line_out_count) - index = line_out_remap(private, index); - mutex_lock(&private->data_mutex);
oval = private->mux[index]; diff --git a/tools/include/uapi/linux/bpf.h b/tools/include/uapi/linux/bpf.h index 92dbe89dafbf..201dc77ebbd7 100644 --- a/tools/include/uapi/linux/bpf.h +++ b/tools/include/uapi/linux/bpf.h @@ -4353,6 +4353,8 @@ union bpf_attr { * long bpf_get_task_stack(struct task_struct *task, void *buf, u32 size, u64 flags) * Description * Return a user or a kernel stack in bpf program provided buffer. + * Note: the user stack will only be populated if the *task* is + * the current task; all other tasks will return -EOPNOTSUPP. * To achieve this, the helper needs *task*, which is a valid * pointer to **struct task_struct**. To store the stacktrace, the * bpf program provides *buf* with a nonnegative *size*. @@ -4364,6 +4366,7 @@ union bpf_attr { * * **BPF_F_USER_STACK** * Collect a user space stack instead of a kernel stack. + * The *task* must be the current task. * **BPF_F_USER_BUILD_ID** * Collect buildid+offset instead of ips for user stack, * only valid if **BPF_F_USER_STACK** is also specified. diff --git a/tools/lib/api/io.h b/tools/lib/api/io.h index 777c20f6b604..458acd294237 100644 --- a/tools/lib/api/io.h +++ b/tools/lib/api/io.h @@ -9,6 +9,7 @@
#include <stdlib.h> #include <unistd.h> +#include <linux/types.h>
struct io { /* File descriptor being read/ */ diff --git a/tools/perf/util/bpf-event.c b/tools/perf/util/bpf-event.c index cc7c1f90cf62..91c7bfa82a50 100644 --- a/tools/perf/util/bpf-event.c +++ b/tools/perf/util/bpf-event.c @@ -606,9 +606,9 @@ int evlist__add_bpf_sb_event(struct evlist *evlist, struct perf_env *env) return evlist__add_sb_event(evlist, &attr, bpf_event__sb_cb, env); }
-void bpf_event__print_bpf_prog_info(struct bpf_prog_info *info, - struct perf_env *env, - FILE *fp) +void __bpf_event__print_bpf_prog_info(struct bpf_prog_info *info, + struct perf_env *env, + FILE *fp) { __u32 *prog_lens = (__u32 *)(uintptr_t)(info->jited_func_lens); __u64 *prog_addrs = (__u64 *)(uintptr_t)(info->jited_ksyms); @@ -624,7 +624,7 @@ void bpf_event__print_bpf_prog_info(struct bpf_prog_info *info, if (info->btf_id) { struct btf_node *node;
- node = perf_env__find_btf(env, info->btf_id); + node = __perf_env__find_btf(env, info->btf_id); if (node) btf = btf__new((__u8 *)(node->data), node->data_size); diff --git a/tools/perf/util/bpf-event.h b/tools/perf/util/bpf-event.h index 1bcbd4fb6c66..e2f0420905f5 100644 --- a/tools/perf/util/bpf-event.h +++ b/tools/perf/util/bpf-event.h @@ -33,9 +33,9 @@ struct btf_node { int machine__process_bpf(struct machine *machine, union perf_event *event, struct perf_sample *sample); int evlist__add_bpf_sb_event(struct evlist *evlist, struct perf_env *env); -void bpf_event__print_bpf_prog_info(struct bpf_prog_info *info, - struct perf_env *env, - FILE *fp); +void __bpf_event__print_bpf_prog_info(struct bpf_prog_info *info, + struct perf_env *env, + FILE *fp); #else static inline int machine__process_bpf(struct machine *machine __maybe_unused, union perf_event *event __maybe_unused, @@ -50,9 +50,9 @@ static inline int evlist__add_bpf_sb_event(struct evlist *evlist __maybe_unused, return 0; }
-static inline void bpf_event__print_bpf_prog_info(struct bpf_prog_info *info __maybe_unused, - struct perf_env *env __maybe_unused, - FILE *fp __maybe_unused) +static inline void __bpf_event__print_bpf_prog_info(struct bpf_prog_info *info __maybe_unused, + struct perf_env *env __maybe_unused, + FILE *fp __maybe_unused) {
} diff --git a/tools/perf/util/env.c b/tools/perf/util/env.c index 5b8cf6a421a4..5d878bae7d9a 100644 --- a/tools/perf/util/env.c +++ b/tools/perf/util/env.c @@ -21,13 +21,19 @@ struct perf_env perf_env;
void perf_env__insert_bpf_prog_info(struct perf_env *env, struct bpf_prog_info_node *info_node) +{ + down_write(&env->bpf_progs.lock); + __perf_env__insert_bpf_prog_info(env, info_node); + up_write(&env->bpf_progs.lock); +} + +void __perf_env__insert_bpf_prog_info(struct perf_env *env, struct bpf_prog_info_node *info_node) { __u32 prog_id = info_node->info_linear->info.id; struct bpf_prog_info_node *node; struct rb_node *parent = NULL; struct rb_node **p;
- down_write(&env->bpf_progs.lock); p = &env->bpf_progs.infos.rb_node;
while (*p != NULL) { @@ -39,15 +45,13 @@ void perf_env__insert_bpf_prog_info(struct perf_env *env, p = &(*p)->rb_right; } else { pr_debug("duplicated bpf prog info %u\n", prog_id); - goto out; + return; } }
rb_link_node(&info_node->rb_node, parent, p); rb_insert_color(&info_node->rb_node, &env->bpf_progs.infos); env->bpf_progs.infos_cnt++; -out: - up_write(&env->bpf_progs.lock); }
struct bpf_prog_info_node *perf_env__find_bpf_prog_info(struct perf_env *env, @@ -76,14 +80,22 @@ struct bpf_prog_info_node *perf_env__find_bpf_prog_info(struct perf_env *env, }
bool perf_env__insert_btf(struct perf_env *env, struct btf_node *btf_node) +{ + bool ret; + + down_write(&env->bpf_progs.lock); + ret = __perf_env__insert_btf(env, btf_node); + up_write(&env->bpf_progs.lock); + return ret; +} + +bool __perf_env__insert_btf(struct perf_env *env, struct btf_node *btf_node) { struct rb_node *parent = NULL; __u32 btf_id = btf_node->id; struct btf_node *node; struct rb_node **p; - bool ret = true;
- down_write(&env->bpf_progs.lock); p = &env->bpf_progs.btfs.rb_node;
while (*p != NULL) { @@ -95,25 +107,31 @@ bool perf_env__insert_btf(struct perf_env *env, struct btf_node *btf_node) p = &(*p)->rb_right; } else { pr_debug("duplicated btf %u\n", btf_id); - ret = false; - goto out; + return false; } }
rb_link_node(&btf_node->rb_node, parent, p); rb_insert_color(&btf_node->rb_node, &env->bpf_progs.btfs); env->bpf_progs.btfs_cnt++; -out: - up_write(&env->bpf_progs.lock); - return ret; + return true; }
struct btf_node *perf_env__find_btf(struct perf_env *env, __u32 btf_id) +{ + struct btf_node *res; + + down_read(&env->bpf_progs.lock); + res = __perf_env__find_btf(env, btf_id); + up_read(&env->bpf_progs.lock); + return res; +} + +struct btf_node *__perf_env__find_btf(struct perf_env *env, __u32 btf_id) { struct btf_node *node = NULL; struct rb_node *n;
- down_read(&env->bpf_progs.lock); n = env->bpf_progs.btfs.rb_node;
while (n) { @@ -123,13 +141,9 @@ struct btf_node *perf_env__find_btf(struct perf_env *env, __u32 btf_id) else if (btf_id > node->id) n = n->rb_right; else - goto out; + return node; } - node = NULL; - -out: - up_read(&env->bpf_progs.lock); - return node; + return NULL; }
/* purge data in bpf_progs.infos tree */ diff --git a/tools/perf/util/env.h b/tools/perf/util/env.h index 4566c51f2fd9..359eff51cb85 100644 --- a/tools/perf/util/env.h +++ b/tools/perf/util/env.h @@ -164,12 +164,16 @@ const char *perf_env__raw_arch(struct perf_env *env); int perf_env__nr_cpus_avail(struct perf_env *env);
void perf_env__init(struct perf_env *env); +void __perf_env__insert_bpf_prog_info(struct perf_env *env, + struct bpf_prog_info_node *info_node); void perf_env__insert_bpf_prog_info(struct perf_env *env, struct bpf_prog_info_node *info_node); struct bpf_prog_info_node *perf_env__find_bpf_prog_info(struct perf_env *env, __u32 prog_id); bool perf_env__insert_btf(struct perf_env *env, struct btf_node *btf_node); +bool __perf_env__insert_btf(struct perf_env *env, struct btf_node *btf_node); struct btf_node *perf_env__find_btf(struct perf_env *env, __u32 btf_id); +struct btf_node *__perf_env__find_btf(struct perf_env *env, __u32 btf_id);
int perf_env__numa_node(struct perf_env *env, struct perf_cpu cpu); char *perf_env__find_pmu_cap(struct perf_env *env, const char *pmu_name, diff --git a/tools/perf/util/genelf.c b/tools/perf/util/genelf.c index fefc72066c4e..ac17a3cb59dc 100644 --- a/tools/perf/util/genelf.c +++ b/tools/perf/util/genelf.c @@ -293,9 +293,9 @@ jit_write_elf(int fd, uint64_t load_addr, const char *sym, */ phdr = elf_newphdr(e, 1); phdr[0].p_type = PT_LOAD; - phdr[0].p_offset = 0; - phdr[0].p_vaddr = 0; - phdr[0].p_paddr = 0; + phdr[0].p_offset = GEN_ELF_TEXT_OFFSET; + phdr[0].p_vaddr = GEN_ELF_TEXT_OFFSET; + phdr[0].p_paddr = GEN_ELF_TEXT_OFFSET; phdr[0].p_filesz = csize; phdr[0].p_memsz = csize; phdr[0].p_flags = PF_X | PF_R; diff --git a/tools/perf/util/header.c b/tools/perf/util/header.c index 9e2dce70b130..b2b0293567f0 100644 --- a/tools/perf/util/header.c +++ b/tools/perf/util/header.c @@ -1809,8 +1809,8 @@ static void print_bpf_prog_info(struct feat_fd *ff, FILE *fp) node = rb_entry(next, struct bpf_prog_info_node, rb_node); next = rb_next(&node->rb_node);
- bpf_event__print_bpf_prog_info(&node->info_linear->info, - env, fp); + __bpf_event__print_bpf_prog_info(&node->info_linear->info, + env, fp); }
up_read(&env->bpf_progs.lock); @@ -3136,7 +3136,7 @@ static int process_bpf_prog_info(struct feat_fd *ff, void *data __maybe_unused) /* after reading from file, translate offset to address */ bpil_offs_to_addr(info_linear); info_node->info_linear = info_linear; - perf_env__insert_bpf_prog_info(env, info_node); + __perf_env__insert_bpf_prog_info(env, info_node); }
up_write(&env->bpf_progs.lock); @@ -3183,7 +3183,7 @@ static int process_bpf_btf(struct feat_fd *ff, void *data __maybe_unused) if (__do_read(ff, node->data, data_size)) goto out;
- perf_env__insert_btf(env, node); + __perf_env__insert_btf(env, node); node = NULL; }
@@ -4314,9 +4314,10 @@ size_t perf_event__fprintf_event_update(union perf_event *event, FILE *fp) ret += fprintf(fp, "... ");
map = cpu_map__new_data(&ev->cpus.cpus); - if (map) + if (map) { ret += cpu_map__fprintf(map, fp); - else + perf_cpu_map__put(map); + } else ret += fprintf(fp, "failed to get cpus\n"); break; default: diff --git a/tools/perf/util/hisi-ptt.c b/tools/perf/util/hisi-ptt.c index 45b614bb73bf..764d660d30e2 100644 --- a/tools/perf/util/hisi-ptt.c +++ b/tools/perf/util/hisi-ptt.c @@ -121,6 +121,7 @@ static int hisi_ptt_process_auxtrace_event(struct perf_session *session, if (dump_trace) hisi_ptt_dump_event(ptt, data, size);
+ free(data); return 0; }
diff --git a/tools/testing/selftests/alsa/mixer-test.c b/tools/testing/selftests/alsa/mixer-test.c index 37da902545a4..9ad39db32d14 100644 --- a/tools/testing/selftests/alsa/mixer-test.c +++ b/tools/testing/selftests/alsa/mixer-test.c @@ -205,7 +205,7 @@ static void find_controls(void) err = snd_ctl_poll_descriptors(card_data->handle, &card_data->pollfd, 1); if (err != 1) { - ksft_exit_fail_msg("snd_ctl_poll_descriptors() failed for %d\n", + ksft_exit_fail_msg("snd_ctl_poll_descriptors() failed for card %d: %d\n", card, err); }
@@ -358,7 +358,7 @@ static bool ctl_value_index_valid(struct ctl_data *ctl, }
if (int64_val > snd_ctl_elem_info_get_max64(ctl->info)) { - ksft_print_msg("%s.%d value %lld more than maximum %lld\n", + ksft_print_msg("%s.%d value %lld more than maximum %ld\n", ctl->name, index, int64_val, snd_ctl_elem_info_get_max(ctl->info)); return false; diff --git a/tools/testing/selftests/bpf/prog_tests/bpf_iter.c b/tools/testing/selftests/bpf/prog_tests/bpf_iter.c index ecde236047fe..0c67a4e28eff 100644 --- a/tools/testing/selftests/bpf/prog_tests/bpf_iter.c +++ b/tools/testing/selftests/bpf/prog_tests/bpf_iter.c @@ -338,6 +338,8 @@ static void test_task_stack(void) do_dummy_read(skel->progs.dump_task_stack); do_dummy_read(skel->progs.get_task_user_stacks);
+ ASSERT_EQ(skel->bss->num_user_stacks, 1, "num_user_stacks"); + bpf_iter_task_stack__destroy(skel); }
diff --git a/tools/testing/selftests/bpf/prog_tests/time_tai.c b/tools/testing/selftests/bpf/prog_tests/time_tai.c index a31119823666..f45af1b0ef2c 100644 --- a/tools/testing/selftests/bpf/prog_tests/time_tai.c +++ b/tools/testing/selftests/bpf/prog_tests/time_tai.c @@ -56,7 +56,7 @@ void test_time_tai(void) ASSERT_NEQ(ts2, 0, "tai_ts2");
/* TAI is moving forward only */ - ASSERT_GT(ts2, ts1, "tai_forward"); + ASSERT_GE(ts2, ts1, "tai_forward");
/* Check for future */ ret = clock_gettime(CLOCK_TAI, &now_tai); diff --git a/tools/testing/selftests/bpf/progs/bpf_iter_task_stack.c b/tools/testing/selftests/bpf/progs/bpf_iter_task_stack.c index f2b8167b72a8..442f4ca39fd7 100644 --- a/tools/testing/selftests/bpf/progs/bpf_iter_task_stack.c +++ b/tools/testing/selftests/bpf/progs/bpf_iter_task_stack.c @@ -35,6 +35,8 @@ int dump_task_stack(struct bpf_iter__task *ctx) return 0; }
+int num_user_stacks = 0; + SEC("iter/task") int get_task_user_stacks(struct bpf_iter__task *ctx) { @@ -51,6 +53,9 @@ int get_task_user_stacks(struct bpf_iter__task *ctx) if (res <= 0) return 0;
+ /* Only one task, the current one, should succeed */ + ++num_user_stacks; + buf_sz += res;
/* If the verifier doesn't refine bpf_get_task_stack res, and instead diff --git a/tools/testing/selftests/bpf/progs/xdp_synproxy_kern.c b/tools/testing/selftests/bpf/progs/xdp_synproxy_kern.c index 736686e903f6..26bfbc73d129 100644 --- a/tools/testing/selftests/bpf/progs/xdp_synproxy_kern.c +++ b/tools/testing/selftests/bpf/progs/xdp_synproxy_kern.c @@ -447,13 +447,13 @@ static __always_inline int tcp_lookup(void *ctx, struct header_pointers *hdr, bo unsigned long status = ct->status;
bpf_ct_release(ct); - if (status & IPS_CONFIRMED_BIT) + if (status & IPS_CONFIRMED) return XDP_PASS; } else if (ct_lookup_opts.error != -ENOENT) { return XDP_ABORTED; }
- /* error == -ENOENT || !(status & IPS_CONFIRMED_BIT) */ + /* error == -ENOENT || !(status & IPS_CONFIRMED) */ return XDP_TX; }
diff --git a/tools/testing/selftests/drivers/net/mlxsw/qos_pfc.sh b/tools/testing/selftests/drivers/net/mlxsw/qos_pfc.sh index f9858e221996..6a3002fbcf43 100755 --- a/tools/testing/selftests/drivers/net/mlxsw/qos_pfc.sh +++ b/tools/testing/selftests/drivers/net/mlxsw/qos_pfc.sh @@ -121,6 +121,9 @@ h2_destroy()
switch_create() { + local lanes_swp4 + local pg1_size + # pools # -----
@@ -230,7 +233,20 @@ switch_create() dcb pfc set dev $swp4 prio-pfc all:off 1:on # PG0 will get autoconfigured to Xoff, give PG1 arbitrarily 100K, which # is (-2*MTU) about 80K of delay provision. - dcb buffer set dev $swp4 buffer-size all:0 1:$_100KB + pg1_size=$_100KB + + setup_wait_dev_with_timeout $swp4 + + lanes_swp4=$(ethtool $swp4 | grep 'Lanes:') + lanes_swp4=${lanes_swp4#*"Lanes: "} + + # 8-lane ports use two buffers among which the configured buffer + # is split, so double the size to get twice (20K + 80K). + if [[ $lanes_swp4 -eq 8 ]]; then + pg1_size=$((pg1_size * 2)) + fi + + dcb buffer set dev $swp4 buffer-size all:0 1:$pg1_size
# bridges # ------- diff --git a/tools/testing/selftests/drivers/net/mlxsw/spectrum-2/tc_flower.sh b/tools/testing/selftests/drivers/net/mlxsw/spectrum-2/tc_flower.sh index fb850e0ec837..7bf56ea161e3 100755 --- a/tools/testing/selftests/drivers/net/mlxsw/spectrum-2/tc_flower.sh +++ b/tools/testing/selftests/drivers/net/mlxsw/spectrum-2/tc_flower.sh @@ -10,7 +10,8 @@ lib_dir=$(dirname $0)/../../../../net/forwarding ALL_TESTS="single_mask_test identical_filters_test two_masks_test \ multiple_masks_test ctcam_edge_cases_test delta_simple_test \ delta_two_masks_one_key_test delta_simple_rehash_test \ - bloom_simple_test bloom_complex_test bloom_delta_test" + bloom_simple_test bloom_complex_test bloom_delta_test \ + max_erp_entries_test" NUM_NETIFS=2 source $lib_dir/lib.sh source $lib_dir/tc_common.sh @@ -983,6 +984,55 @@ bloom_delta_test() log_test "bloom delta test ($tcflags)" }
+max_erp_entries_test() +{ + # The number of eRP entries is limited. Once the maximum number of eRPs + # has been reached, filters cannot be added. This test verifies that + # when this limit is reached, inserstion fails without crashing. + + RET=0 + + local num_masks=32 + local num_regions=15 + local chain_failed + local mask_failed + local ret + + if [[ "$tcflags" != "skip_sw" ]]; then + return 0; + fi + + for ((i=1; i < $num_regions; i++)); do + for ((j=$num_masks; j >= 0; j--)); do + tc filter add dev $h2 ingress chain $i protocol ip \ + pref $i handle $j flower $tcflags \ + dst_ip 192.1.0.0/$j &> /dev/null + ret=$? + + if [ $ret -ne 0 ]; then + chain_failed=$i + mask_failed=$j + break 2 + fi + done + done + + # We expect to exceed the maximum number of eRP entries, so that + # insertion eventually fails. Otherwise, the test should be adjusted to + # add more filters. + check_fail $ret "expected to exceed number of eRP entries" + + for ((; i >= 1; i--)); do + for ((j=0; j <= $num_masks; j++)); do + tc filter del dev $h2 ingress chain $i protocol ip \ + pref $i handle $j flower &> /dev/null + done + done + + log_test "max eRP entries test ($tcflags). " \ + "max chain $chain_failed, mask $mask_failed" +} + setup_prepare() { h1=${NETIFS[p1]} diff --git a/tools/testing/selftests/net/arp_ndisc_untracked_subnets.sh b/tools/testing/selftests/net/arp_ndisc_untracked_subnets.sh index c899b446acb6..327427ec10f5 100755 --- a/tools/testing/selftests/net/arp_ndisc_untracked_subnets.sh +++ b/tools/testing/selftests/net/arp_ndisc_untracked_subnets.sh @@ -150,7 +150,7 @@ arp_test_gratuitous() { fi # Supply arp_accept option to set up which sets it in sysctl setup ${arp_accept} - ip netns exec ${HOST_NS} arping -A -U ${HOST_ADDR} -c1 2>&1 >/dev/null + ip netns exec ${HOST_NS} arping -A -I ${HOST_INTF} -U ${HOST_ADDR} -c1 2>&1 >/dev/null
if verify_arp $1 $2; then printf " TEST: %-60s [ OK ]\n" "${test_msg[*]}" diff --git a/tools/testing/selftests/net/fib_nexthop_multiprefix.sh b/tools/testing/selftests/net/fib_nexthop_multiprefix.sh index 51df5e305855..b52d59547fc5 100755 --- a/tools/testing/selftests/net/fib_nexthop_multiprefix.sh +++ b/tools/testing/selftests/net/fib_nexthop_multiprefix.sh @@ -209,12 +209,12 @@ validate_v6_exception() echo "Route get" ip -netns h0 -6 ro get ${dst} echo "Searching for:" - echo " ${dst} from :: via ${r1} dev eth0 src ${h0} .* mtu ${mtu}" + echo " ${dst}.* via ${r1} dev eth0 src ${h0} .* mtu ${mtu}" echo fi
ip -netns h0 -6 ro get ${dst} | \ - grep -q "${dst} from :: via ${r1} dev eth0 src ${h0} .* mtu ${mtu}" + grep -q "${dst}.* via ${r1} dev eth0 src ${h0} .* mtu ${mtu}" rc=$?
log_test $rc 0 "IPv6: host 0 to host ${i}, mtu ${mtu}" diff --git a/tools/testing/selftests/powerpc/math/fpu_preempt.c b/tools/testing/selftests/powerpc/math/fpu_preempt.c index 5235bdc8c0b1..3e5b5663d244 100644 --- a/tools/testing/selftests/powerpc/math/fpu_preempt.c +++ b/tools/testing/selftests/powerpc/math/fpu_preempt.c @@ -37,19 +37,20 @@ __thread double darray[] = {0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1.0, int threads_starting; int running;
-extern void preempt_fpu(double *darray, int *threads_starting, int *running); +extern int preempt_fpu(double *darray, int *threads_starting, int *running);
void *preempt_fpu_c(void *p) { + long rc; int i; + srand(pthread_self()); for (i = 0; i < 21; i++) darray[i] = rand();
- /* Test failed if it ever returns */ - preempt_fpu(darray, &threads_starting, &running); + rc = preempt_fpu(darray, &threads_starting, &running);
- return p; + return (void *)rc; }
int test_preempt_fpu(void) diff --git a/tools/testing/selftests/powerpc/math/vmx_preempt.c b/tools/testing/selftests/powerpc/math/vmx_preempt.c index 6761d6ce30ec..6f7cf400c687 100644 --- a/tools/testing/selftests/powerpc/math/vmx_preempt.c +++ b/tools/testing/selftests/powerpc/math/vmx_preempt.c @@ -37,19 +37,21 @@ __thread vector int varray[] = {{1, 2, 3, 4}, {5, 6, 7, 8}, {9, 10,11,12}, int threads_starting; int running;
-extern void preempt_vmx(vector int *varray, int *threads_starting, int *running); +extern int preempt_vmx(vector int *varray, int *threads_starting, int *running);
void *preempt_vmx_c(void *p) { int i, j; + long rc; + srand(pthread_self()); for (i = 0; i < 12; i++) for (j = 0; j < 4; j++) varray[i][j] = rand();
- /* Test fails if it ever returns */ - preempt_vmx(varray, &threads_starting, &running); - return p; + rc = preempt_vmx(varray, &threads_starting, &running); + + return (void *)rc; }
int test_preempt_vmx(void) diff --git a/tools/testing/selftests/sgx/Makefile b/tools/testing/selftests/sgx/Makefile index 75af864e07b6..04ee17d3d394 100644 --- a/tools/testing/selftests/sgx/Makefile +++ b/tools/testing/selftests/sgx/Makefile @@ -16,9 +16,9 @@ HOST_CFLAGS := -Wall -Werror -g $(INCLUDES) -fPIC -z noexecstack ENCL_CFLAGS := -Wall -Werror -static -nostdlib -nostartfiles -fPIC \ -fno-stack-protector -mrdrnd $(INCLUDES)
+ifeq ($(CAN_BUILD_X86_64), 1) TEST_CUSTOM_PROGS := $(OUTPUT)/test_sgx
-ifeq ($(CAN_BUILD_X86_64), 1) all: $(TEST_CUSTOM_PROGS) $(OUTPUT)/test_encl.elf endif
diff --git a/tools/testing/selftests/sgx/load.c b/tools/testing/selftests/sgx/load.c index 94bdeac1cf04..c9f658e44de6 100644 --- a/tools/testing/selftests/sgx/load.c +++ b/tools/testing/selftests/sgx/load.c @@ -136,11 +136,11 @@ static bool encl_ioc_add_pages(struct encl *encl, struct encl_segment *seg) */ uint64_t encl_get_entry(struct encl *encl, const char *symbol) { + Elf64_Sym *symtab = NULL; + char *sym_names = NULL; Elf64_Shdr *sections; - Elf64_Sym *symtab; Elf64_Ehdr *ehdr; - char *sym_names; - int num_sym; + int num_sym = 0; int i;
ehdr = encl->bin; @@ -161,6 +161,9 @@ uint64_t encl_get_entry(struct encl *encl, const char *symbol) } }
+ if (!symtab || !sym_names) + return 0; + for (i = 0; i < num_sym; i++) { Elf64_Sym *sym = &symtab[i];
diff --git a/tools/testing/selftests/sgx/sigstruct.c b/tools/testing/selftests/sgx/sigstruct.c index a07896a46364..d73b29becf5b 100644 --- a/tools/testing/selftests/sgx/sigstruct.c +++ b/tools/testing/selftests/sgx/sigstruct.c @@ -318,9 +318,9 @@ bool encl_measure(struct encl *encl) struct sgx_sigstruct *sigstruct = &encl->sigstruct; struct sgx_sigstruct_payload payload; uint8_t digest[SHA256_DIGEST_LENGTH]; + EVP_MD_CTX *ctx = NULL; unsigned int siglen; RSA *key = NULL; - EVP_MD_CTX *ctx; int i;
memset(sigstruct, 0, sizeof(*sigstruct)); @@ -384,7 +384,8 @@ bool encl_measure(struct encl *encl) return true;
err: - EVP_MD_CTX_destroy(ctx); + if (ctx) + EVP_MD_CTX_destroy(ctx); RSA_free(key); return false; } diff --git a/tools/testing/selftests/sgx/test_encl.c b/tools/testing/selftests/sgx/test_encl.c index c0d6397295e3..ae791df3e5a5 100644 --- a/tools/testing/selftests/sgx/test_encl.c +++ b/tools/testing/selftests/sgx/test_encl.c @@ -24,10 +24,11 @@ static void do_encl_emodpe(void *_op) secinfo.flags = op->flags;
asm volatile(".byte 0x0f, 0x01, 0xd7" - : + : /* no outputs */ : "a" (EMODPE), "b" (&secinfo), - "c" (op->epc_addr)); + "c" (op->epc_addr) + : "memory" /* read from secinfo pointer */); }
static void do_encl_eaccept(void *_op) @@ -42,7 +43,8 @@ static void do_encl_eaccept(void *_op) : "=a" (rax) : "a" (EACCEPT), "b" (&secinfo), - "c" (op->epc_addr)); + "c" (op->epc_addr) + : "memory" /* read from secinfo pointer */);
op->ret = rax; }
linux-stable-mirror@lists.linaro.org