summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Documentation/arch/powerpc/index.rst1
-rw-r--r--Documentation/devicetree/bindings/soc/xilinx/xilinx.yaml81
-rw-r--r--Documentation/devicetree/bindings/timer/renesas,rz-mtu3.yaml7
-rw-r--r--Documentation/gpu/amdgpu/amd-hardware-list-info.rst4
-rw-r--r--Documentation/gpu/amdgpu/apu-asic-info-table.csv34
-rw-r--r--Documentation/gpu/amdgpu/dgpu-asic-info-table.csv58
-rw-r--r--MAINTAINERS10
-rw-r--r--Next/SHA1s407
-rw-r--r--Next/Trees409
-rw-r--r--Next/merge.log3094
-rw-r--r--arch/arm/boot/dts/aspeed/aspeed-bmc-ibm-everest.dts24
-rw-r--r--arch/arm/boot/dts/aspeed/aspeed-bmc-inspur-fp5280g2.dts3
-rw-r--r--arch/arm/boot/dts/aspeed/aspeed-bmc-opp-lanyang.dts2
-rw-r--r--arch/arm/boot/dts/aspeed/aspeed-bmc-opp-mowgli.dts2
-rw-r--r--arch/arm/boot/dts/aspeed/aspeed-bmc-opp-nicole.dts3
-rw-r--r--arch/arm/boot/dts/aspeed/aspeed-bmc-opp-palmetto.dts2
-rw-r--r--arch/arm/boot/dts/aspeed/aspeed-bmc-opp-romulus.dts3
-rw-r--r--arch/arm/boot/dts/aspeed/aspeed-bmc-opp-witherspoon.dts2
-rw-r--r--arch/arm/boot/dts/aspeed/aspeed-bmc-opp-zaius.dts2
-rw-r--r--arch/arm/boot/dts/aspeed/aspeed-g6.dtsi4
-rw-r--r--arch/arm/boot/dts/aspeed/ibm-power10-dual.dtsi12
-rw-r--r--arch/arm/boot/dts/aspeed/ibm-power10-quad.dtsi12
-rw-r--r--arch/arm64/boot/dts/xilinx/Makefile24
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-sck-kd-g-revA.dtso390
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-sck-kr-g-revA.dtso438
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-sck-kr-g-revB.dtso451
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-sck-kv-g-revA.dtso19
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-sck-kv-g-revB.dtso35
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-sm-k24-revA.dts23
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-sm-k26-revA.dts7
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-smk-k24-revA.dts21
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-zc1751-xm016-dc2.dts1
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-zc1751-xm017-dc3.dts1
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-zcu100-revC.dts21
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-zcu102-revA.dts18
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-zcu104-revA.dts18
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-zcu104-revC.dts18
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-zcu106-revA.dts10
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp-zcu111-revA.dts20
-rw-r--r--arch/arm64/boot/dts/xilinx/zynqmp.dtsi14
-rw-r--r--arch/loongarch/boot/dts/loongson-2k0500-ref.dts9
-rw-r--r--arch/loongarch/boot/dts/loongson-2k0500.dtsi28
-rw-r--r--arch/loongarch/boot/dts/loongson-2k1000-ref.dts13
-rw-r--r--arch/loongarch/boot/dts/loongson-2k1000.dtsi24
-rw-r--r--arch/loongarch/boot/dts/loongson-2k2000-ref.dts10
-rw-r--r--arch/loongarch/boot/dts/loongson-2k2000.dtsi18
-rw-r--r--arch/loongarch/include/asm/inst.h3
-rw-r--r--arch/loongarch/include/asm/loongarch.h7
-rw-r--r--arch/loongarch/kernel/env.c13
-rw-r--r--arch/loongarch/kernel/inst.c55
-rw-r--r--arch/loongarch/kernel/relocate_kernel.S2
-rw-r--r--arch/loongarch/kernel/setup.c18
-rw-r--r--arch/loongarch/kernel/unwind_orc.c2
-rw-r--r--arch/loongarch/net/bpf_jit.c699
-rw-r--r--arch/loongarch/net/bpf_jit.h6
-rw-r--r--arch/loongarch/vdso/Makefile2
-rw-r--r--arch/x86/include/asm/hw_irq.h6
-rw-r--r--arch/x86/include/asm/intel-family.h5
-rw-r--r--arch/x86/kernel/irq.c63
-rw-r--r--block/bfq-iosched.h10
-rw-r--r--drivers/base/regmap/regmap-irq.c30
-rw-r--r--drivers/bluetooth/btintel_pcie.c8
-rw-r--r--drivers/bluetooth/btmtk.c7
-rw-r--r--drivers/bluetooth/btusb.c2
-rw-r--r--drivers/char/ipmi/ipmi_msghandler.c8
-rw-r--r--drivers/dpll/zl3073x/Kconfig10
-rw-r--r--drivers/gpio/gpio-mlxbf2.c2
-rw-r--r--drivers/gpio/gpio-pxa.c8
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_aca.c51
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c7
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_cper.c8
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_cs.c20
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_device.c45
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c24
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c2
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_gem.c37
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_gem.h1
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_gmc.h15
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_job.c7
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_nbio.c3
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_object.h2
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_ras.c21
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_ras.h1
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_reset.h11
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_seq64.c8
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c87
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.h8
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c17
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_vm.h4
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_xcp.c1
-rw-r--r--drivers/gpu/drm/amd/amdgpu/gmc_v10_0.c57
-rw-r--r--drivers/gpu/drm/amd/amdgpu/gmc_v11_0.c57
-rw-r--r--drivers/gpu/drm/amd/amdgpu/gmc_v12_0.c47
-rw-r--r--drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c4
-rw-r--r--drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c4
-rw-r--r--drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c10
-rw-r--r--drivers/gpu/drm/amd/amdgpu/gmc_v9_0.c61
-rw-r--r--drivers/gpu/drm/amd/amdgpu/jpeg_v4_0_3.c2
-rw-r--r--drivers/gpu/drm/amd/amdgpu/jpeg_v5_0_1.c23
-rw-r--r--drivers/gpu/drm/amd/amdgpu/mmhub_v3_0_1.c57
-rw-r--r--drivers/gpu/drm/amd/amdgpu/mmhub_v3_3.c105
-rw-r--r--drivers/gpu/drm/amd/amdgpu/sdma_v7_0.c2
-rw-r--r--drivers/gpu/drm/amd/amdgpu/vcn_v2_0.c79
-rw-r--r--drivers/gpu/drm/amd/amdgpu/vcn_v2_5.c83
-rw-r--r--drivers/gpu/drm/amd/amdgpu/vcn_v3_0.c78
-rw-r--r--drivers/gpu/drm/amd/amdgpu/vcn_v4_0.c80
-rw-r--r--drivers/gpu/drm/amd/amdgpu/vcn_v4_0_3.c81
-rw-r--r--drivers/gpu/drm/amd/amdgpu/vcn_v4_0_5.c80
-rw-r--r--drivers/gpu/drm/amd/amdgpu/vcn_v5_0_0.c91
-rw-r--r--drivers/gpu/drm/amd/amdgpu/vcn_v5_0_0.h5
-rw-r--r--drivers/gpu/drm/amd/amdgpu/vcn_v5_0_1.c61
-rw-r--r--drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager.c2
-rw-r--r--drivers/gpu/drm/amd/amdkfd/kfd_mqd_manager_v9.c61
-rw-r--r--drivers/gpu/drm/amd/amdkfd/kfd_process_queue_manager.c20
-rw-r--r--drivers/gpu/drm/amd/amdkfd/kfd_svm.c13
-rw-r--r--drivers/gpu/drm/amd/amdxcp/amdgpu_xcp_drv.c56
-rw-r--r--drivers/gpu/drm/amd/amdxcp/amdgpu_xcp_drv.h1
-rw-r--r--drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c81
-rw-r--r--drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h14
-rw-r--r--drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crtc.c9
-rw-r--r--drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c9
-rw-r--r--drivers/gpu/drm/amd/display/dc/clk_mgr/clk_mgr.c1
-rw-r--r--drivers/gpu/drm/amd/display/dc/clk_mgr/dce100/dce_clk_mgr.c5
-rw-r--r--drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c16
-rw-r--r--drivers/gpu/drm/amd/display/dc/core/dc.c37
-rw-r--r--drivers/gpu/drm/amd/display/dc/core/dc_resource.c8
-rw-r--r--drivers/gpu/drm/amd/display/dc/dc.h59
-rw-r--r--drivers/gpu/drm/amd/display/dc/dml/dcn301/dcn301_fpu.c20
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubbub/dcn30/dcn30_hubbub.c31
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubbub/dcn30/dcn30_hubbub.h6
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubbub/dcn31/dcn31_hubbub.c2
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubbub/dcn32/dcn32_hubbub.c2
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubbub/dcn35/dcn35_hubbub.c2
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubbub/dcn401/dcn401_hubbub.c2
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubp/dcn10/dcn10_hubp.h9
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubp/dcn20/dcn20_hubp.h1
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubp/dcn30/dcn30_hubp.c26
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubp/dcn30/dcn30_hubp.h8
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubp/dcn31/dcn31_hubp.c15
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubp/dcn31/dcn31_hubp.h6
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubp/dcn32/dcn32_hubp.c3
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubp/dcn35/dcn35_hubp.c3
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubp/dcn401/dcn401_hubp.c41
-rw-r--r--drivers/gpu/drm/amd/display/dc/hubp/dcn401/dcn401_hubp.h8
-rw-r--r--drivers/gpu/drm/amd/display/dc/hwss/dcn10/dcn10_hwseq.c63
-rw-r--r--drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_hwseq.c48
-rw-r--r--drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_hwseq.h5
-rw-r--r--drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_init.c1
-rw-r--r--drivers/gpu/drm/amd/display/dc/hwss/dcn31/dcn31_init.c1
-rw-r--r--drivers/gpu/drm/amd/display/dc/hwss/dcn314/dcn314_init.c1
-rw-r--r--drivers/gpu/drm/amd/display/dc/hwss/dcn32/dcn32_init.c1
-rw-r--r--drivers/gpu/drm/amd/display/dc/hwss/dcn35/dcn35_init.c1
-rw-r--r--drivers/gpu/drm/amd/display/dc/hwss/dcn351/dcn351_init.c1
-rw-r--r--drivers/gpu/drm/amd/display/dc/hwss/dcn401/dcn401_hwseq.c36
-rw-r--r--drivers/gpu/drm/amd/display/dc/hwss/dcn401/dcn401_init.c1
-rw-r--r--drivers/gpu/drm/amd/display/dc/hwss/hw_sequencer.h4
-rw-r--r--drivers/gpu/drm/amd/display/dc/inc/hw/dchubbub.h2
-rw-r--r--drivers/gpu/drm/amd/display/dc/inc/hw/hubp.h21
-rw-r--r--drivers/gpu/drm/amd/display/dc/inc/hw/mpc.h11
-rw-r--r--drivers/gpu/drm/amd/display/dc/link/protocols/link_edp_panel_control.c2
-rw-r--r--drivers/gpu/drm/amd/display/dc/resource/dce60/dce60_resource.c34
-rw-r--r--drivers/gpu/drm/amd/display/dc/resource/dcn32/dcn32_resource.h3
-rw-r--r--drivers/gpu/drm/amd/display/dc/resource/dcn401/dcn401_resource.c1
-rw-r--r--drivers/gpu/drm/amd/display/dc/resource/dcn401/dcn401_resource.h3
-rw-r--r--drivers/gpu/drm/amd/display/dmub/dmub_srv.h1
-rw-r--r--drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h3
-rw-r--r--drivers/gpu/drm/amd/display/dmub/src/dmub_dcn31.c1
-rw-r--r--drivers/gpu/drm/amd/display/include/dal_asic_id.h5
-rw-r--r--drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c16
-rw-r--r--drivers/gpu/drm/amd/pm/swsmu/smu11/arcturus_ppt.c2
-rw-r--r--drivers/gpu/drm/amd/pm/swsmu/smu13/aldebaran_ppt.c2
-rw-r--r--drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_6_ppt.c30
-rw-r--r--drivers/gpu/drm/bridge/aux-bridge.c2
-rw-r--r--drivers/gpu/drm/drm_bridge.c1
-rw-r--r--drivers/gpu/drm/drm_gem.c2
-rw-r--r--drivers/gpu/drm/i915/gem/i915_gem_shmem.c7
-rw-r--r--drivers/gpu/drm/ttm/ttm_backup.c2
-rw-r--r--drivers/gpu/drm/xe/Kconfig1
-rw-r--r--drivers/gpu/drm/xe/abi/guc_actions_abi.h8
-rw-r--r--drivers/gpu/drm/xe/xe_device.c8
-rw-r--r--drivers/gpu/drm/xe/xe_exec_queue.c48
-rw-r--r--drivers/gpu/drm/xe/xe_exec_queue.h4
-rw-r--r--drivers/gpu/drm/xe/xe_gpu_scheduler.c13
-rw-r--r--drivers/gpu/drm/xe/xe_gpu_scheduler.h1
-rw-r--r--drivers/gpu/drm/xe/xe_gt.c10
-rw-r--r--drivers/gpu/drm/xe/xe_gt_debugfs.c5
-rw-r--r--drivers/gpu/drm/xe/xe_gt_sriov_pf.c79
-rw-r--r--drivers/gpu/drm/xe/xe_gt_sriov_pf.h1
-rw-r--r--drivers/gpu/drm/xe/xe_gt_sriov_pf_config.c10
-rw-r--r--drivers/gpu/drm/xe/xe_gt_sriov_pf_debugfs.c4
-rw-r--r--drivers/gpu/drm/xe/xe_gt_sriov_vf.c14
-rw-r--r--drivers/gpu/drm/xe/xe_gt_sriov_vf.h1
-rw-r--r--drivers/gpu/drm/xe/xe_guc_buf.c2
-rw-r--r--drivers/gpu/drm/xe/xe_guc_capture.c6
-rw-r--r--drivers/gpu/drm/xe/xe_guc_submit.c175
-rw-r--r--drivers/gpu/drm/xe/xe_guc_submit.h9
-rw-r--r--drivers/gpu/drm/xe/xe_guc_types.h6
-rw-r--r--drivers/gpu/drm/xe/xe_lrc.c107
-rw-r--r--drivers/gpu/drm/xe/xe_lrc.h9
-rw-r--r--drivers/gpu/drm/xe/xe_pci_sriov.c7
-rw-r--r--drivers/gpu/drm/xe/xe_sa.c1
-rw-r--r--drivers/gpu/drm/xe/xe_sa.h15
-rw-r--r--drivers/gpu/drm/xe/xe_sa_types.h1
-rw-r--r--drivers/gpu/drm/xe/xe_sriov_pf.c27
-rw-r--r--drivers/gpu/drm/xe/xe_sriov_pf.h1
-rw-r--r--drivers/gpu/drm/xe/xe_sriov_vf.c78
-rw-r--r--drivers/gpu/drm/xe/xe_sriov_vf_ccs.c6
-rw-r--r--drivers/gpu/drm/xe/xe_wa.c13
-rw-r--r--drivers/i2c/busses/Kconfig1
-rw-r--r--drivers/i2c/i2c-core-acpi.c1
-rw-r--r--drivers/i2c/muxes/i2c-mux-mule.c3
-rw-r--r--drivers/iio/accel/sca3300.c2
-rw-r--r--drivers/iio/adc/ad7124.c14
-rw-r--r--drivers/iio/adc/ad7173.c87
-rw-r--r--drivers/iio/proximity/isl29501.c16
-rw-r--r--drivers/iio/temperature/maxim_thermocouple.c26
-rw-r--r--drivers/input/misc/max77693-haptic.c41
-rw-r--r--drivers/irqchip/irq-riscv-imsic-platform.c2
-rw-r--r--drivers/md/dm-raid.c42
-rw-r--r--drivers/md/md-bitmap.c8
-rw-r--r--drivers/md/md-cluster.c16
-rw-r--r--drivers/md/md.c73
-rw-r--r--drivers/md/md.h2
-rw-r--r--drivers/md/raid0.c6
-rw-r--r--drivers/md/raid1-10.c2
-rw-r--r--drivers/md/raid1.c94
-rw-r--r--drivers/md/raid1.h22
-rw-r--r--drivers/md/raid10.c16
-rw-r--r--drivers/md/raid5-ppl.c6
-rw-r--r--drivers/md/raid5.c30
-rw-r--r--drivers/media/Kconfig13
-rw-r--r--drivers/media/Makefile2
-rw-r--r--drivers/media/virtio/Makefile9
-rw-r--r--drivers/media/virtio/protocol.h288
-rw-r--r--drivers/media/virtio/scatterlist_builder.c563
-rw-r--r--drivers/media/virtio/scatterlist_builder.h111
-rw-r--r--drivers/media/virtio/session.h109
-rw-r--r--drivers/media/virtio/virtio_media.h93
-rw-r--r--drivers/media/virtio/virtio_media_driver.c959
-rw-r--r--drivers/media/virtio/virtio_media_ioctls.c1297
-rw-r--r--drivers/net/ethernet/airoha/airoha_ppe.c26
-rw-r--r--drivers/net/ethernet/mellanox/mlx5/core/en_rx.c1
-rw-r--r--drivers/net/ethernet/sfc/tc_encap_actions.c2
-rw-r--r--drivers/net/mdio/mdio-bcm-unimac.c5
-rw-r--r--drivers/rtc/rtc-ds1307.c15
-rw-r--r--drivers/rtc/rtc-ds1685.c4
-rw-r--r--drivers/rtc/rtc-hym8563.c15
-rw-r--r--drivers/rtc/rtc-m41t80.c21
-rw-r--r--drivers/rtc/rtc-max31335.c12
-rw-r--r--drivers/rtc/rtc-nct3018y.c15
-rw-r--r--drivers/rtc/rtc-pcf85063.c15
-rw-r--r--drivers/rtc/rtc-pcf8563.c15
-rw-r--r--drivers/rtc/rtc-rv3028.c15
-rw-r--r--drivers/rtc/rtc-rv3032.c21
-rw-r--r--drivers/tee/optee/core.c2
-rw-r--r--drivers/tee/tee_core.c2
-rw-r--r--drivers/tee/tee_shm.c14
-rw-r--r--drivers/vhost/vhost.c1
-rw-r--r--drivers/video/console/vgacon.c2
-rw-r--r--drivers/video/fbdev/core/fbcon.c9
-rw-r--r--drivers/virtio/virtio_ring.c12
-rw-r--r--fs/bcachefs/alloc_background.c64
-rw-r--r--fs/bcachefs/backpointers.c28
-rw-r--r--fs/bcachefs/bcachefs.h21
-rw-r--r--fs/bcachefs/bcachefs_format.h42
-rw-r--r--fs/bcachefs/bkey_methods.c6
-rw-r--r--fs/bcachefs/bkey_types.h5
-rw-r--r--fs/bcachefs/btree_cache.c6
-rw-r--r--fs/bcachefs/btree_cache.h8
-rw-r--r--fs/bcachefs/btree_gc.c127
-rw-r--r--fs/bcachefs/btree_io.c2
-rw-r--r--fs/bcachefs/btree_iter.c78
-rw-r--r--fs/bcachefs/btree_iter.h6
-rw-r--r--fs/bcachefs/btree_key_cache.c1
-rw-r--r--fs/bcachefs/btree_node_scan.c4
-rw-r--r--fs/bcachefs/btree_trans_commit.c2
-rw-r--r--fs/bcachefs/btree_types.h18
-rw-r--r--fs/bcachefs/btree_update.c57
-rw-r--r--fs/bcachefs/btree_update.h17
-rw-r--r--fs/bcachefs/btree_update_interior.c22
-rw-r--r--fs/bcachefs/btree_write_buffer.c10
-rw-r--r--fs/bcachefs/btree_write_buffer.h2
-rw-r--r--fs/bcachefs/data_update.c11
-rw-r--r--fs/bcachefs/data_update.h1
-rw-r--r--fs/bcachefs/dirent.c17
-rw-r--r--fs/bcachefs/disk_accounting.c3
-rw-r--r--fs/bcachefs/disk_accounting.h10
-rw-r--r--fs/bcachefs/ec.c36
-rw-r--r--fs/bcachefs/errcode.h1
-rw-r--r--fs/bcachefs/error.h3
-rw-r--r--fs/bcachefs/extent_update.c56
-rw-r--r--fs/bcachefs/extent_update.h2
-rw-r--r--fs/bcachefs/extents.c17
-rw-r--r--fs/bcachefs/extents.h1
-rw-r--r--fs/bcachefs/fs-io-buffered.c1
-rw-r--r--fs/bcachefs/fs.c16
-rw-r--r--fs/bcachefs/fsck.c35
-rw-r--r--fs/bcachefs/inode.c7
-rw-r--r--fs/bcachefs/io_misc.c14
-rw-r--r--fs/bcachefs/logged_ops.h2
-rw-r--r--fs/bcachefs/lru.h10
-rw-r--r--fs/bcachefs/move.c24
-rw-r--r--fs/bcachefs/movinggc.c188
-rw-r--r--fs/bcachefs/namei.c11
-rw-r--r--fs/bcachefs/rebalance.c93
-rw-r--r--fs/bcachefs/recovery.c195
-rw-r--r--fs/bcachefs/sb-counters_format.h6
-rw-r--r--fs/bcachefs/sb-errors_format.h4
-rw-r--r--fs/bcachefs/sb-members.c116
-rw-r--r--fs/bcachefs/sb-members.h25
-rw-r--r--fs/bcachefs/snapshot.c2
-rw-r--r--fs/bcachefs/super-io.c37
-rw-r--r--fs/bcachefs/super.c315
-rw-r--r--fs/bcachefs/trace.h5
-rw-r--r--fs/ext4/namei.c2
-rw-r--r--fs/smb/client/cifs_debug.c6
-rw-r--r--fs/smb/client/smbdirect.c124
-rw-r--r--fs/smb/client/smbdirect.h4
-rw-r--r--include/crypto/hash.h2
-rw-r--r--include/linux/module.h18
-rw-r--r--include/linux/ring_buffer.h3
-rw-r--r--include/linux/rtc/ds1685.h2
-rw-r--r--include/linux/shmem_fs.h4
-rw-r--r--include/linux/skbuff.h23
-rw-r--r--include/net/dst.h12
-rw-r--r--include/net/udp.h24
-rw-r--r--include/uapi/linux/raid/md_p.h2
-rw-r--r--include/uapi/linux/vhost.h4
-rw-r--r--include/uapi/linux/virtio_ids.h1
-rw-r--r--include/uapi/linux/vt.h34
-rw-r--r--kernel/bpf/verifier.c5
-rw-r--r--kernel/fork.c2
-rw-r--r--kernel/hung_task.c78
-rw-r--r--kernel/panic.c27
-rw-r--r--kernel/sched/psi.c6
-rw-r--r--kernel/smp.c2
-rw-r--r--kernel/trace/ring_buffer.c16
-rw-r--r--kernel/trace/trace.c287
-rw-r--r--kernel/trace/trace_events_synth.c6
-rw-r--r--kernel/trace/trace_output.c8
-rw-r--r--lib/Kconfig.debug1
-rw-r--r--localversion-next1
-rw-r--r--mm/debug_vm_pgtable.c9
-rw-r--r--mm/kasan/kasan_test_c.c2
-rw-r--r--mm/kmemleak.c5
-rw-r--r--mm/mempool.c24
-rw-r--r--mm/shmem.c9
-rw-r--r--mm/userfaultfd.c9
-rw-r--r--net/core/filter.c3
-rw-r--r--net/ipv4/ip_output.c15
-rw-r--r--net/ipv6/ip6_offload.c4
-rw-r--r--net/netfilter/nf_bpf_link.c3
-rw-r--r--net/sched/sch_taprio.c21
-rw-r--r--rust/helpers/helpers.c2
-rw-r--r--rust/kernel/device_id.rs8
-rw-r--r--scripts/Makefile.vmlinux14
-rwxr-xr-xscripts/link-vmlinux.sh5
-rwxr-xr-xscripts/mksysmap3
-rw-r--r--scripts/mod/file2alias.c34
-rw-r--r--scripts/mod/modpost.c15
-rw-r--r--scripts/mod/modpost.h2
-rw-r--r--security/apparmor/policy.c5
-rw-r--r--sound/hda/codecs/realtek/alc269.c1
-rw-r--r--sound/usb/pcm.c9
-rw-r--r--tools/accounting/getdelays.c167
-rw-r--r--tools/perf/util/build-id.c2
-rw-r--r--tools/testing/selftests/bpf/progs/verifier_ctx.c23
-rw-r--r--tools/testing/selftests/mm/uffd-stress.c2
-rwxr-xr-xtools/testing/selftests/net/test_neigh.sh6
-rwxr-xr-xtools/testing/selftests/net/vlan_hw_filter.sh16
370 files changed, 10624 insertions, 6247 deletions
diff --git a/Documentation/arch/powerpc/index.rst b/Documentation/arch/powerpc/index.rst
index 592efca7d8ec..53fc9f89f3e4 100644
--- a/Documentation/arch/powerpc/index.rst
+++ b/Documentation/arch/powerpc/index.rst
@@ -37,7 +37,6 @@ powerpc
vas-api
vcpudispatch_stats
vmemmap_dedup
- htm
features
diff --git a/Documentation/devicetree/bindings/soc/xilinx/xilinx.yaml b/Documentation/devicetree/bindings/soc/xilinx/xilinx.yaml
index fb5c39c79d28..c9f99e0df2b3 100644
--- a/Documentation/devicetree/bindings/soc/xilinx/xilinx.yaml
+++ b/Documentation/devicetree/bindings/soc/xilinx/xilinx.yaml
@@ -116,6 +116,36 @@ properties:
- const: xlnx,zynqmp-zcu111
- const: xlnx,zynqmp
+ - description: Xilinx Kria SOMs K24
+ minItems: 3
+ items:
+ enum:
+ - xlnx,zynqmp-sm-k24-rev1
+ - xlnx,zynqmp-sm-k24-revB
+ - xlnx,zynqmp-sm-k24-revA
+ - xlnx,zynqmp-sm-k24
+ - xlnx,zynqmp
+ allOf:
+ - contains:
+ const: xlnx,zynqmp
+ - contains:
+ const: xlnx,zynqmp-sm-k24
+
+ - description: Xilinx Kria SOMs K24 (starter)
+ minItems: 3
+ items:
+ enum:
+ - xlnx,zynqmp-smk-k24-rev1
+ - xlnx,zynqmp-smk-k24-revB
+ - xlnx,zynqmp-smk-k24-revA
+ - xlnx,zynqmp-smk-k24
+ - xlnx,zynqmp
+ allOf:
+ - contains:
+ const: xlnx,zynqmp
+ - contains:
+ const: xlnx,zynqmp-smk-k24
+
- description: Xilinx Kria SOMs
minItems: 3
items:
@@ -148,6 +178,57 @@ properties:
- contains:
const: xlnx,zynqmp-smk-k26
+ - description: Xilinx Kria SOM KD240 revA/B/1
+ minItems: 3
+ items:
+ enum:
+ - xlnx,zynqmp-sk-kd240-rev1
+ - xlnx,zynqmp-sk-kd240-revB
+ - xlnx,zynqmp-sk-kd240-revA
+ - xlnx,zynqmp-sk-kd240
+ - xlnx,zynqmp
+ allOf:
+ - contains:
+ const: xlnx,zynqmp-sk-kd240-revA
+ - contains:
+ const: xlnx,zynqmp-sk-kd240
+ - contains:
+ const: xlnx,zynqmp
+
+ - description: Xilinx Kria SOM KR260 revA/Y/Z
+ minItems: 3
+ items:
+ enum:
+ - xlnx,zynqmp-sk-kr260-revA
+ - xlnx,zynqmp-sk-kr260-revY
+ - xlnx,zynqmp-sk-kr260-revZ
+ - xlnx,zynqmp-sk-kr260
+ - xlnx,zynqmp
+ allOf:
+ - contains:
+ const: xlnx,zynqmp-sk-kr260-revA
+ - contains:
+ const: xlnx,zynqmp-sk-kr260
+ - contains:
+ const: xlnx,zynqmp
+
+ - description: Xilinx Kria SOM KR260 rev2/1/B
+ minItems: 3
+ items:
+ enum:
+ - xlnx,zynqmp-sk-kr260-rev2
+ - xlnx,zynqmp-sk-kr260-rev1
+ - xlnx,zynqmp-sk-kr260-revB
+ - xlnx,zynqmp-sk-kr260
+ - xlnx,zynqmp
+ allOf:
+ - contains:
+ const: xlnx,zynqmp-sk-kr260-revB
+ - contains:
+ const: xlnx,zynqmp-sk-kr260
+ - contains:
+ const: xlnx,zynqmp
+
- description: Xilinx Kria SOM KV260 revA/Y/Z
minItems: 3
items:
diff --git a/Documentation/devicetree/bindings/timer/renesas,rz-mtu3.yaml b/Documentation/devicetree/bindings/timer/renesas,rz-mtu3.yaml
index 3ad10c5b66ba..3931054b42fb 100644
--- a/Documentation/devicetree/bindings/timer/renesas,rz-mtu3.yaml
+++ b/Documentation/devicetree/bindings/timer/renesas,rz-mtu3.yaml
@@ -221,10 +221,7 @@ properties:
maxItems: 1
"#pwm-cells":
- oneOf:
- - const: 2
- deprecated: true
- - const: 3
+ const: 2
required:
- compatible
@@ -302,5 +299,5 @@ examples:
clocks = <&cpg CPG_MOD R9A07G044_MTU_X_MCK_MTU3>;
power-domains = <&cpg>;
resets = <&cpg R9A07G044_MTU_X_PRESET_MTU3>;
- #pwm-cells = <3>;
+ #pwm-cells = <2>;
};
diff --git a/Documentation/gpu/amdgpu/amd-hardware-list-info.rst b/Documentation/gpu/amdgpu/amd-hardware-list-info.rst
index 1786544fe7c1..e72f4ff770c4 100644
--- a/Documentation/gpu/amdgpu/amd-hardware-list-info.rst
+++ b/Documentation/gpu/amdgpu/amd-hardware-list-info.rst
@@ -10,7 +10,7 @@ Accelerated Processing Units (APU) Info
.. csv-table::
:header-rows: 1
- :widths: 3, 2, 2, 1, 1, 1, 1
+ :widths: 3, 2, 2, 1, 1, 1, 1, 1
:file: ./apu-asic-info-table.csv
Discrete GPU Info
@@ -18,6 +18,6 @@ Discrete GPU Info
.. csv-table::
:header-rows: 1
- :widths: 3, 2, 2, 1, 1, 1
+ :widths: 3, 2, 2, 1, 1, 1, 1, 1
:file: ./dgpu-asic-info-table.csv
diff --git a/Documentation/gpu/amdgpu/apu-asic-info-table.csv b/Documentation/gpu/amdgpu/apu-asic-info-table.csv
index 1d50b539677f..b479c5629146 100644
--- a/Documentation/gpu/amdgpu/apu-asic-info-table.csv
+++ b/Documentation/gpu/amdgpu/apu-asic-info-table.csv
@@ -1,17 +1,17 @@
-Product Name, Code Reference, DCN/DCE version, GC version, VCE/UVD/VCN version, SDMA version, MP0 version
-Radeon R* Graphics, CARRIZO/STONEY, DCE 11, 8, VCE 3 / UVD 6, 3, n/a
-Ryzen 3000 series / AMD Ryzen Embedded V1*/R1* with Radeon Vega Gfx, RAVEN/PICASSO, DCN 1.0, 9.1.0, VCN 1.0, 4.1.0, 10.0.0
-Ryzen 4000 series, RENOIR, DCN 2.1, 9.3, VCN 2.2, 4.1.2, 11.0.3
-Ryzen 3000 series / AMD Ryzen Embedded V1*/R1* with Radeon Vega Gfx, RAVEN2, DCN 1.0, 9.2.2, VCN 1.0.1, 4.1.1, 10.0.1
-SteamDeck, VANGOGH, DCN 3.0.1, 10.3.1, VCN 3.1.0, 5.2.1, 11.5.0
-Ryzen 5000 series / Ryzen 7x30 series, GREEN SARDINE / Cezanne / Barcelo / Barcelo-R, DCN 2.1, 9.3, VCN 2.2, 4.1.1, 12.0.1
-Ryzen 6000 series / Ryzen 7x35 series / Ryzen 7x36 series, YELLOW CARP / Rembrandt / Rembrandt-R, 3.1.2, 10.3.3, VCN 3.1.1, 5.2.3, 13.0.3
-Ryzen 7000 series (AM5), Raphael, 3.1.5, 10.3.6, 3.1.2, 5.2.6, 13.0.5
-Ryzen 9000 series (AM5), Granite Ridge, 3.1.5, 10.3.6, 3.1.2, 5.2.6, 13.0.5
-Ryzen 7x45 series (FL1), Dragon Range, 3.1.5, 10.3.6, 3.1.2, 5.2.6, 13.0.5
-Ryzen 7x20 series, Mendocino, 3.1.6, 10.3.7, 3.1.1, 5.2.7, 13.0.8
-Ryzen 7x40 series, Phoenix, 3.1.4, 11.0.1 / 11.0.4, 4.0.2, 6.0.1, 13.0.4 / 13.0.11
-Ryzen 8x40 series, Hawk Point, 3.1.4, 11.0.1 / 11.0.4, 4.0.2, 6.0.1, 13.0.4 / 13.0.11
-Ryzen AI 300 series, Strix Point, 3.5.0, 11.5.0, 4.0.5, 6.1.0, 14.0.0
-Ryzen AI 350 series, Krackan Point, 3.5.0, 11.5.2, 4.0.5, 6.1.2, 14.0.4
-Ryzen AI Max 300 series, Strix Halo, 3.5.1, 11.5.1, 4.0.6, 6.1.1, 14.0.1
+Product Name, Code Reference, DCN/DCE version, GC version, VCE/UVD/VCN version, SDMA version, MP0 version, MP1 version
+Radeon R* Graphics, CARRIZO/STONEY, DCE 11, 8, VCE 3 / UVD 6, 3, n/a, 8
+Ryzen 3000 series / AMD Ryzen Embedded V1*/R1* with Radeon Vega Gfx, RAVEN/PICASSO, DCN 1.0, 9.1.0, VCN 1.0, 4.1.0, 10.0.0, 10.0.0
+Ryzen 4000 series, RENOIR, DCN 2.1, 9.3, VCN 2.2, 4.1.2, 11.0.3, 12.0.1
+Ryzen 3000 series / AMD Ryzen Embedded V1*/R1* with Radeon Vega Gfx, RAVEN2, DCN 1.0, 9.2.2, VCN 1.0.1, 4.1.1, 10.0.1, 10.0.1
+SteamDeck, VANGOGH, DCN 3.0.1, 10.3.1, VCN 3.1.0, 5.2.1, 11.5.0, 11.5.0
+Ryzen 5000 series / Ryzen 7x30 series, GREEN SARDINE / Cezanne / Barcelo / Barcelo-R, DCN 2.1, 9.3, VCN 2.2, 4.1.1, 12.0.1, 12.0.1
+Ryzen 6000 series / Ryzen 7x35 series / Ryzen 7x36 series, YELLOW CARP / Rembrandt / Rembrandt-R, 3.1.2, 10.3.3, VCN 3.1.1, 5.2.3, 13.0.3, 13.0.3
+Ryzen 7000 series (AM5), Raphael, 3.1.5, 10.3.6, 3.1.2, 5.2.6, 13.0.5, 13.0.5
+Ryzen 9000 series (AM5), Granite Ridge, 3.1.5, 10.3.6, 3.1.2, 5.2.6, 13.0.5, 13.0.5
+Ryzen 7x45 series (FL1), Dragon Range, 3.1.5, 10.3.6, 3.1.2, 5.2.6, 13.0.5, 13.0.5
+Ryzen 7x20 series, Mendocino, 3.1.6, 10.3.7, 3.1.1, 5.2.7, 13.0.8, 13.0.8
+Ryzen 7x40 series, Phoenix, 3.1.4, 11.0.1 / 11.0.4, 4.0.2, 6.0.1, 13.0.4 / 13.0.11, 13.0.4 / 13.0.11
+Ryzen 8x40 series, Hawk Point, 3.1.4, 11.0.1 / 11.0.4, 4.0.2, 6.0.1, 13.0.4 / 13.0.11, 13.0.4 / 13.0.11
+Ryzen AI 300 series, Strix Point, 3.5.0, 11.5.0, 4.0.5, 6.1.0, 14.0.0, 14.0.0
+Ryzen AI 350 series, Krackan Point, 3.5.0, 11.5.2, 4.0.5, 6.1.2, 14.0.4, 14.0.4
+Ryzen AI Max 300 series, Strix Halo, 3.5.1, 11.5.1, 4.0.6, 6.1.1, 14.0.1, 14.0.1
diff --git a/Documentation/gpu/amdgpu/dgpu-asic-info-table.csv b/Documentation/gpu/amdgpu/dgpu-asic-info-table.csv
index d2f10ee69dfc..a3796daec9ec 100644
--- a/Documentation/gpu/amdgpu/dgpu-asic-info-table.csv
+++ b/Documentation/gpu/amdgpu/dgpu-asic-info-table.csv
@@ -1,28 +1,30 @@
-Product Name, Code Reference, DCN/DCE version, GC version, VCN version, SDMA version
-AMD Radeon (TM) HD 8500M/ 8600M /M200 /M320 /M330 /M335 Series, HAINAN, --, 6, --, --
-AMD Radeon HD 7800 /7900 /FireGL Series, TAHITI, DCE 6, 6, VCE 1 / UVD 3, --
-AMD Radeon R7 (TM|HD) M265 /M370 /8500M /8600 /8700 /8700M, OLAND, DCE 6, 6, VCE 1 / UVD 3, --
-AMD Radeon (TM) (HD|R7) 7800 /7970 /8800 /8970 /370/ Series, PITCAIRN, DCE 6, 6, VCE 1 / UVD 3, --
-AMD Radeon (TM|R7|R9|HD) E8860 /M360 /7700 /7800 /8800 /9000(M) /W4100 Series, VERDE, DCE 6, 6, VCE 1 / UVD 3, --
-AMD Radeon HD M280X /M380 /7700 /8950 /W5100, BONAIRE, DCE 8, 7, VCE 2 / UVD 4.2, 1
-AMD Radeon (R9|TM) 200 /390 /W8100 /W9100 Series, HAWAII, DCE 8, 7, VCE 2 / UVD 4.2, 1
-AMD Radeon (TM) R(5|7) M315 /M340 /M360, TOPAZ, *, 8, --, 2
-AMD Radeon (TM) R9 200 /380 /W7100 /S7150 /M390 /M395 Series, TONGA, DCE 10, 8, VCE 3 / UVD 5, 3
-AMD Radeon (FirePro) (TM) R9 Fury Series, FIJI, DCE 10, 8, VCE 3 / UVD 6, 3
-Radeon RX 470 /480 /570 /580 /590 Series - AMD Radeon (TM) (Pro WX) 5100 /E9390 /E9560 /E9565 /V7350 /7100 /P30PH, POLARIS10, DCE 11.2, 8, VCE 3.4 / UVD 6.3, 3
-Radeon (TM) (RX|Pro WX) E9260 /460 /V5300X /550 /560(X) Series, POLARIS11, DCE 11.2, 8, VCE 3.4 / UVD 6.3, 3
-Radeon (RX/Pro) 500 /540(X) /550 /640 /WX2100 /WX3100 /WX200 Series, POLARIS12, DCE 11.2, 8, VCE 3.4 / UVD 6.3, 3
-Radeon (RX|TM) (PRO|WX) Vega /MI25 /V320 /V340L /8200 /9100 /SSG MxGPU, VEGA10, DCE 12, 9.0.1, VCE 4.0.0 / UVD 7.0.0, 4.0.0
-AMD Radeon (Pro) VII /MI50 /MI60, VEGA20, DCE 12, 9.4.0, VCE 4.1.0 / UVD 7.2.0, 4.2.0
-MI100, ARCTURUS, *, 9.4.1, VCN 2.5.0, 4.2.2
-MI200 Series, ALDEBARAN, *, 9.4.2, VCN 2.6.0, 4.4.0
-MI300 Series, AQUA_VANJARAM, *, 9.4.3, VCN 4.0.3, 4.4.2
-AMD Radeon (RX|Pro) 5600(M|XT) /5700 (M|XT|XTB) /W5700, NAVI10, DCN 2.0.0, 10.1.10, VCN 2.0.0, 5.0.0
-AMD Radeon (Pro) 5300 /5500XTB/5500(XT|M) /W5500M /W5500, NAVI14, DCN 2.0.0, 10.1.1, VCN 2.0.2, 5.0.2
-AMD Radeon RX 6800(XT) /6900(XT) /W6800, SIENNA_CICHLID, DCN 3.0.0, 10.3.0, VCN 3.0.0, 5.2.0
-AMD Radeon RX 6700 XT / 6800M / 6700M, NAVY_FLOUNDER, DCN 3.0.0, 10.3.2, VCN 3.0.0, 5.2.2
-AMD Radeon RX 6600(XT) /6600M /W6600 /W6600M, DIMGREY_CAVEFISH, DCN 3.0.2, 10.3.4, VCN 3.0.16, 5.2.4
-AMD Radeon RX 6500M /6300M /W6500M /W6300M, BEIGE_GOBY, DCN 3.0.3, 10.3.5, VCN 3.0.33, 5.2.5
-AMD Radeon RX 7900 XT /XTX, , DCN 3.2.0, 11.0.0, VCN 4.0.0, 6.0.0
-AMD Radeon RX 7800 XT, , DCN 3.2.0, 11.0.3, VCN 4.0.0, 6.0.3
-AMD Radeon RX 7600M (XT) /7700S /7600S, , DCN 3.2.1, 11.0.2, VCN 4.0.4, 6.0.2
+Product Name, Code Reference, DCN/DCE version, GC version, VCN version, SDMA version, MP0 version, MP1 version
+AMD Radeon (TM) HD 8500M/ 8600M /M200 /M320 /M330 /M335 Series, HAINAN, --, 6, --, --, --, 6
+AMD Radeon HD 7800 /7900 /FireGL Series, TAHITI, DCE 6, 6, VCE 1 / UVD 3, --, --, 6
+AMD Radeon R7 (TM|HD) M265 /M370 /8500M /8600 /8700 /8700M, OLAND, DCE 6, 6, VCE 1 / UVD 3, --, --, 6
+AMD Radeon (TM) (HD|R7) 7800 /7970 /8800 /8970 /370/ Series, PITCAIRN, DCE 6, 6, VCE 1 / UVD 3, --, --, 6
+AMD Radeon (TM|R7|R9|HD) E8860 /M360 /7700 /7800 /8800 /9000(M) /W4100 Series, VERDE, DCE 6, 6, VCE 1 / UVD 3, --, --, 6
+AMD Radeon HD M280X /M380 /7700 /8950 /W5100, BONAIRE, DCE 8, 7, VCE 2 / UVD 4.2, 1, --, 7
+AMD Radeon (R9|TM) 200 /390 /W8100 /W9100 Series, HAWAII, DCE 8, 7, VCE 2 / UVD 4.2, 1, --, 7
+AMD Radeon (TM) R(5|7) M315 /M340 /M360, TOPAZ, *, 8, --, 2, n/a, 7
+AMD Radeon (TM) R9 200 /380 /W7100 /S7150 /M390 /M395 Series, TONGA, DCE 10, 8, VCE 3 / UVD 5, 3, n/a, 7
+AMD Radeon (FirePro) (TM) R9 Fury Series, FIJI, DCE 10, 8, VCE 3 / UVD 6, 3, n/a, 7
+Radeon RX 470 /480 /570 /580 /590 Series - AMD Radeon (TM) (Pro WX) 5100 /E9390 /E9560 /E9565 /V7350 /7100 /P30PH, POLARIS10, DCE 11.2, 8, VCE 3.4 / UVD 6.3, 3, n/a, 7
+Radeon (TM) (RX|Pro WX) E9260 /460 /V5300X /550 /560(X) Series, POLARIS11, DCE 11.2, 8, VCE 3.4 / UVD 6.3, 3, n/a, 7
+Radeon (RX/Pro) 500 /540(X) /550 /640 /WX2100 /WX3100 /WX200 Series, POLARIS12, DCE 11.2, 8, VCE 3.4 / UVD 6.3, 3, n/a, 7
+Radeon (RX|TM) (PRO|WX) Vega /MI25 /V320 /V340L /8200 /9100 /SSG MxGPU, VEGA10, DCE 12, 9.0.1, VCE 4.0.0 / UVD 7.0.0, 4.0.0, 9.0.0, 9.0.0
+AMD Radeon (Pro) VII /MI50 /MI60, VEGA20, DCE 12, 9.4.0, VCE 4.1.0 / UVD 7.2.0, 4.2.0, 11.0.2, 11.0.2
+MI100, ARCTURUS, *, 9.4.1, VCN 2.5.0, 4.2.2, 11.0.4, 11.0.2
+MI200 Series, ALDEBARAN, *, 9.4.2, VCN 2.6.0, 4.4.0, 13.0.2, 13.0.2
+MI300 Series, AQUA_VANJARAM, *, 9.4.3, VCN 4.0.3, 4.4.2, 13.0.6, 13.0.6
+AMD Radeon (RX|Pro) 5600(M|XT) /5700 (M|XT|XTB) /W5700, NAVI10, DCN 2.0.0, 10.1.10, VCN 2.0.0, 5.0.0, 11.0.0, 11.0.0
+AMD Radeon (Pro) 5300 /5500XTB/5500(XT|M) /W5500M /W5500, NAVI14, DCN 2.0.0, 10.1.1, VCN 2.0.2, 5.0.2, 11.0.5, 11.0.5
+AMD Radeon RX 6800(XT) /6900(XT) /W6800, SIENNA_CICHLID, DCN 3.0.0, 10.3.0, VCN 3.0.0, 5.2.0, 11.0.7, 11.0.7
+AMD Radeon RX 6700 XT / 6800M / 6700M, NAVY_FLOUNDER, DCN 3.0.0, 10.3.2, VCN 3.0.0, 5.2.2, 11.0.11, 11.0.11
+AMD Radeon RX 6600(XT) /6600M /W6600 /W6600M, DIMGREY_CAVEFISH, DCN 3.0.2, 10.3.4, VCN 3.0.16, 5.2.4, 11.0.12, 11.0.12
+AMD Radeon RX 6500M /6300M /W6500M /W6300M, BEIGE_GOBY, DCN 3.0.3, 10.3.5, VCN 3.0.33, 5.2.5, 11.0.13, 11.0.13
+AMD Radeon RX 7900 XT /XTX, , DCN 3.2.0, 11.0.0, VCN 4.0.0, 6.0.0, 13.0.0, 13.0.0
+AMD Radeon RX 7800 XT, , DCN 3.2.0, 11.0.3, VCN 4.0.0, 6.0.3, 13.0.10, 13.0.10
+AMD Radeon RX 7600M (XT) /7700S /7600S, , DCN 3.2.1, 11.0.2, VCN 4.0.4, 6.0.2, 13.0.7, 13.0.7
+AMD Radeon RX 9070 (XT), , DCN 4.0.1, 12.0.1, VCN 5.0.0, 7.0.1, 14.0.3, 14.0.3
+AMD Radeon RX 9060 XT, , DCN 4.0.1, 12.0.0, VCN 5.0.0, 7.0.0, 14.0.2, 14.0.2
diff --git a/MAINTAINERS b/MAINTAINERS
index 494b12c03de7..4912b8a83bbb 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -6713,7 +6713,7 @@ S: Supported
F: drivers/input/keyboard/dlink-dir685-touchkeys.c
DALLAS/MAXIM DS1685-FAMILY REAL TIME CLOCK
-M: Joshua Kinard <kumba@gentoo.org>
+M: Joshua Kinard <linux@kumba.dev>
S: Maintained
F: drivers/rtc/rtc-ds1685.c
F: include/linux/rtc/ds1685.h
@@ -11439,6 +11439,7 @@ F: drivers/tty/hvc/
HUNG TASK DETECTOR
M: Andrew Morton <akpm@linux-foundation.org>
R: Lance Yang <lance.yang@linux.dev>
+R: Masami Hiramatsu <mhiramat@kernel.org>
L: linux-kernel@vger.kernel.org
S: Maintained
F: include/linux/hung_task.h
@@ -26312,7 +26313,6 @@ S: Maintained
F: include/linux/unwind*.h
F: kernel/unwind/
-
UTIL-LINUX PACKAGE
M: Karel Zak <kzak@redhat.com>
L: util-linux@vger.kernel.org
@@ -26736,12 +26736,6 @@ S: Maintained
F: drivers/iommu/virtio-iommu.c
F: include/uapi/linux/virtio_iommu.h
-VIRTIO MEDIA DRIVER
-M: Alexandre Courbot <gnurou@gmail.com>
-L: linux-media@vger.kernel.org
-S: Maintained
-F: drivers/media/virtio/
-
VIRTIO MEM DRIVER
M: David Hildenbrand <david@redhat.com>
L: virtualization@lists.linux.dev
diff --git a/Next/SHA1s b/Next/SHA1s
new file mode 100644
index 000000000000..ce3f9b5a5e6c
--- /dev/null
+++ b/Next/SHA1s
@@ -0,0 +1,407 @@
+Name SHA1
+---- ----
+origin 35a813e010b99894bb4706c56c16a580bf7959c2
+fixes 89be9a83ccf1f88522317ce02f854f30d6115c41
+ext4-fixes d0b3b7b22dfa1f4b515fd3a295b3fd958f9e81af
+vfs-brauner-fixes 8b3c655fa2406b9853138142746a39b7615c54a2
+fscrypt-current 0af2f6be1b4281385b618cb86ad946eded089ac8
+fsverity-current 0af2f6be1b4281385b618cb86ad946eded089ac8
+btrfs-fixes 61d18d91dd4aed6df52fac2bf0683eab6784ef85
+vfs-fixes 33927f3d0ecdcff06326d6e4edb6166aed42811c
+erofs-fixes 347e9f5043c89695b01e66b3ed111755afcf1911
+nfsd-fixes 94d10a4dba0bc482f2b01e39f06d5513d0f75742
+v9fs-fixes 2014c95afecee3e76ca4a56956a936e23283f05b
+overlayfs-fixes 924577e4f6ca473de1528953a0e13505fae61d7b
+bcachefs ae4d71be53dd5cb1495ebc52295c8942c2dfe238
+fscrypt fa65058063cbaba6e519b5291a7e2e9e0fa24ae3
+btrfs 442ee950ea05968ab5bfaeeb0c6660c567c61bfa
+ceph b828b4bf29d10a3e505a76a39c4daea969e19dc9
+cifs da3d9a37f3cbb44f387b810bda8ca0094e135a2d
+configfs c6b1908224593db76f77b904894cd51933559ae9
+ecryptfs fba133a3411847db49297c965218400c49571ebd
+dlm 6f8b4788266c7df3b7cfc6c665f663b4c3d09aad
+erofs df0ce6cefa453d2236381645e529a27ef2f0a573
+exfat b33f91c6276255ca0b90c42142828de05496ed1d
+exportfs adc218676eef25575469234709c2d87185ca223a
+ext3 17e58687367a5d9488106067112ef7dfb201d985
+ext4 261a2abe20b034c5383a1474133bad3110291ece
+f2fs 078cad8212ce4f4ebbafcc0936475b8215e1ca2a
+fsverity d0b3b7b22dfa1f4b515fd3a295b3fd958f9e81af
+fuse f0e84022479b4700609e874cf220b5d7d0363403
+gfs2 a90f1b6ad6649d553c9d76f50a42e4ba5783164b
+jfs 856db37592021e9155384094e331e2d4589f28b1
+ksmbd e5cf61fa6e2fb9ae6339eaa892612488c966baaf
+nfs 99765233ab42bf7a4950377ad7894dce8a5c0e60
+nfs-anna 38074de35b015df5623f524d6f2b49a0cd395c40
+nfsd e339967eecf1305557f7c697e1bc10b5cc495454
+ntfs3 a49f0abd8959048af18c6c690b065eb0d65b2d21
+orangefs 2138e89cb066b40386b1d9ddd61253347d356474
+overlayfs 6f9ccdad0feaef58b05f07e0fc9d31004147177c
+ubifs 99dbb2a1bd661418be33b1ff1462c09b7d2221cf
+v9fs 4210030d8bc4834fcb774babc458d02a2432ee76
+v9fs-ericvh 2014c95afecee3e76ca4a56956a936e23283f05b
+xfs ded74fddcaf685a9440c5612f7831d0c4c1473ca
+zonefs 6982100bb8297c46122cac4f684dcf44cb7d0d8c
+vfs-brauner 66639db858112bf6b0f76677f7517643d586e575
+vfs dd589648208a4deab9049805e94b680a15149e61
+mm-hotfixes 415d5ad3746153d0c45b2cd00bdbd801fcb1d4b2
+fs-current 7d46dcab452bfbdf4f16ba51db11ed31f8a5f60e
+kbuild-current e04c78d86a9699d136910cfc0bdcf01087e3267e
+arc-current d7b8f8e20813f0179d8ef519541a3527e7661d3a
+arm-current 0c66c6f4e21cb22220cbd8821c5c73fc157d20dc
+arm64-fixes d42e6c20de6192f8e4ab4cf10be8c694ef27e8cb
+arm-soc-fixes 9f9d41d643224e1cc7eac89794cf5e5997f8171f
+davinci-current 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+drivers-memory-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+sophgo-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+sophgo-soc-fixes 0af2f6be1b4281385b618cb86ad946eded089ac8
+m68k-current c8995932db2bad6fa093ac64dbaf7a3e8870eafa
+powerpc-fixes ab107276607af90b13a5994997e19b7b9731e251
+s390-fixes 62355f1f87b8c7f8785a8dd3cd5ca6e5b513566a
+net 1dbf1d590d10a6d1978e8184f8dfe20af22d680a
+bpf 1b30d44417278196a90c79244bb43e8428586345
+ipsec 28712d6ed32028b0f2e0defe6681411496971ca3
+netfilter eccf7a3480a06eb698f064af829733bd8d0ec263
+ipvs eccf7a3480a06eb698f064af829733bd8d0ec263
+wireless 6832a9317eee280117cd695fa885b2b7a7a38daf
+ath d9104cec3e8fe4b458b74709853231385779001f
+iwlwifi 6832a9317eee280117cd695fa885b2b7a7a38daf
+wpan 8ce4f287524c74a118b0af1eebd4b24a8efca57a
+rdma-fixes a9a9e68954f29b1e197663f76289db4879fd51bb
+sound-current dbe05428c4e54068a86e7e02405f3b30b1d2b3dd
+sound-asoc-fixes 282528da82a0436f3bed0755338539ba5d7d730b
+regmap-fixes 067aa458a064cd860baef7503c3264bb3482d37e
+regulator-fixes 10dfd36f078423c51602a9a21ed85e8e6c947a00
+spi-fixes a49bfbecfde75fa95677d4dfe95de8b25f8de37f
+pci-current 0bd0a41a5120f78685a132834865b0a631b9026a
+driver-core.current d632ab86aff2cef21f794e337a8e7f2320ac3973
+tty.current 55a984928bfa30c7877e28f16910e6de1c170f1f
+usb.current d632ab86aff2cef21f794e337a8e7f2320ac3973
+usb-serial-fixes ad1244e1ce18f8c1a5ebad8074bfcf10eacb0311
+phy 89be9a83ccf1f88522317ce02f854f30d6115c41
+staging.current d632ab86aff2cef21f794e337a8e7f2320ac3973
+iio-fixes 187d5553e33ea656c2a93d3e98309dfc166a0de5
+counter-current 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+char-misc.current d632ab86aff2cef21f794e337a8e7f2320ac3973
+soundwire-fixes 89be9a83ccf1f88522317ce02f854f30d6115c41
+thunderbolt-fixes 038d61fd642278bab63ee8ef722c50d10ab01e8f
+input-current bcce05041b21888f10b80ea903dcfe51a25c586e
+crypto-current 9d9b193ed73a65ec47cf1fd39925b09da8216461
+libcrypto-fixes 68279380266a5fa70e664de754503338e2ec3f43
+vfio-fixes c1d9dac0db168198b6f63f460665256dedad9b6e
+kselftest-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+dmaengine-fixes 89be9a83ccf1f88522317ce02f854f30d6115c41
+backlight-fixes 1613e604df0cd359cf2a7fbd9be7a0bcfacfabd0
+mtd-fixes 6463cbe08b0cbf9bba8763306764f5fd643023e1
+mfd-fixes d9d79e4f7dc935fea96dbf3de524404c08d08b03
+v4l-dvb-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+reset-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+mips-fixes 86731a2a651e58953fc949573895f2fa6d456841
+at91-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+omap-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+kvm-fixes 038d61fd642278bab63ee8ef722c50d10ab01e8f
+kvms390-fixes d8dfda5af0be6e48178b6f4b46c6af30b06335b2
+hwmon-fixes 9c62e2282900332c8b711d9f9e37af369a8ef71b
+nvdimm-fixes d0b3b7b22dfa1f4b515fd3a295b3fd958f9e81af
+cxl-fixes d0b3b7b22dfa1f4b515fd3a295b3fd958f9e81af
+dma-mapping-fixes aa807b9f22df2eee28593cbbabba0f93f4aa26c1
+drivers-x86-fixes e2967b50b709970547b5cdfa1b42526835327f36
+samsung-krzk-fixes 8d2c2fa2209e83d0eb10f7330d8a0bbdc1df32ff
+pinctrl-samsung-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+devicetree-fixes 79aef1a3705bbc95b36dad892af1f313490bd65c
+dt-krzk-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+scsi-fixes 021f243627ead17eb6500170256d3d9be787dad8
+drm-fixes 038d61fd642278bab63ee8ef722c50d10ab01e8f
+drm-intel-fixes 038d61fd642278bab63ee8ef722c50d10ab01e8f
+mmc-fixes 4b290aae788e06561754b28c6842e4080957d3f7
+rtc-fixes 08d82d0cad51c2b1d454fe41ea1ff96ade676961
+gnss-fixes 86731a2a651e58953fc949573895f2fa6d456841
+hyperv-fixes a4131a50d072b369bfed0b41e741c41fd8048641
+risc-v-fixes b65ca21835ed615907ba231a60db80a2605b94dc
+riscv-dt-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+riscv-soc-fixes 0af2f6be1b4281385b618cb86ad946eded089ac8
+fpga-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+spdx beb6c8326eb4e7006c4aa16b0fee3e303d42e685
+gpio-brgl-fixes 89be9a83ccf1f88522317ce02f854f30d6115c41
+gpio-intel-fixes 9ab29ed505557bd106e292184fa4917955eb8e6e
+pinctrl-intel-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+auxdisplay-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+kunit-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+memblock-fixes da8bf5daa5e55a6af2b285ecda460d6454712ff4
+renesas-fixes 379c590113ce46f605439d4887996c60ab8820cc
+perf-current 6235ce77749f45cac27f630337e2fdf04e8a6c73
+efi-fixes 64e135f1eaba0bbb0cdee859af3328c68d5b9789
+battery-fixes 0af2f6be1b4281385b618cb86ad946eded089ac8
+iommufd-fixes 9a96876e3c6578031fa5dc5dde7759d383b2fb75
+rust-fixes d2eedaa3909be9102d648a4a0a50ccf64f96c54f
+w1-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+pmdomain-fixes 621a88dbfe9006c318a0cafbd12e677ccfe006e7
+i2c-host-fixes 0ae982df67760cd08affa935c0fe86c8a9311797
+sparc-fixes 6613476e225e090cc9aad49be7fa504e290dd33d
+clk-fixes e4b2a0c2b9be6d10b0e50a7485fe9f569a6f2436
+thead-clk-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+pwrseq-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+thead-dt-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+ftrace-fixes 327e28664307d49ce3fa71ba30dcc0007c270974
+ring-buffer-fixes e4d4b8670c44cdd22212cab3c576e2d317efa67c
+trace-fixes b5e8acc14dcb314a9b61ff19dcd9fdd0d88f70df
+tracefs-fixes 8b55572e51805184353ee7d587c720a51818fb82
+spacemit-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+tip-fixes f88a000d5409e74dec51e2b1793a0e708d1920b4
+slab-fixes be8250786ca94952a19ce87f98ad9906448bc9ef
+drm-msm-fixes 8290d37ad2b087bbcfe65fa5bcaf260e184b250a
+uml-fixes 2dca89df0d1116f722b4be100e4bfcff858058e8
+fwctl-fixes 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+devsec-tsm-fixes fba4ceaa242d2bdf4c04b77bda41d32d02d3925d
+drm-misc-fixes 038d61fd642278bab63ee8ef722c50d10ab01e8f
+linus ffd294d346d185b70e28b1a28abe367bbfe53c04
+mm-stable a2152fef29020e740ba0276930f3a24440012505
+mm-nonmm-stable 085dece6cc88b5c6fc6f2eca0403bfd2c5fbc7cb
+mm-unstable 66b994de3cf1c4520fd249e861bc83b1f902d20b
+mm-nonmm-unstable 021cf32328d6583f3a75fb4f136e7a6f8efe8192
+kbuild dae742fa564b7f53de83c16dce033d547c84c0f3
+clang-format c147f663b6a5813b9860f3917cc473fb2c462d8d
+perf 6235ce77749f45cac27f630337e2fdf04e8a6c73
+compiler-attributes 98f7e32f20d28ec452afb208f9cffc08448a2652
+dma-mapping fbf5e2234169067a811ab38dc89cc0d260499622
+asm-generic 582847f9702461b0a1cba3efdb2b8135bf940d53
+alpha 1523226edda566057bdd3264ceb56631ddf5f6f7
+arm 8dd85887ad83438750fa09237da9342ce966dd0f
+arm64 5b1ae9de71335865d06ff0e60eadcf368a735edf
+arm-perf e480898e767c54a883e965fc306e2ece013cbca5
+arm-soc 9f9d41d643224e1cc7eac89794cf5e5997f8171f
+amlogic 58abdca0eb653c1a2e755ba9ba406ee475d87636
+asahi-soc 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+at91 e99113d11171a03c865ca5b10e0ae9b587034ae2
+bmc acba3fae64fd9c9862e1452c1a4f788055fab0e9
+broadcom 89abb622d518a917e16b6cd441dc75f547300303
+davinci 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+drivers-memory 93a7aedc4cc4476da54ea45f3ed5308aabafef75
+fsl 8b3da0519ae664dd7e3d840c3a6851ec5a7f42de
+imx-mxs cdc22fb12efffa2357cea791a7c4a1a4407a66a7
+mediatek 6cbb623586d5cd1abf2b1b8500294546b8543058
+mvebu 88084e0358ff6f5c39accddf3f0da4162e6d0ccf
+omap db91121f001a3a1fad41ff816bdbddb7da443297
+qcom ba94ec807b071becbed7377f8c84308f1b6ccd51
+renesas 7a323accaf6bf40f0d345694978e3657363c3772
+reset 335bb23abed39d9ec174ea520bc2337e2fe605ef
+rockchip 1f0c7abd82357d425e34645fa086280f552ae822
+samsung-krzk 94f19ac4670d5867609484329ee62f6bf254c090
+scmi d2eedaa3909be9102d648a4a0a50ccf64f96c54f
+sophgo 349ae53a949ce96d0e1453170d31d26ed54ba68e
+sophgo-soc c8754c7deab4cbfa947fa2d656cbaf83771828ef
+spacemit 6be7a5a768aafcb07d177bd2ae36ab84e4e0acde
+stm32 1a32f7427eb3d1248bc64cd745b93f88cc838933
+sunxi cbe908fc8ebbea52f2d674773c2ddaf8cbfa4757
+tee 84c5f44d24c6a26d38642d996507f08ac92eb3ed
+tegra 499b75defe5654ba29e838bd2f5e79d3a16229af
+thead-dt c31f2899eab084b3557e9f9e10fc7898113ef18d
+ti 65f6e3eb6351ff402a03f2b6b56ab1fd61511334
+xilinx 3a0e3f82b8ee4386bfbc2cdcdf4243a3e8de4bad
+clk 64c21f253a3737c15ab745e9276b2352d86aed26
+clk-imx c78865241ecffaff7ce5db00ed5b71c1a70c0ff1
+clk-renesas 0ab2d84f94dae48c3e7605cdc99dbb4e7c7b206a
+thead-clk 54edba916e2913b0893b0f6404b73155d48374ea
+csky 2b48804336be69272d43939ff0dc3b0c0a703395
+loongarch bcfdf97c1abcb0147e4ed00350a25ad3393c2c33
+m68k c8995932db2bad6fa093ac64dbaf7a3e8870eafa
+m68knommu 89be9a83ccf1f88522317ce02f854f30d6115c41
+microblaze c0e7bb02f7962cd4b2327196aa1b0f9568c783e4
+mips 3ebcbf079c26ab6e82faa7f896b66def55547eee
+openrisc f0eedcf22581ca1cc438fb38a479ff41ab882d51
+parisc-hd 89f686a0fb6e473a876a9a60a13aec67a62b9a7e
+powerpc cf2a6de32cabbf84a889e24a9ee7c51dee4a1f70
+risc-v fda589c286040d9ba2d72a0eaf0a13945fc48026
+riscv-dt 28fa0dcb571ab8f3be4d919f0e20e01d4e44bcb1
+riscv-soc bd4d5d3faadcdf5d65377f14dcbaa4dbb27ee637
+s390 d3a0de1a9dbc77623ffeb4d478204c4df0470236
+sh c32969d0362a790fbc6117e0b6a737a7e510b843
+sparc 2cec2c4dc90cbf5194c1acef08c1e74f0437af95
+uml fc9ed2f6589dc2c11f05883e5c323be5f39fd241
+xtensa 44a4ef59d5506c6dc7599d876a3a1014697ec480
+fs-next 0264e7f5188b34d7ffce79c364667e69a663013f
+printk dcc3191a3dde4027ac3a995d852b957e398cf6cc
+pci 0bd0a41a5120f78685a132834865b0a631b9026a
+pstore d679c2e1e8d96f71f85e2ef3877407d264212cc3
+hid 1330eb33bddca5f8dd163bbe3a8f8e828697c0fd
+i2c 976990f4120c220816b46650d840019451698a28
+i2c-host 85c34532849dae0fdcf880900ac9d7718a73fd1b
+i3c 3b661ca549b9e5bb11d0bc97ada6110aac3282d2
+dmi 4d1b28a8119c615f1e932520f9ee1f80bdda5204
+hwmon-staging de1fffd88600c5ee1c095c84b86484cd0329a9e8
+jc_docs 35293ebbb65e0295d3b9357f786004ae1026d00f
+v4l-dvb d968e50b5c26642754492dea23cbd3592bde62d8
+v4l-dvb-next b36c41c51e9d763393634359b90f02414ef470a3
+pm 77d832285656c59238e7992f12296e18657251ee
+cpufreq-arm bbd67be5546d6080a7dc9903355a54ac4b865caa
+cpupower e6c3f96141ebab688d96cf582bcab67f930e0baa
+devfreq 7da2fdaaa1e6062686ac96a9f096c2d7847533e4
+pmdomain 05e35bd07d56780f0a5119973995b97a16843579
+opp 22679d807dea5c065d8019acfce48f20e87ba5ca
+thermal 1d264d3a198839c7483580acdce17e1015d0ef91
+rdma ee235923d205c6de73bf5035f3cdcaee22f3291c
+net-next d9104cec3e8fe4b458b74709853231385779001f
+bpf-next 821c9e515db512904250e1d460109a1dc4c7ef6b
+ipsec-next 95cfe23285a6de17f11715378c93e6aee6d0ca75
+mlx5-next 888a7776f4fb04c19bec70c737c61c2f383c6b1e
+netfilter-next e3f96b3556e4856dc4125ce875e87c5b5028b40b
+ipvs-next e3f96b3556e4856dc4125ce875e87c5b5028b40b
+bluetooth df18778595f9423542f38784749feca5471f9de7
+wireless-next 126d85fb040559ba6654f51c0b587d280b041abb
+ath-next 708243c62efde8241e2c66e9c3f377658855149d
+iwlwifi-next d2af710d6d50b3a3e691c4e2b262ed9de3038e96
+wpan-next 1dd9291eb90378f8096669d9cb33761fd84599e0
+wpan-staging 1dd9291eb90378f8096669d9cb33761fd84599e0
+mtd 9cf9db888f387844e063efc6296e9fa5c042995e
+nand fb2fae70e7e985c4acb1ad96110d8b98bb64a87c
+spi-nor 2e3a7476ec3989e77270b9481e76e137824b17c0
+crypto 9d9b193ed73a65ec47cf1fd39925b09da8216461
+libcrypto 2a1a127aecf628a7629c860e2ad645174b5d3211
+drm 6531a2cf07ef156956840853692755cc7e1621b7
+drm-exynos 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+drm-misc 584460393efbcccb6388b1cd5d37284b5326709c
+amdgpu 1c2efae2f855e348d772c071c8c30217d8a0dbae
+drm-intel 5a569ef4d4ab184a481dd8ecb58f464a89b44d2f
+drm-msm 8290d37ad2b087bbcfe65fa5bcaf260e184b250a
+drm-msm-lumag cd86e80b77b2f3d9e72c2d27a967b666d2c47a44
+drm-nova 14ae91a81ec8fa0bc23170d4aa16dd2a20d54105
+drm-xe bcddb12c027434fdf0491c1a05a3fe4fd2263d71
+etnaviv 6bde14ba5f7ef59e103ac317df6cc5ac4291ff4a
+fbdev e4fc307d8e24f122402907ebf585248cad52841d
+regmap 067aa458a064cd860baef7503c3264bb3482d37e
+sound dbe05428c4e54068a86e7e02405f3b30b1d2b3dd
+ieee1394 95a042a0c8ecd3c1e886648f6f6ab9c7e4403db9
+sound-asoc 282528da82a0436f3bed0755338539ba5d7d730b
+modules 40a826bd6c82ae45cfd3a19cd2a60a10f56b74c0
+input a7bee4e7f78089c101be2ad51f4b5ec64782053e
+block 20c74c07321713217b2f84c55dfd717729aa6111
+device-mapper 55a0fbd2ac3fe8f61a30ea697b2eb3034f6778c8
+libata 6cb43739b93c64c4a2148222bd606e6920257752
+pcmcia 0630e3bc0e91b57288921df2927859b23184ca45
+mmc 4b290aae788e06561754b28c6842e4080957d3f7
+mfd b6bf74c821780259495b1f86e319854ef5bee0db
+backlight 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+battery 7b41a2341fa62babda5d5c7a32c632e9eba2ee11
+regulator 10dfd36f078423c51602a9a21ed85e8e6c947a00
+security 5d8b97c946777118930e1cfb075cab59a139ca7c
+apparmor 5f49c2d1f422c660c726ac5e0499c66c901633c2
+integrity aa9bb1b32594cd67cafd29b330b158128b503882
+selinux 850dada4b3afd014e2c69226bf9bb85469338000
+smack 6ddd169d0288ebee8ec9afcd75825ce8476edb00
+tomoyo 038d61fd642278bab63ee8ef722c50d10ab01e8f
+tpmdd 7f0c6675b3194461ad7bb8db1d822445121fb029
+watchdog 48defdf6b083f74a44e1f742db284960d3444aec
+iommu b9e6e8ae0a5f9edae7cc1b5972a1d3dea9223fe2
+audit ae1ae11fb277f1335d6bcd4935ba0ea985af3c32
+devicetree 0121898ec05fa4c1f566fc05c7e8b3caf0998f97
+dt-krzk 6cd594ed969d5cfc7f97029f8ca0d240637ebb8d
+mailbox 872798f61d8bfea857e54aa17baa7b0d3ee24b65
+spi a49bfbecfde75fa95677d4dfe95de8b25f8de37f
+tip 40d6e791ba3ac9f66eba33833710a2e2f1aa8a66
+clockevents d7b8f8e20813f0179d8ef519541a3527e7661d3a
+edac 1fb0ddddf5d139089675b86702933cbca992b4d4
+ftrace 39f069d5a466cb9a572ee10c5391e822cdccaf05
+rcu cc1d1365f0f414f6522378867baa997642a7e6b2
+paulmck b706eec9304fc3cbc48a6a09aff8533081815ebc
+kvm 196d9e72c4b0bd68b74a4ec7f52d248f37d0f030
+kvm-arm 7b8346bd9fce6b76a96c6780d2e5bba76687f97f
+kvms390 57d88f02eb4449d96dfee3af4b7cd4287998bdbd
+kvm-ppc fac04efc5c793dccbd07e2d59af9f90b7fc0dca4
+kvm-riscv 07a289a031404ec583c01d8e87680d434fc62c1f
+kvm-x86 33f843444e28920d6e624c6c24637b4bb5d3c8de
+xen-tip 114a2de6fa86d99ed9546cc9113a3cad58beef79
+percpu 87d6aab2389e5ce0197d8257d5f8ee965a67c4cd
+workqueues 324cee0c272cb3fa6c4d3c0de4b68a9c5357d2e7
+sched-ext 9f0744a0e87e4e74725d495bba2aa540dec4a77a
+drivers-x86 1798561befd8be1e52feb54f850efcab5a595f43
+chrome-platform cc2d5b72b13b3af2b9b4bed3d5dfd0de14414230
+chrome-platform-firmware 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+hsi 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+leds-lj 4903924ac7ef31fbbe48b3261b1bc86ce6cd7e97
+ipmi ec50ec378e3fd83bde9b3d622ceac3509a60b6b5
+driver-core d632ab86aff2cef21f794e337a8e7f2320ac3973
+usb d632ab86aff2cef21f794e337a8e7f2320ac3973
+thunderbolt 2d1beba54fdaac0d624b016025d4ec5856713fb1
+usb-serial bdf2ab177e2fca85394fce86629f5e35aa7fa33a
+tty 89748acdf226fd1a8775ff6fa2703f8412b286c8
+char-misc d632ab86aff2cef21f794e337a8e7f2320ac3973
+accel f03eee5fc922158654405318a02db9982c0ddf07
+coresight a80198ba650f50d266d7fc4a6c5262df9970f9f2
+fastrpc 0af2f6be1b4281385b618cb86ad946eded089ac8
+fpga 37e00703228ab44d0aacc32a97809a4f6f58df1b
+icc ca652cf0c2612add5d3c9283bbc742dabc704a77
+iio 0a686b9c4f847dc21346df8e56d5b119918fefef
+phy-next 4a3556b81b99f0c8c0358f7cc6801a62b4538fe2
+soundwire 34b1cb4ec286603127aa8c4191ea527eb8dd3567
+extcon 5f09caafc652bcee7a5247e40dd34d1de1ad7d7f
+gnss e326371f3002dbf54befd8ada9570fa489a46991
+vfio d2272d898186fa96c6fa4ad067219b45b8c2ef5f
+w1 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+spmi 0ff41df1cb268fc69e703a08a57ee14ae967d0ca
+staging d632ab86aff2cef21f794e337a8e7f2320ac3973
+counter-next 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+siox db418d5f1ca5b7bafc8eaa9393ea18a7901bb0ed
+mux 59b723cd2adbac2a34fc8e12c74ae26ae45bf230
+dmaengine e3a9ccd21897a59d02cf2b7a95297086249306d6
+cgroup d445d2ab8129b1da93f25a9a71e36f43223d5543
+scsi b3a40acce7b3d0a7e9d0b2042a33129a7e3d6e41
+scsi-mkp 383cd6d879a18acdaa84c29330b25c49cbc0b490
+vhost 06a1fa9a0b79be71b7426ed792cf189b2b0ffac6
+rpmsg 01d7d9241256597eb38ec8a119ff89062b9fa10a
+gpio-brgl 63c7bc53a35e785accdc2ceab8f72d94501931ab
+gpio-intel 9ab29ed505557bd106e292184fa4917955eb8e6e
+pinctrl a3fe1324c3c5c292ec79bd756497c1c44ff247d2
+pinctrl-intel 3b4408038da935be7b1efb7589cc1badb6d10a67
+pinctrl-renesas 7000167796a00d64322dc3ed0c0970e31d481ed6
+pinctrl-samsung 683d532dfc9657ab8aae25204f378352ed144646
+pwm 65c6f742ab14ab1a2679fba72b82dcc0289d96f1
+ktest a5e71638ddd7f1dc0b9f3a5ac8ab8bef48b9f0ee
+kselftest 30fb5e134f05800dc424f8aa1d69841a6bdd9a54
+kunit 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+kunit-next 34db4fba81916a2001d7a503dfcf718c08ed5c42
+livepatching a8e905a819fdfb4ce674363896320e36657d0f16
+rtc bb5b0b4317c9516bdc5e9a4235e3b5f1a73b7e48
+nvdimm 9f97e61bde6a91a429f48da1a461488a15b01813
+at24 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+ntb 0cadf92e93d4caed1714faac53e9a0051810f4b0
+seccomp b0c9bfbab925ac6385d4d06a134fd89cadf771fe
+slimbus 0af2f6be1b4281385b618cb86ad946eded089ac8
+nvmem 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+xarray 6684aba0780da9f505c202f27e68ee6d18c0aa66
+hyperv d9016a249be5316ec2476f9947356711e70a16ec
+auxdisplay 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+kgdb afdbe49276accb87a0c7414e75864c78289ece2f
+hmm 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+cfi 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+mhi 00559ba3ae740e7544b48fb509b2b97f56615892
+memblock 3b394dff15e14550a26b133fc7b556b5b526f6a5
+cxl f11a5f89910a7ae970fbce4fdc02d86a8ba8570f
+zstd 65d1f5507ed2c78c64fce40e44e5574a9419eb09
+efi 02eb7a8eee20b9ec6aafd5e17c5c41b53e8b13ef
+unicode 6b56a63d286f6f57066c4b5648d8fbec9510beae
+slab 8185696483dcb29688fc23c45c99d86b73754982
+random 3778dcb2dcc1ce03a2b25e5d951fe9912e843d1e
+landlock 6dde339a3df80a57ac3d780d8cfc14d9262e2acd
+rust d2eedaa3909be9102d648a4a0a50ccf64f96c54f
+rust-alloc d49ac7744f578bcc8708a845cce24d3b91f86260
+rust-io 86731a2a651e58953fc949573895f2fa6d456841
+rust-pin-init fc3870dc5cadb701b4122e4a8daa85f9fa2f57b9
+rust-timekeeping d4b29ddf82a458935f1bd4909b8a7a13df9d3bdc
+rust-xarray fa616196fbea12462107774fb6a1908c95f71cf0
+sysctl 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+execve 7f71195c15dcf5f34c4c7f056603659374e3a525
+bitmap 89748acdf226fd1a8775ff6fa2703f8412b286c8
+hte 9e4259716f60c96c069a38e826884ad783dc4eb4
+kspp f627b51aaa041cba715b59026cf2d9cb1476c7ed
+nolibc b9e50363178a40c76bebaf2f00faa2b0b6baf8d1
+iommufd 2c78e74493d33b002312296fbab1d688bfd0f76f
+turbostat 447c98c1ca4a4b0d43be99f76c558c09956484f3
+pwrseq 07d59dec6795428983a840de85aa02febaf7e01b
+capabilities-next cdd73b1666079a73d061396f361df55d59fe96e6
+ipe 038d61fd642278bab63ee8ef722c50d10ab01e8f
+kcsan 9872916ad1a1a5e7d089e05166c85dbd65e5b0e8
+crc 118da22eb6fbd48f896d17411f942399283d600c
+fwctl 19272b37aa4f83ca52bdf9c16d5d81bdd1354494
+devsec-tsm 9d948b8804096d940022b1a3c483a5beb8b46574
+hisilicon b1136432c97241f0e5c40d58597da00d49cd9917
+kthread d8b4bf4ea04dd96fe43f6010c614149aba4c9b91
diff --git a/Next/Trees b/Next/Trees
new file mode 100644
index 000000000000..2477ec47fb71
--- /dev/null
+++ b/Next/Trees
@@ -0,0 +1,409 @@
+Trees included into this release:
+
+Name Type Url
+---- ---- ---
+origin git git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git#master
+fixes git git://git.kernel.org/pub/scm/linux/kernel/git/sfr/next-fixes.git#fixes
+ext4-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/tytso/ext4.git#fixes
+vfs-brauner-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/vfs/vfs.git#vfs.fixes
+fscrypt-current git git://git.kernel.org/pub/scm/fs/fscrypt/linux.git#for-current
+fsverity-current git git://git.kernel.org/pub/scm/fs/fsverity/linux.git#for-current
+btrfs-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/kdave/linux.git#next-fixes
+vfs-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs.git#fixes
+erofs-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/xiang/erofs.git#fixes
+nfsd-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/cel/linux#nfsd-fixes
+v9fs-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/ericvh/v9fs.git#fixes/next
+overlayfs-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/overlayfs/vfs.git#ovl-fixes
+bcachefs git git://evilpiepirate.org/bcachefs.git#for-next
+fscrypt git git://git.kernel.org/pub/scm/fs/fscrypt/linux.git#for-next
+btrfs git git://git.kernel.org/pub/scm/linux/kernel/git/kdave/linux.git#for-next
+ceph git git://github.com/ceph/ceph-client.git#master
+cifs git git://git.samba.org/sfrench/cifs-2.6.git#for-next
+configfs git git://git.kernel.org/pub/scm/linux/kernel/git/a.hindborg/linux.git#configfs-next
+ecryptfs git git://git.kernel.org/pub/scm/linux/kernel/git/tyhicks/ecryptfs.git#next
+dlm git git://git.kernel.org/pub/scm/linux/kernel/git/teigland/linux-dlm.git#next
+erofs git git://git.kernel.org/pub/scm/linux/kernel/git/xiang/erofs.git#dev
+exfat git git://git.kernel.org/pub/scm/linux/kernel/git/linkinjeon/exfat.git#dev
+exportfs git git://git.kernel.org/pub/scm/linux/kernel/git/cel/linux#exportfs-next
+ext3 git git://git.kernel.org/pub/scm/linux/kernel/git/jack/linux-fs.git#for_next
+ext4 git git://git.kernel.org/pub/scm/linux/kernel/git/tytso/ext4.git#dev
+f2fs git git://git.kernel.org/pub/scm/linux/kernel/git/jaegeuk/f2fs.git#dev
+fsverity git git://git.kernel.org/pub/scm/fs/fsverity/linux.git#for-next
+fuse git git://git.kernel.org/pub/scm/linux/kernel/git/mszeredi/fuse.git#for-next
+gfs2 git git://git.kernel.org/pub/scm/linux/kernel/git/gfs2/linux-gfs2.git#for-next
+jfs git git://github.com/kleikamp/linux-shaggy.git#jfs-next
+ksmbd git https://github.com/smfrench/smb3-kernel.git#ksmbd-for-next
+nfs git git://git.linux-nfs.org/projects/trondmy/nfs-2.6.git#linux-next
+nfs-anna git git://git.linux-nfs.org/projects/anna/linux-nfs.git#linux-next
+nfsd git git://git.kernel.org/pub/scm/linux/kernel/git/cel/linux#nfsd-next
+ntfs3 git https://github.com/Paragon-Software-Group/linux-ntfs3.git#master
+orangefs git git://git.kernel.org/pub/scm/linux/kernel/git/hubcap/linux#for-next
+overlayfs git git://git.kernel.org/pub/scm/linux/kernel/git/overlayfs/vfs.git#overlayfs-next
+ubifs git git://git.kernel.org/pub/scm/linux/kernel/git/rw/ubifs.git#next
+v9fs git git://github.com/martinetd/linux#9p-next
+v9fs-ericvh git git://git.kernel.org/pub/scm/linux/kernel/git/ericvh/v9fs.git#ericvh/for-next
+xfs git git://git.kernel.org/pub/scm/fs/xfs/xfs-linux.git#for-next
+zonefs git git://git.kernel.org/pub/scm/linux/kernel/git/dlemoal/zonefs.git#for-next
+vfs-brauner git git://git.kernel.org/pub/scm/linux/kernel/git/vfs/vfs.git#vfs.all
+vfs git git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs.git#for-next
+mm-hotfixes git git://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm#mm-hotfixes-unstable
+fs-current git linux-next
+kbuild-current git git://git.kernel.org/pub/scm/linux/kernel/git/masahiroy/linux-kbuild.git#fixes
+arc-current git git://git.kernel.org/pub/scm/linux/kernel/git/vgupta/arc.git#for-curr
+arm-current git git://git.kernel.org/pub/scm/linux/kernel/git/rmk/linux.git#fixes
+arm64-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/arm64/linux#for-next/fixes
+arm-soc-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/soc/soc.git#arm/fixes
+davinci-current git git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git#davinci/for-current
+drivers-memory-fixes git https://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux-mem-ctrl.git#fixes
+sophgo-fixes git https://github.com/sophgo/linux.git#fixes
+sophgo-soc-fixes git https://github.com/sophgo/linux.git#soc-fixes
+m68k-current git git://git.kernel.org/pub/scm/linux/kernel/git/geert/linux-m68k.git#for-linus
+powerpc-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/powerpc/linux.git#fixes
+s390-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/s390/linux.git#fixes
+net git git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net.git#main
+bpf git git://git.kernel.org/pub/scm/linux/kernel/git/bpf/bpf.git#master
+ipsec git git://git.kernel.org/pub/scm/linux/kernel/git/klassert/ipsec.git#master
+netfilter git git://git.kernel.org/pub/scm/linux/kernel/git/netfilter/nf.git#main
+ipvs git git://git.kernel.org/pub/scm/linux/kernel/git/horms/ipvs.git#main
+wireless git git://git.kernel.org/pub/scm/linux/kernel/git/wireless/wireless.git#for-next
+ath git git://git.kernel.org/pub/scm/linux/kernel/git/ath/ath.git#for-current
+iwlwifi git https://git.kernel.org/pub/scm/linux/kernel/git/iwlwifi/iwlwifi-next.git#fixes
+wpan git git://git.kernel.org/pub/scm/linux/kernel/git/wpan/wpan.git#master
+rdma-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/rdma/rdma.git#for-rc
+sound-current git git://git.kernel.org/pub/scm/linux/kernel/git/tiwai/sound.git#for-linus
+sound-asoc-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/broonie/sound.git#for-linus
+regmap-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/broonie/regmap.git#for-linus
+regulator-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/broonie/regulator.git#for-linus
+spi-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/broonie/spi.git#for-linus
+pci-current git git://git.kernel.org/pub/scm/linux/kernel/git/pci/pci.git#for-linus
+driver-core.current git git://git.kernel.org/pub/scm/linux/kernel/git/driver-core/driver-core.git#driver-core-linus
+tty.current git git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/tty.git#tty-linus
+usb.current git git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/usb.git#usb-linus
+usb-serial-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/johan/usb-serial.git#usb-linus
+phy git git://git.kernel.org/pub/scm/linux/kernel/git/phy/linux-phy.git#fixes
+staging.current git git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/staging.git#staging-linus
+iio-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/jic23/iio.git#fixes-togreg
+counter-current git git://git.kernel.org/pub/scm/linux/kernel/git/wbg/counter.git#counter-current
+char-misc.current git git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/char-misc.git#char-misc-linus
+soundwire-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/vkoul/soundwire.git#fixes
+thunderbolt-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/westeri/thunderbolt.git#fixes
+input-current git git://git.kernel.org/pub/scm/linux/kernel/git/dtor/input.git#for-linus
+crypto-current git git://git.kernel.org/pub/scm/linux/kernel/git/herbert/crypto-2.6.git#master
+libcrypto-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/ebiggers/linux.git#libcrypto-fixes
+vfio-fixes git git://github.com/awilliam/linux-vfio.git#for-linus
+kselftest-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux-kselftest.git#fixes
+dmaengine-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/vkoul/dmaengine.git#fixes
+backlight-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/lee/backlight.git#for-backlight-fixes
+mtd-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/mtd/linux.git#mtd/fixes
+mfd-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/lee/mfd.git#for-mfd-fixes
+v4l-dvb-fixes git git://linuxtv.org/media-ci/media-pending.git#fixes
+reset-fixes git https://git.pengutronix.de/git/pza/linux#reset/fixes
+mips-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/mips/linux.git#mips-fixes
+at91-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/at91/linux.git#at91-fixes
+omap-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/khilman/linux-omap.git#fixes
+kvm-fixes git git://git.kernel.org/pub/scm/virt/kvm/kvm.git#master
+kvms390-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/kvms390/linux.git#master
+hwmon-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/groeck/linux-staging.git#hwmon
+nvdimm-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/nvdimm/nvdimm.git#libnvdimm-fixes
+cxl-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/cxl/cxl.git#fixes
+dma-mapping-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/mszyprowski/linux.git#dma-mapping-fixes
+drivers-x86-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/pdx86/platform-drivers-x86.git#fixes
+samsung-krzk-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux.git#fixes
+pinctrl-samsung-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/pinctrl/samsung.git#fixes
+devicetree-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/robh/linux.git#dt/linus
+dt-krzk-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux-dt.git#fixes
+scsi-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/mkp/scsi.git#fixes
+drm-fixes git https://gitlab.freedesktop.org/drm/kernel.git#drm-fixes
+drm-intel-fixes git https://gitlab.freedesktop.org/drm/i915/kernel#for-linux-next-fixes
+mmc-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/ulfh/mmc.git#fixes
+rtc-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/abelloni/linux.git#rtc-fixes
+gnss-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/johan/gnss.git#gnss-linus
+hyperv-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/hyperv/linux.git#hyperv-fixes
+risc-v-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/riscv/linux.git#fixes
+riscv-dt-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/conor/linux.git#riscv-dt-fixes
+riscv-soc-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/conor/linux.git#riscv-soc-fixes
+fpga-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/fpga/linux-fpga.git#fixes
+spdx git git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/spdx.git#spdx-linus
+gpio-brgl-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git#gpio/for-current
+gpio-intel-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/andy/linux-gpio-intel.git#fixes
+pinctrl-intel-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/pinctrl/intel.git#fixes
+auxdisplay-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/andy/linux-auxdisplay.git#fixes
+kunit-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux-kselftest.git#kunit-fixes
+memblock-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/rppt/memblock.git#fixes
+renesas-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/geert/renesas-devel.git#fixes
+perf-current git git://git.kernel.org/pub/scm/linux/kernel/git/perf/perf-tools#perf-tools
+efi-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/efi/efi.git#urgent
+battery-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/sre/linux-power-supply.git#fixes
+iommufd-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/jgg/iommufd.git#for-rc
+rust-fixes git https://github.com/Rust-for-Linux/linux.git#rust-fixes
+w1-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux-w1.git#fixes
+pmdomain-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/ulfh/linux-pm.git#fixes
+i2c-host-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/andi.shyti/linux.git#i2c/i2c-host-fixes
+sparc-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/alarsson/linux-sparc.git#for-linus
+clk-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/clk/linux.git#clk-fixes
+thead-clk-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/fustini/linux.git#thead-clk-fixes
+pwrseq-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git#pwrseq/for-current
+thead-dt-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/fustini/linux.git#thead-dt-fixes
+ftrace-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git#ftrace/fixes
+ring-buffer-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git#ring-buffer/fixes
+trace-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git#trace/fixes
+tracefs-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git#tracefs/fixes
+spacemit-fixes git https://github.com/spacemit-com/linux#fixes
+tip-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip.git#tip/urgent
+slab-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/vbabka/slab.git#slab/for-next-fixes
+drm-msm-fixes git https://gitlab.freedesktop.org/drm/msm.git#msm-fixes
+uml-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/uml/linux.git#fixes
+fwctl-fixes git git//git.kernel.org/pub/scm/linux/kernel/git/fwctl/fwctl.git#for-rc
+devsec-tsm-fixes git git://git.kernel.org/pub/scm/linux/kernel/git/devsec/tsm.git#fixes
+drm-misc-fixes git https://gitlab.freedesktop.org/drm/misc/kernel.git#for-linux-next-fixes
+linus git git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git#for-next
+mm-stable git git://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm#mm-stable
+mm-nonmm-stable git git://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm#mm-nonmm-stable
+mm-unstable git git://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm#mm-unstable
+mm-nonmm-unstable git git://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm#mm-nonmm-unstable
+kbuild git git://git.kernel.org/pub/scm/linux/kernel/git/masahiroy/linux-kbuild.git#for-next
+clang-format git https://github.com/ojeda/linux.git#clang-format
+perf git git://git.kernel.org/pub/scm/linux/kernel/git/perf/perf-tools-next.git#perf-tools-next
+compiler-attributes git https://github.com/ojeda/linux.git#compiler-attributes
+dma-mapping git git://git.kernel.org/pub/scm/linux/kernel/git/mszyprowski/linux.git#dma-mapping-for-next
+asm-generic git git://git.kernel.org/pub/scm/linux/kernel/git/arnd/asm-generic.git#master
+alpha git git://git.kernel.org/pub/scm/linux/kernel/git/mattst88/alpha.git#alpha-next
+arm git git://git.kernel.org/pub/scm/linux/kernel/git/rmk/linux.git#for-next
+arm64 git git://git.kernel.org/pub/scm/linux/kernel/git/arm64/linux#for-next/core
+arm-perf git git://git.kernel.org/pub/scm/linux/kernel/git/will/linux.git#for-next/perf
+arm-soc git git://git.kernel.org/pub/scm/linux/kernel/git/soc/soc.git#for-next
+amlogic git git://git.kernel.org/pub/scm/linux/kernel/git/amlogic/linux.git#for-next
+asahi-soc git https://github.com/AsahiLinux/linux.git#asahi-soc/for-next
+at91 git git://git.kernel.org/pub/scm/linux/kernel/git/at91/linux.git#at91-next
+bmc git git://git.kernel.org/pub/scm/linux/kernel/git/bmc/linux.git#for-next
+broadcom git https://github.com/Broadcom/stblinux.git#next
+davinci git git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git#davinci/for-next
+drivers-memory git https://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux-mem-ctrl.git#for-next
+fsl git https://github.com/chleroy/linux.git#soc_fsl
+imx-mxs git git://git.kernel.org/pub/scm/linux/kernel/git/shawnguo/linux.git#for-next
+mediatek git git://git.kernel.org/pub/scm/linux/kernel/git/mediatek/linux.git#for-next
+mvebu git git://git.kernel.org/pub/scm/linux/kernel/git/gclement/mvebu.git#for-next
+omap git git://git.kernel.org/pub/scm/linux/kernel/git/khilman/linux-omap.git#for-next
+qcom git git://git.kernel.org/pub/scm/linux/kernel/git/qcom/linux.git#for-next
+renesas git git://git.kernel.org/pub/scm/linux/kernel/git/geert/renesas-devel.git#next
+reset git https://git.pengutronix.de/git/pza/linux#reset/next
+rockchip git git://git.kernel.org/pub/scm/linux/kernel/git/mmind/linux-rockchip.git#for-next
+samsung-krzk git git://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux.git#for-next
+scmi git git://git.kernel.org/pub/scm/linux/kernel/git/sudeep.holla/linux.git#for-linux-next
+sophgo git https://github.com/sophgo/linux.git#for-next
+sophgo-soc git https://github.com/sophgo/linux.git#soc-for-next
+spacemit git https://github.com/spacemit-com/linux#for-next
+stm32 git git://git.kernel.org/pub/scm/linux/kernel/git/atorgue/stm32.git#stm32-next
+sunxi git git://git.kernel.org/pub/scm/linux/kernel/git/sunxi/linux.git#sunxi/for-next
+tee git git://git.kernel.org/pub/scm/linux/kernel/git/jenswi/linux-tee.git#next
+tegra git git://git.kernel.org/pub/scm/linux/kernel/git/tegra/linux.git#for-next
+thead-dt git git://git.kernel.org/pub/scm/linux/kernel/git/fustini/linux.git#thead-dt-for-next
+ti git git://git.kernel.org/pub/scm/linux/kernel/git/ti/linux.git#ti-next
+xilinx git git://github.com/Xilinx/linux-xlnx.git#for-next
+clk git git://git.kernel.org/pub/scm/linux/kernel/git/clk/linux.git#clk-next
+clk-imx git git://git.kernel.org/pub/scm/linux/kernel/git/abelvesa/linux.git#for-next
+clk-renesas git git://git.kernel.org/pub/scm/linux/kernel/git/geert/renesas-drivers.git#renesas-clk
+thead-clk git git://git.kernel.org/pub/scm/linux/kernel/git/fustini/linux.git#thead-clk-for-next
+csky git git://github.com/c-sky/csky-linux.git#linux-next
+loongarch git git://git.kernel.org/pub/scm/linux/kernel/git/chenhuacai/linux-loongson.git#loongarch-next
+m68k git git://git.kernel.org/pub/scm/linux/kernel/git/geert/linux-m68k.git#for-next
+m68knommu git git://git.kernel.org/pub/scm/linux/kernel/git/gerg/m68knommu.git#for-next
+microblaze git git://git.monstr.eu/linux-2.6-microblaze.git#next
+mips git git://git.kernel.org/pub/scm/linux/kernel/git/mips/linux.git#mips-next
+openrisc git git://github.com/openrisc/linux.git#for-next
+parisc-hd git git://git.kernel.org/pub/scm/linux/kernel/git/deller/parisc-linux.git#for-next
+powerpc git git://git.kernel.org/pub/scm/linux/kernel/git/powerpc/linux.git#next
+risc-v git git://git.kernel.org/pub/scm/linux/kernel/git/riscv/linux.git#for-next
+riscv-dt git git://git.kernel.org/pub/scm/linux/kernel/git/conor/linux.git#riscv-dt-for-next
+riscv-soc git git://git.kernel.org/pub/scm/linux/kernel/git/conor/linux.git#riscv-soc-for-next
+s390 git git://git.kernel.org/pub/scm/linux/kernel/git/s390/linux.git#for-next
+sh git git:git.kernel.org/pub/scm/linux/kernel/git/glaubitz/sh-linux.git#for-next
+sparc git git://git.kernel.org/pub/scm/linux/kernel/git/alarsson/linux-sparc.git#for-next
+uml git git://git.kernel.org/pub/scm/linux/kernel/git/uml/linux.git#next
+xtensa git git://github.com/jcmvbkbc/linux-xtensa.git#xtensa-for-next
+fs-next git linux-next
+printk git git://git.kernel.org/pub/scm/linux/kernel/git/printk/linux.git#for-next
+pci git git://git.kernel.org/pub/scm/linux/kernel/git/pci/pci.git#next
+pstore git git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux.git#for-next/pstore
+hid git git://git.kernel.org/pub/scm/linux/kernel/git/hid/hid.git#for-next
+i2c git git://git.kernel.org/pub/scm/linux/kernel/git/wsa/linux.git#i2c/for-next
+i2c-host git git://git.kernel.org/pub/scm/linux/kernel/git/andi.shyti/linux.git#i2c/i2c-host
+i3c git git://git.kernel.org/pub/scm/linux/kernel/git/i3c/linux.git#i3c/next
+dmi git git://git.kernel.org/pub/scm/linux/kernel/git/jdelvare/staging.git#dmi-for-next
+hwmon-staging git git://git.kernel.org/pub/scm/linux/kernel/git/groeck/linux-staging.git#hwmon-next
+jc_docs git git://git.lwn.net/linux.git#docs-next
+v4l-dvb git git://linuxtv.org/media-ci/media-pending.git#next
+v4l-dvb-next git git://linuxtv.org/mchehab/media-next.git#master
+pm git git://git.kernel.org/pub/scm/linux/kernel/git/rafael/linux-pm.git#linux-next
+cpufreq-arm git git://git.kernel.org/pub/scm/linux/kernel/git/vireshk/pm.git#cpufreq/arm/linux-next
+cpupower git git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux.git#cpupower
+devfreq git git://git.kernel.org/pub/scm/linux/kernel/git/chanwoo/linux.git#devfreq-next
+pmdomain git git://git.kernel.org/pub/scm/linux/kernel/git/ulfh/linux-pm.git#next
+opp git git://git.kernel.org/pub/scm/linux/kernel/git/vireshk/pm.git#opp/linux-next
+thermal git git://git.kernel.org/pub/scm/linux/kernel/git/thermal/linux.git#thermal/linux-next
+rdma git git://git.kernel.org/pub/scm/linux/kernel/git/rdma/rdma.git#for-next
+net-next git git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net-next.git#main
+bpf-next git git://git.kernel.org/pub/scm/linux/kernel/git/bpf/bpf-next.git#for-next
+ipsec-next git git://git.kernel.org/pub/scm/linux/kernel/git/klassert/ipsec-next.git#master
+mlx5-next git git://git.kernel.org/pub/scm/linux/kernel/git/mellanox/linux.git#mlx5-next
+netfilter-next git git://git.kernel.org/pub/scm/linux/kernel/git/netfilter/nf-next.git#main
+ipvs-next git git://git.kernel.org/pub/scm/linux/kernel/git/horms/ipvs-next.git#main
+bluetooth git git://git.kernel.org/pub/scm/linux/kernel/git/bluetooth/bluetooth-next.git#master
+wireless-next git git://git.kernel.org/pub/scm/linux/kernel/git/wireless/wireless-next.git#for-next
+ath-next git git://git.kernel.org/pub/scm/linux/kernel/git/ath/ath.git#for-next
+iwlwifi-next git https://git.kernel.org/pub/scm/linux/kernel/git/iwlwifi/iwlwifi-next.git#next
+wpan-next git git://git.kernel.org/pub/scm/linux/kernel/git/wpan/wpan-next.git#master
+wpan-staging git git://git.kernel.org/pub/scm/linux/kernel/git/wpan/wpan-next.git#staging
+mtd git git://git.kernel.org/pub/scm/linux/kernel/git/mtd/linux.git#mtd/next
+nand git git://git.kernel.org/pub/scm/linux/kernel/git/mtd/linux.git#nand/next
+spi-nor git git://git.kernel.org/pub/scm/linux/kernel/git/mtd/linux.git#spi-nor/next
+crypto git git://git.kernel.org/pub/scm/linux/kernel/git/herbert/cryptodev-2.6.git#master
+libcrypto git git://git.kernel.org/pub/scm/linux/kernel/git/ebiggers/linux.git#libcrypto-next
+drm git https://gitlab.freedesktop.org/drm/kernel.git#drm-next
+drm-exynos git git://git.kernel.org/pub/scm/linux/kernel/git/daeinki/drm-exynos.git#for-linux-next
+drm-misc git https://gitlab.freedesktop.org/drm/misc/kernel.git#for-linux-next
+amdgpu git https://gitlab.freedesktop.org/agd5f/linux#drm-next
+drm-intel git https://gitlab.freedesktop.org/drm/i915/kernel#for-linux-next
+drm-msm git https://gitlab.freedesktop.org/drm/msm.git#msm-next
+drm-msm-lumag git https://gitlab.freedesktop.org/lumag/msm.git#msm-next-lumag
+drm-nova git https://gitlab.freedesktop.org/drm/nova.git#nova-next
+drm-xe git https://gitlab.freedesktop.org/drm/xe/kernel#drm-xe-next
+etnaviv git https://git.pengutronix.de/git/lst/linux#etnaviv/next
+fbdev git git://git.kernel.org/pub/scm/linux/kernel/git/deller/linux-fbdev.git#for-next
+regmap git git://git.kernel.org/pub/scm/linux/kernel/git/broonie/regmap.git#for-next
+sound git git://git.kernel.org/pub/scm/linux/kernel/git/tiwai/sound.git#for-next
+ieee1394 git https://git.kernel.org/pub/scm/linux/kernel/git/ieee1394/linux1394.git#for-next
+sound-asoc git git://git.kernel.org/pub/scm/linux/kernel/git/broonie/sound.git#for-next
+modules git git://git.kernel.org/pub/scm/linux/kernel/git/modules/linux.git#modules-next
+input git git://git.kernel.org/pub/scm/linux/kernel/git/dtor/input.git#next
+block git git://git.kernel.dk/linux-block.git#for-next
+device-mapper git git://git.kernel.org/pub/scm/linux/kernel/git/device-mapper/linux-dm.git#for-next
+libata git git://git.kernel.org/pub/scm/linux/kernel/git/libata/linux#for-next
+pcmcia git git://git.kernel.org/pub/scm/linux/kernel/git/brodo/linux.git#pcmcia-next
+mmc git git://git.kernel.org/pub/scm/linux/kernel/git/ulfh/mmc.git#next
+mfd git git://git.kernel.org/pub/scm/linux/kernel/git/lee/mfd.git#for-mfd-next
+backlight git git://git.kernel.org/pub/scm/linux/kernel/git/lee/backlight.git#for-backlight-next
+battery git git://git.kernel.org/pub/scm/linux/kernel/git/sre/linux-power-supply.git#for-next
+regulator git git://git.kernel.org/pub/scm/linux/kernel/git/broonie/regulator.git#for-next
+security git git://git.kernel.org/pub/scm/linux/kernel/git/pcmoore/lsm.git#next
+apparmor git git://git.kernel.org/pub/scm/linux/kernel/git/jj/linux-apparmor#apparmor-next
+integrity git git://git.kernel.org/pub/scm/linux/kernel/git/zohar/linux-integrity#next-integrity
+selinux git git://git.kernel.org/pub/scm/linux/kernel/git/pcmoore/selinux.git#next
+smack git git://github.com/cschaufler/smack-next#next
+tomoyo git git://git.code.sf.net/p/tomoyo/tomoyo.git#master
+tpmdd git git://git.kernel.org/pub/scm/linux/kernel/git/jarkko/linux-tpmdd.git#next
+watchdog git git://www.linux-watchdog.org/linux-watchdog-next.git#master
+iommu git git://git.kernel.org/pub/scm/linux/kernel/git/iommu/linux.git#next
+audit git git://git.kernel.org/pub/scm/linux/kernel/git/pcmoore/audit.git#next
+devicetree git git://git.kernel.org/pub/scm/linux/kernel/git/robh/linux.git#for-next
+dt-krzk git git://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux-dt.git#for-next
+mailbox git git://git.kernel.org/pub/scm/linux/kernel/git/jassibrar/mailbox.git#for-next
+spi git git://git.kernel.org/pub/scm/linux/kernel/git/broonie/spi.git#for-next
+tip git git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip.git#master
+clockevents git git://git.kernel.org/pub/scm/linux/kernel/git/daniel.lezcano/linux.git#timers/drivers/next
+edac git git://git.kernel.org/pub/scm/linux/kernel/git/ras/ras.git#edac-for-next
+ftrace git git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git#for-next
+rcu git git://git.kernel.org/pub/scm/linux/kernel/git/rcu/linux.git#next
+paulmck git git://git.kernel.org/pub/scm/linux/kernel/git/paulmck/linux-rcu.git#non-rcu/next
+kvm git git://git.kernel.org/pub/scm/virt/kvm/kvm.git#next
+kvm-arm git git://git.kernel.org/pub/scm/linux/kernel/git/kvmarm/kvmarm.git#next
+kvms390 git git://git.kernel.org/pub/scm/linux/kernel/git/kvms390/linux.git#next
+kvm-ppc git git://git.kernel.org/pub/scm/linux/kernel/git/powerpc/linux.git#topic/ppc-kvm
+kvm-riscv git https://github.com/kvm-riscv/linux.git#riscv_kvm_next
+kvm-x86 git https://github.com/kvm-x86/linux.git#next
+xen-tip git git://git.kernel.org/pub/scm/linux/kernel/git/xen/tip.git#linux-next
+percpu git git://git.kernel.org/pub/scm/linux/kernel/git/dennis/percpu.git#for-next
+workqueues git git://git.kernel.org/pub/scm/linux/kernel/git/tj/wq.git#for-next
+sched-ext git git://git.kernel.org/pub/scm/linux/kernel/git/tj/sched_ext.git#for-next
+drivers-x86 git git://git.kernel.org/pub/scm/linux/kernel/git/pdx86/platform-drivers-x86.git#for-next
+chrome-platform git git://git.kernel.org/pub/scm/linux/kernel/git/chrome-platform/linux.git#for-next
+chrome-platform-firmware git git://git.kernel.org/pub/scm/linux/kernel/git/chrome-platform/linux.git#for-firmware-next
+hsi git git://git.kernel.org/pub/scm/linux/kernel/git/sre/linux-hsi.git#for-next
+leds-lj git git://git.kernel.org/pub/scm/linux/kernel/git/lee/leds.git#for-leds-next
+ipmi git git://github.com/cminyard/linux-ipmi.git#for-next
+driver-core git git://git.kernel.org/pub/scm/linux/kernel/git/driver-core/driver-core.git#driver-core-next
+usb git git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/usb.git#usb-next
+thunderbolt git git://git.kernel.org/pub/scm/linux/kernel/git/westeri/thunderbolt.git#next
+usb-serial git git://git.kernel.org/pub/scm/linux/kernel/git/johan/usb-serial.git#usb-next
+tty git git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/tty.git#tty-next
+char-misc git git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/char-misc.git#char-misc-next
+accel git git://git.kernel.org/pub/scm/linux/kernel/git/ogabbay/linux.git#habanalabs-next
+coresight git git://git.kernel.org/pub/scm/linux/kernel/git/coresight/linux.git#next
+fastrpc git git://git.kernel.org/pub/scm/linux/kernel/git/srini/fastrpc.git#for-next
+fpga git git://git.kernel.org/pub/scm/linux/kernel/git/fpga/linux-fpga.git#for-next
+icc git git://git.kernel.org/pub/scm/linux/kernel/git/djakov/icc.git#icc-next
+iio git git://git.kernel.org/pub/scm/linux/kernel/git/jic23/iio.git#togreg
+phy-next git git://git.kernel.org/pub/scm/linux/kernel/git/phy/linux-phy.git#next
+soundwire git git://git.kernel.org/pub/scm/linux/kernel/git/vkoul/soundwire.git#next
+extcon git git://git.kernel.org/pub/scm/linux/kernel/git/chanwoo/extcon.git#extcon-next
+gnss git git://git.kernel.org/pub/scm/linux/kernel/git/johan/gnss.git#gnss-next
+vfio git git://github.com/awilliam/linux-vfio.git#next
+w1 git git://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux-w1.git#for-next
+spmi git git://git.kernel.org/pub/scm/linux/kernel/git/sboyd/spmi.git#spmi-next
+staging git git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/staging.git#staging-next
+counter-next git git://git.kernel.org/pub/scm/linux/kernel/git/wbg/counter.git#counter-next
+siox git git://git.kernel.org/pub/scm/linux/kernel/git/ukleinek/linux.git#siox/for-next
+mux git https://gitlab.com/peda-linux/mux.git#for-next
+dmaengine git git://git.kernel.org/pub/scm/linux/kernel/git/vkoul/dmaengine.git#next
+cgroup git git://git.kernel.org/pub/scm/linux/kernel/git/tj/cgroup.git#for-next
+scsi git git://git.kernel.org/pub/scm/linux/kernel/git/jejb/scsi.git#for-next
+scsi-mkp git git://git.kernel.org/pub/scm/linux/kernel/git/mkp/scsi.git#for-next
+vhost git git://git.kernel.org/pub/scm/linux/kernel/git/mst/vhost.git#linux-next
+rpmsg git git://git.kernel.org/pub/scm/linux/kernel/git/remoteproc/linux.git#for-next
+gpio-brgl git git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git#gpio/for-next
+gpio-intel git git://git.kernel.org/pub/scm/linux/kernel/git/andy/linux-gpio-intel.git#for-next
+pinctrl git git://git.kernel.org/pub/scm/linux/kernel/git/linusw/linux-pinctrl.git#for-next
+pinctrl-intel git git://git.kernel.org/pub/scm/linux/kernel/git/pinctrl/intel.git#for-next
+pinctrl-renesas git git://git.kernel.org/pub/scm/linux/kernel/git/geert/renesas-drivers.git#renesas-pinctrl
+pinctrl-samsung git git://git.kernel.org/pub/scm/linux/kernel/git/pinctrl/samsung.git#for-next
+pwm git git://git.kernel.org/pub/scm/linux/kernel/git/ukleinek/linux.git#pwm/for-next
+ktest git git://git.kernel.org/pub/scm/linux/kernel/git/rostedt/linux-ktest.git#for-next
+kselftest git git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux-kselftest.git#next
+kunit git git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux-kselftest.git#test
+kunit-next git git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux-kselftest.git#kunit
+livepatching git git://git.kernel.org/pub/scm/linux/kernel/git/livepatching/livepatching#for-next
+rtc git git://git.kernel.org/pub/scm/linux/kernel/git/abelloni/linux.git#rtc-next
+nvdimm git git://git.kernel.org/pub/scm/linux/kernel/git/nvdimm/nvdimm.git#libnvdimm-for-next
+at24 git git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git#at24/for-next
+ntb git https://github.com/jonmason/ntb.git#ntb-next
+seccomp git git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux.git#for-next/seccomp
+slimbus git git://git.kernel.org/pub/scm/linux/kernel/git/srini/slimbus.git#for-next
+nvmem git git://git.kernel.org/pub/scm/linux/kernel/git/srini/nvmem.git#for-next
+xarray git git://git.infradead.org/users/willy/xarray.git#main
+hyperv git git://git.kernel.org/pub/scm/linux/kernel/git/hyperv/linux.git#hyperv-next
+auxdisplay git git://git.kernel.org/pub/scm/linux/kernel/git/andy/linux-auxdisplay.git#for-next
+kgdb git git://git.kernel.org/pub/scm/linux/kernel/git/danielt/linux.git#kgdb/for-next
+hmm git git://git.kernel.org/pub/scm/linux/kernel/git/rdma/rdma.git#hmm
+cfi git git://git.kernel.org/pub/scm/linux/kernel/git/mtd/linux.git#cfi/next
+mhi git git://git.kernel.org/pub/scm/linux/kernel/git/mani/mhi.git#mhi-next
+memblock git git://git.kernel.org/pub/scm/linux/kernel/git/rppt/memblock.git#for-next
+cxl git git://git.kernel.org/pub/scm/linux/kernel/git/cxl/cxl.git#next
+zstd git https://github.com/terrelln/linux.git#zstd-next
+efi git git://git.kernel.org/pub/scm/linux/kernel/git/efi/efi.git#next
+unicode git git://git.kernel.org/pub/scm/linux/kernel/git/krisman/unicode.git#for-next
+slab git git://git.kernel.org/pub/scm/linux/kernel/git/vbabka/slab.git#slab/for-next
+random git git://git.kernel.org/pub/scm/linux/kernel/git/crng/random.git#master
+landlock git git://git.kernel.org/pub/scm/linux/kernel/git/mic/linux.git#next
+rust git https://github.com/Rust-for-Linux/linux.git#rust-next
+rust-alloc git https://github.com/Rust-for-Linux/linux.git#alloc-next
+rust-io git https://github.com/Rust-for-Linux/linux.git#io-next
+rust-pin-init git https://github.com/Rust-for-Linux/linux.git#pin-init-next
+rust-timekeeping git https://github.com/Rust-for-Linux/linux.git#timekeeping-next
+rust-xarray git https://github.com/Rust-for-Linux/linux.git#xarray-next
+sysctl git git://git.kernel.org/pub/scm/linux/kernel/git/sysctl/sysctl.git#sysctl-next
+execve git git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux.git#for-next/execve
+bitmap git https://github.com/norov/linux.git#bitmap-for-next
+hte git git://git.kernel.org/pub/scm/linux/kernel/git/pateldipen1984/linux.git#for-next
+kspp git git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux.git#for-next/kspp
+nolibc git git://git.kernel.org/pub/scm/linux/kernel/git/nolibc/linux-nolibc.git#for-next
+iommufd git git://git.kernel.org/pub/scm/linux/kernel/git/jgg/iommufd.git#for-next
+turbostat git git://git.kernel.org/pub/scm/linux/kernel/git/lenb/linux.git#next
+pwrseq git git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git#pwrseq/for-next
+capabilities-next git git://git.kernel.org/pub/scm/linux/kernel/git/sergeh/linux.git#caps-next
+ipe git https://git.kernel.org/pub/scm/linux/kernel/git/wufan/ipe.git#next
+kcsan git git://git.kernel.org/pub/scm/linux/kernel/git/melver/linux.git#next
+crc git git://git.kernel.org/pub/scm/linux/kernel/git/ebiggers/linux.git#crc-next
+fwctl git git//git.kernel.org/pub/scm/linux/kernel/git/fwctl/fwctl.git#for-next
+devsec-tsm git git://git.kernel.org/pub/scm/linux/kernel/git/devsec/tsm.git#next
+hisilicon git https://github.com/hisilicon/linux-hisi.git#for-next
+kthread git git://git.kernel.org/pub/scm/linux/kernel/git/frederic/linux-dynticks.git#for-next
diff --git a/Next/merge.log b/Next/merge.log
new file mode 100644
index 000000000000..03828a662f7b
--- /dev/null
+++ b/Next/merge.log
@@ -0,0 +1,3094 @@
+$ date -R
+Tue, 05 Aug 2025 09:05:52 +1000
+$ git checkout master
+Already on 'master'
+$ git reset --hard stable
+HEAD is now at 3c4a063b1f8a Merge tag 'trace-v6.17-2' of git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace
+Merging origin/master (35a813e010b9 Merge tag 'printk-for-6.17' of git://git.kernel.org/pub/scm/linux/kernel/git/printk/linux)
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git origin/master
+Updating 3c4a063b1f8a..35a813e010b9
+Fast-forward (no commit created; -m option ignored)
+ .mailmap | 1 +
+ Documentation/accounting/delay-accounting.rst | 56 ++
+ .../device-mapper/thin-provisioning.rst | 16 +-
+ Documentation/admin-guide/kdump/kdump.rst | 21 +
+ Documentation/admin-guide/kernel-parameters.txt | 86 +-
+ Documentation/admin-guide/sysctl/kernel.rst | 20 +-
+ .../devicetree/bindings/rtc/amlogic,a4-rtc.yaml | 11 +-
+ .../devicetree/bindings/rtc/nxp,lpc1788-rtc.yaml | 7 +-
+ .../devicetree/bindings/rtc/nxp,lpc3220-rtc.yaml | 49 ++
+ .../devicetree/bindings/rtc/nxp,pcf85063.yaml | 33 +-
+ .../{soc/sophgo => rtc}/sophgo,cv1800b-rtc.yaml | 2 +-
+ .../devicetree/bindings/rtc/trivial-rtc.yaml | 2 -
+ MAINTAINERS | 14 +-
+ arch/alpha/kernel/core_marvel.c | 11 +-
+ arch/arm/kernel/setup.c | 2 +-
+ arch/arm64/mm/init.c | 2 +-
+ arch/loongarch/kernel/setup.c | 2 +-
+ arch/mips/kernel/setup.c | 2 +-
+ arch/openrisc/include/asm/mmu.h | 2 +-
+ arch/openrisc/include/asm/page.h | 8 +-
+ arch/openrisc/include/asm/pgtable.h | 4 +-
+ arch/openrisc/include/asm/processor.h | 4 +-
+ arch/openrisc/include/asm/ptrace.h | 4 +-
+ arch/openrisc/include/asm/setup.h | 2 +-
+ arch/openrisc/include/asm/thread_info.h | 8 +-
+ arch/openrisc/include/uapi/asm/ptrace.h | 2 +-
+ arch/powerpc/include/asm/ppc-opcode.h | 1 +
+ arch/powerpc/kernel/eeh.c | 1 +
+ arch/powerpc/kernel/eeh_driver.c | 48 +-
+ arch/powerpc/kernel/eeh_pe.c | 10 +-
+ arch/powerpc/kernel/fadump.c | 2 +-
+ arch/powerpc/kernel/pci-hotplug.c | 3 +
+ arch/powerpc/kexec/core.c | 2 +-
+ arch/powerpc/mm/nohash/kaslr_booke.c | 2 +-
+ arch/powerpc/net/bpf_jit_comp64.c | 82 ++
+ arch/riscv/Kconfig | 1 +
+ arch/riscv/kernel/kexec_elf.c | 1 +
+ arch/riscv/kernel/setup.c | 5 +
+ arch/riscv/mm/init.c | 2 +-
+ arch/s390/kernel/setup.c | 2 +-
+ arch/sh/kernel/machine_kexec.c | 2 +-
+ arch/x86/kernel/crash.c | 26 +-
+ arch/x86/kernel/setup.c | 5 +-
+ arch/x86/kvm/i8254.c | 4 +-
+ crypto/async_tx/async_pq.c | 2 +-
+ crypto/async_tx/async_raid6_recov.c | 4 +-
+ drivers/cxl/core/mce.h | 2 +-
+ drivers/gpu/drm/i915/gt/uc/intel_guc_log.c | 3 +-
+ drivers/gpu/drm/xe/xe_vm_types.h | 2 +-
+ drivers/md/dm-flakey.c | 9 +-
+ drivers/md/dm-ima.c | 42 +-
+ drivers/md/dm-path-selector.c | 8 +-
+ drivers/md/dm-path-selector.h | 2 +-
+ drivers/md/dm-ps-historical-service-time.c | 9 +-
+ drivers/md/dm-ps-io-affinity.c | 5 +-
+ drivers/md/dm-ps-queue-length.c | 9 +-
+ drivers/md/dm-ps-round-robin.c | 9 +-
+ drivers/md/dm-ps-service-time.c | 9 +-
+ drivers/md/dm-raid.c | 7 +-
+ drivers/md/dm-table.c | 10 +-
+ drivers/md/dm-thin.c | 7 +-
+ drivers/md/dm-vdo/funnel-workqueue.c | 3 +-
+ drivers/md/dm-verity-fec.c | 4 +-
+ drivers/md/dm-verity-target.c | 185 +----
+ drivers/md/dm-verity.h | 22 +-
+ drivers/md/dm-zone.c | 2 -
+ drivers/md/dm-zoned-target.c | 2 +-
+ drivers/md/dm.c | 11 +-
+ drivers/net/ethernet/marvell/mvneta.c | 2 +-
+ drivers/net/wwan/iosm/iosm_ipc_trace.c | 3 +-
+ drivers/net/wwan/t7xx/t7xx_port_trace.c | 2 +-
+ drivers/pci/hotplug/pnv_php.c | 250 +++++-
+ drivers/rtc/Kconfig | 21 +-
+ drivers/rtc/Makefile | 2 +-
+ drivers/rtc/lib.c | 40 +-
+ drivers/rtc/rtc-ds1307.c | 30 +-
+ drivers/rtc/rtc-ds1685.c | 4 +-
+ drivers/rtc/rtc-hym8563.c | 15 +-
+ drivers/rtc/rtc-m41t80.c | 25 +-
+ drivers/rtc/rtc-max31335.c | 12 +-
+ drivers/rtc/rtc-nct3018y.c | 15 +-
+ drivers/rtc/rtc-pcf85063.c | 351 ++++++---
+ drivers/rtc/rtc-pcf8563.c | 15 +-
+ drivers/rtc/rtc-rv3028.c | 15 +-
+ drivers/rtc/rtc-rv3032.c | 21 +-
+ drivers/rtc/rtc-s3c.c | 8 +-
+ drivers/rtc/rtc-sh.c | 8 +-
+ drivers/rtc/sysfs.c | 64 +-
+ drivers/rtc/{lib_test.c => test_rtc_lib.c} | 0
+ fs/fat/fatent.c | 2 +-
+ fs/fat/misc.c | 6 +-
+ fs/ocfs2/aops.c | 1 +
+ fs/ocfs2/dir.c | 8 +
+ fs/ocfs2/dlm/dlmrecovery.c | 2 +-
+ fs/ocfs2/inode.c | 70 +-
+ fs/ocfs2/move_extents.c | 19 +-
+ fs/ocfs2/namei.c | 11 +-
+ fs/ocfs2/stack_user.c | 15 +-
+ fs/proc/vmcore.c | 29 +-
+ fs/squashfs/block.c | 47 +-
+ fs/squashfs/file.c | 7 +-
+ include/linux/compiler-gcc.h | 2 +
+ include/linux/crash_reserve.h | 15 +-
+ include/linux/gcd.h | 3 +
+ include/linux/hung_task.h | 18 +-
+ include/linux/jhash.h | 8 +-
+ include/linux/kexec.h | 10 +
+ include/linux/raid/pq.h | 12 +-
+ include/linux/relay.h | 24 +-
+ include/linux/rtc/ds1685.h | 2 +-
+ include/linux/rwsem.h | 12 +
+ include/linux/sprintf.h | 2 +-
+ include/linux/sys_info.h | 28 +
+ include/linux/xxhash.h | 26 -
+ include/uapi/linux/kexec.h | 1 +
+ include/xen/xenbus.h | 2 +-
+ init/Kconfig | 4 +
+ init/main.c | 6 +-
+ kernel/crash_core.c | 15 +
+ kernel/crash_reserve.c | 68 +-
+ kernel/events/uprobes.c | 4 +-
+ kernel/exit.c | 7 +-
+ kernel/fork.c | 95 ++-
+ kernel/hung_task.c | 29 +-
+ kernel/kcov.c | 2 +-
+ kernel/kexec.c | 2 +-
+ kernel/kexec_core.c | 100 ++-
+ kernel/kexec_file.c | 51 +-
+ kernel/kexec_internal.h | 2 +-
+ kernel/kthread.c | 11 +-
+ kernel/locking/rwsem.c | 31 +-
+ kernel/panic.c | 71 +-
+ kernel/printk/internal.h | 2 +
+ kernel/printk/nbcon.c | 89 ++-
+ kernel/printk/printk.c | 20 +-
+ kernel/relay.c | 69 +-
+ kernel/sched/psi.c | 6 +-
+ kernel/trace/blktrace.c | 22 +-
+ kernel/ucount.c | 16 +-
+ lib/Kconfig.debug | 20 +
+ lib/Makefile | 3 +-
+ lib/math/div64.c | 13 +-
+ lib/math/gcd.c | 27 +-
+ lib/raid6/algos.c | 3 -
+ lib/raid6/recov.c | 6 +-
+ lib/raid6/recov_avx2.c | 6 +-
+ lib/raid6/recov_avx512.c | 6 +-
+ lib/raid6/recov_loongarch_simd.c | 12 +-
+ lib/raid6/recov_neon.c | 6 +-
+ lib/raid6/recov_rvv.c | 6 +-
+ lib/raid6/recov_s390xc.c | 6 +-
+ lib/raid6/recov_ssse3.c | 6 +-
+ lib/stackdepot.c | 67 +-
+ lib/sys_info.c | 122 +++
+ lib/test_kho.c | 305 ++++++++
+ lib/vsprintf.c | 70 +-
+ lib/xxhash.c | 107 ---
+ mm/slub.c | 5 +-
+ samples/Kconfig | 9 +-
+ samples/hung_task/hung_task_tests.c | 81 +-
+ scripts/checkpatch.pl | 33 +-
+ scripts/coccinelle/misc/secs_to_jiffies.cocci | 49 +-
+ scripts/gdb/linux/constants.py.in | 12 +-
+ scripts/spelling.txt | 1 +
+ security/apparmor/Makefile | 6 +-
+ security/apparmor/af_unix.c | 799 +++++++++++++++++++
+ security/apparmor/apparmorfs.c | 39 +-
+ security/apparmor/audit.c | 2 +-
+ security/apparmor/capability.c | 61 +-
+ security/apparmor/domain.c | 203 +++--
+ security/apparmor/file.c | 92 ++-
+ security/apparmor/include/af_unix.h | 55 ++
+ security/apparmor/include/apparmor.h | 4 +-
+ security/apparmor/include/audit.h | 5 +-
+ security/apparmor/include/capability.h | 1 +
+ security/apparmor/include/cred.h | 31 +-
+ security/apparmor/include/file.h | 11 +-
+ security/apparmor/include/ipc.h | 3 +
+ security/apparmor/include/label.h | 51 +-
+ security/apparmor/include/lib.h | 46 +-
+ security/apparmor/include/match.h | 10 +-
+ security/apparmor/include/net.h | 36 +-
+ security/apparmor/include/path.h | 1 +
+ security/apparmor/include/perms.h | 8 +-
+ security/apparmor/include/policy.h | 63 +-
+ security/apparmor/include/sig_names.h | 6 +-
+ security/apparmor/include/signal.h | 19 +
+ security/apparmor/ipc.c | 13 +-
+ security/apparmor/label.c | 37 +-
+ security/apparmor/lib.c | 114 +++
+ security/apparmor/lsm.c | 468 ++++++++---
+ security/apparmor/match.c | 23 +-
+ security/apparmor/mount.c | 12 +-
+ security/apparmor/net.c | 189 ++++-
+ security/apparmor/policy.c | 93 ++-
+ security/apparmor/policy_compat.c | 6 +-
+ security/apparmor/policy_ns.c | 2 +-
+ security/apparmor/policy_unpack.c | 67 +-
+ security/apparmor/policy_unpack_test.c | 6 +-
+ security/apparmor/procattr.c | 6 +-
+ security/apparmor/resource.c | 11 +-
+ security/apparmor/task.c | 11 +-
+ tools/accounting/Makefile | 2 +-
+ tools/accounting/delaytop.c | 862 +++++++++++++++++++++
+ tools/accounting/getdelays.c | 167 ++--
+ tools/testing/selftests/bpf/progs/bpf_misc.h | 3 +-
+ tools/testing/selftests/kho/arm64.conf | 9 +
+ tools/testing/selftests/kho/init.c | 100 +++
+ tools/testing/selftests/kho/vmtest.sh | 183 +++++
+ tools/testing/selftests/kho/x86.conf | 7 +
+ tools/testing/selftests/ptrace/.gitignore | 1 +
+ .../intel/workload_hint/workload_hint_test.c | 16 +-
+ 212 files changed, 6222 insertions(+), 1664 deletions(-)
+ create mode 100644 Documentation/devicetree/bindings/rtc/nxp,lpc3220-rtc.yaml
+ rename Documentation/devicetree/bindings/{soc/sophgo => rtc}/sophgo,cv1800b-rtc.yaml (96%)
+ rename drivers/rtc/{lib_test.c => test_rtc_lib.c} (100%)
+ create mode 100644 include/linux/sys_info.h
+ create mode 100644 lib/sys_info.c
+ create mode 100644 lib/test_kho.c
+ create mode 100644 security/apparmor/af_unix.c
+ create mode 100644 security/apparmor/include/af_unix.h
+ create mode 100644 security/apparmor/include/signal.h
+ create mode 100644 tools/accounting/delaytop.c
+ create mode 100644 tools/testing/selftests/kho/arm64.conf
+ create mode 100644 tools/testing/selftests/kho/init.c
+ create mode 100755 tools/testing/selftests/kho/vmtest.sh
+ create mode 100644 tools/testing/selftests/kho/x86.conf
+Merging fixes/fixes (89be9a83ccf1 Linux 6.16-rc7)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/sfr/next-fixes.git fixes/fixes
+Already up to date.
+Merging ext4-fixes/fixes (d0b3b7b22dfa Linux 6.16-rc4)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/tytso/ext4.git ext4-fixes/fixes
+Already up to date.
+Merging vfs-brauner-fixes/vfs.fixes (8b3c655fa240 afs: Set vllist to NULL if addr parsing fails)
+$ git merge -m Merge branch 'vfs.fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/vfs/vfs.git vfs-brauner-fixes/vfs.fixes
+Already up to date.
+Merging fscrypt-current/for-current (0af2f6be1b42 Linux 6.15-rc1)
+$ git merge -m Merge branch 'for-current' of git://git.kernel.org/pub/scm/fs/fscrypt/linux.git fscrypt-current/for-current
+Already up to date.
+Merging fsverity-current/for-current (0af2f6be1b42 Linux 6.15-rc1)
+$ git merge -m Merge branch 'for-current' of git://git.kernel.org/pub/scm/fs/fsverity/linux.git fsverity-current/for-current
+Already up to date.
+Merging btrfs-fixes/next-fixes (61d18d91dd4a Merge branch 'misc-6.17' into next-fixes)
+$ git merge -m Merge branch 'next-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/kdave/linux.git btrfs-fixes/next-fixes
+Merge made by the 'ort' strategy.
+Merging vfs-fixes/fixes (33927f3d0ecd habanalabs: fix UAF in export_dmabuf())
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs.git vfs-fixes/fixes
+Merge made by the 'ort' strategy.
+ drivers/accel/habanalabs/common/memory.c | 23 +++++++----------------
+ 1 file changed, 7 insertions(+), 16 deletions(-)
+Merging erofs-fixes/fixes (347e9f5043c8 Linux 6.16-rc6)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/xiang/erofs.git erofs-fixes/fixes
+Already up to date.
+Merging nfsd-fixes/nfsd-fixes (94d10a4dba0b sunrpc: handle SVC_GARBAGE during svc auth processing as auth error)
+$ git merge -m Merge branch 'nfsd-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/cel/linux nfsd-fixes/nfsd-fixes
+Already up to date.
+Merging v9fs-fixes/fixes/next (2014c95afece Linux 6.14-rc1)
+$ git merge -m Merge branch 'fixes/next' of git://git.kernel.org/pub/scm/linux/kernel/git/ericvh/v9fs.git v9fs-fixes/fixes/next
+Already up to date.
+Merging overlayfs-fixes/ovl-fixes (924577e4f6ca ovl: Fix nested backing file paths)
+$ git merge -m Merge branch 'ovl-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/overlayfs/vfs.git overlayfs-fixes/ovl-fixes
+Already up to date.
+Merging bcachefs/for-next (ae4d71be53dd bcachefs: Don't lock inode around page_symlink)
+$ git merge -m Merge branch 'for-next' of git://evilpiepirate.org/bcachefs.git bcachefs/for-next
+Auto-merging fs/bcachefs/fs-io-buffered.c
+Auto-merging fs/bcachefs/fs.c
+Merge made by the 'ort' strategy.
+ fs/bcachefs/acl.c | 29 +-
+ fs/bcachefs/alloc_background.c | 570 +++++++++----------
+ fs/bcachefs/alloc_background.h | 9 +-
+ fs/bcachefs/alloc_foreground.c | 258 ++++-----
+ fs/bcachefs/alloc_foreground.h | 9 +-
+ fs/bcachefs/async_objs.c | 29 +-
+ fs/bcachefs/async_objs.h | 7 +-
+ fs/bcachefs/async_objs_types.h | 2 +-
+ fs/bcachefs/backpointers.c | 167 +++---
+ fs/bcachefs/bcachefs.h | 91 ++--
+ fs/bcachefs/bcachefs_format.h | 42 +-
+ fs/bcachefs/bkey.c | 4 +-
+ fs/bcachefs/bkey_methods.c | 6 +-
+ fs/bcachefs/bkey_types.h | 5 +
+ fs/bcachefs/bset.c | 74 ++-
+ fs/bcachefs/btree_cache.c | 44 +-
+ fs/bcachefs/btree_cache.h | 19 +
+ fs/bcachefs/btree_gc.c | 258 ++++-----
+ fs/bcachefs/btree_io.c | 123 +++--
+ fs/bcachefs/btree_iter.c | 424 ++++++++-------
+ fs/bcachefs/btree_iter.h | 348 ++++++------
+ fs/bcachefs/btree_journal_iter.c | 20 +-
+ fs/bcachefs/btree_key_cache.c | 69 ++-
+ fs/bcachefs/btree_locking.c | 17 +-
+ fs/bcachefs/btree_node_scan.c | 36 +-
+ fs/bcachefs/btree_trans_commit.c | 125 +++--
+ fs/bcachefs/btree_types.h | 43 +-
+ fs/bcachefs/btree_update.c | 339 ++++++------
+ fs/bcachefs/btree_update.h | 150 +++--
+ fs/bcachefs/btree_update_interior.c | 387 ++++++-------
+ fs/bcachefs/btree_update_interior.h | 12 +-
+ fs/bcachefs/btree_write_buffer.c | 78 ++-
+ fs/bcachefs/btree_write_buffer.h | 8 +-
+ fs/bcachefs/buckets.c | 258 ++++-----
+ fs/bcachefs/buckets_waiting_for_journal.c | 30 +-
+ fs/bcachefs/chardev.c | 120 ++--
+ fs/bcachefs/checksum.c | 54 +-
+ fs/bcachefs/clock.c | 17 +-
+ fs/bcachefs/compress.c | 29 +-
+ fs/bcachefs/compress.h | 36 +-
+ fs/bcachefs/data_update.c | 58 +-
+ fs/bcachefs/data_update.h | 1 +
+ fs/bcachefs/debug.c | 88 ++-
+ fs/bcachefs/dirent.c | 88 ++-
+ fs/bcachefs/dirent.h | 4 +-
+ fs/bcachefs/disk_accounting.c | 270 +++++----
+ fs/bcachefs/disk_accounting.h | 19 +-
+ fs/bcachefs/disk_groups.c | 27 +-
+ fs/bcachefs/ec.c | 396 ++++++--------
+ fs/bcachefs/ec.h | 2 +-
+ fs/bcachefs/enumerated_ref.c | 4 +-
+ fs/bcachefs/errcode.c | 3 +-
+ fs/bcachefs/errcode.h | 14 +
+ fs/bcachefs/error.c | 65 +--
+ fs/bcachefs/error.h | 3 +-
+ fs/bcachefs/extent_update.c | 67 ++-
+ fs/bcachefs/extent_update.h | 2 -
+ fs/bcachefs/extents.c | 55 +-
+ fs/bcachefs/extents.h | 4 +
+ fs/bcachefs/fast_list.c | 32 +-
+ fs/bcachefs/fast_list.h | 2 +-
+ fs/bcachefs/fs-io-buffered.c | 96 ++--
+ fs/bcachefs/fs-io-direct.c | 26 +-
+ fs/bcachefs/fs-io-pagecache.c | 55 +-
+ fs/bcachefs/fs-io.c | 141 +++--
+ fs/bcachefs/fs-io.h | 19 +-
+ fs/bcachefs/fs-ioctl.c | 33 +-
+ fs/bcachefs/fs.c | 254 ++++-----
+ fs/bcachefs/fsck.c | 649 +++++++++++-----------
+ fs/bcachefs/inode.c | 252 ++++-----
+ fs/bcachefs/io_misc.c | 83 ++-
+ fs/bcachefs/io_read.c | 235 ++++----
+ fs/bcachefs/io_read.h | 24 +-
+ fs/bcachefs/io_write.c | 97 ++--
+ fs/bcachefs/journal.c | 253 ++++-----
+ fs/bcachefs/journal.h | 3 +-
+ fs/bcachefs/journal_io.c | 248 +++++----
+ fs/bcachefs/journal_io.h | 7 +
+ fs/bcachefs/journal_reclaim.c | 220 ++++----
+ fs/bcachefs/journal_seq_blacklist.c | 56 +-
+ fs/bcachefs/journal_seq_blacklist.h | 3 +
+ fs/bcachefs/logged_ops.c | 16 +-
+ fs/bcachefs/logged_ops.h | 2 +-
+ fs/bcachefs/lru.c | 48 +-
+ fs/bcachefs/lru.h | 10 +
+ fs/bcachefs/migrate.c | 31 +-
+ fs/bcachefs/move.c | 316 +++++------
+ fs/bcachefs/move.h | 14 +-
+ fs/bcachefs/movinggc.c | 218 +++++---
+ fs/bcachefs/namei.c | 154 +++---
+ fs/bcachefs/nocow_locking.c | 10 +-
+ fs/bcachefs/opts.c | 33 +-
+ fs/bcachefs/opts.h | 8 +-
+ fs/bcachefs/printbuf.h | 4 +
+ fs/bcachefs/progress.c | 6 +-
+ fs/bcachefs/progress.h | 3 +
+ fs/bcachefs/quota.c | 103 ++--
+ fs/bcachefs/rebalance.c | 216 ++++----
+ fs/bcachefs/recovery.c | 412 ++++----------
+ fs/bcachefs/recovery_passes.c | 68 +--
+ fs/bcachefs/recovery_passes.h | 9 +-
+ fs/bcachefs/reflink.c | 137 ++---
+ fs/bcachefs/replicas.c | 161 +++---
+ fs/bcachefs/sb-clean.c | 36 +-
+ fs/bcachefs/sb-counters_format.h | 12 +-
+ fs/bcachefs/sb-downgrade.c | 19 +-
+ fs/bcachefs/sb-errors.c | 45 +-
+ fs/bcachefs/sb-errors_format.h | 11 +-
+ fs/bcachefs/sb-members.c | 164 +++---
+ fs/bcachefs/sb-members.h | 44 +-
+ fs/bcachefs/sb-members_format.h | 2 +-
+ fs/bcachefs/six.c | 21 +-
+ fs/bcachefs/snapshot.c | 435 ++++++---------
+ fs/bcachefs/snapshot.h | 32 +-
+ fs/bcachefs/snapshot_types.h | 2 +-
+ fs/bcachefs/str_hash.c | 57 +-
+ fs/bcachefs/str_hash.h | 47 +-
+ fs/bcachefs/subvolume.c | 246 ++++-----
+ fs/bcachefs/subvolume.h | 20 +-
+ fs/bcachefs/super-io.c | 112 ++--
+ fs/bcachefs/super.c | 871 +++++++++++++++++-------------
+ fs/bcachefs/sysfs.c | 28 +-
+ fs/bcachefs/tests.c | 340 +++++-------
+ fs/bcachefs/thread_with_file.c | 48 +-
+ fs/bcachefs/time_stats.c | 7 +-
+ fs/bcachefs/trace.h | 157 ++----
+ fs/bcachefs/util.c | 28 +-
+ fs/bcachefs/util.h | 10 +-
+ fs/bcachefs/xattr.c | 58 +-
+ lib/closure.c | 12 +-
+ 130 files changed, 6357 insertions(+), 6790 deletions(-)
+Merging fscrypt/for-next (fa65058063cb ceph: Remove gfp_t argument from ceph_fscrypt_encrypt_*())
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/fs/fscrypt/linux.git fscrypt/for-next
+Already up to date.
+Merging btrfs/for-next (442ee950ea05 Merge branch 'for-next-current-v6.15-20250722' into for-next-20250722)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/kdave/linux.git btrfs/for-next
+Merge made by the 'ort' strategy.
+Merging ceph/master (b828b4bf29d1 ceph: fix variable dereferenced before check in ceph_umount_begin())
+$ git merge -m Merge branch 'master' of git://github.com/ceph/ceph-client.git ceph/master
+Already up to date.
+Merging cifs/for-next (da3d9a37f3cb smb: client: let recv_done() avoid touching data_transfer after cleanup/move)
+$ git merge -m Merge branch 'for-next' of git://git.samba.org/sfrench/cifs-2.6.git cifs/for-next
+Merge made by the 'ort' strategy.
+ fs/smb/client/cifs_debug.c | 6 +--
+ fs/smb/client/cifsfs.c | 2 +-
+ fs/smb/client/cifsglob.h | 5 ++
+ fs/smb/client/cifssmb.c | 4 +-
+ fs/smb/client/fs_context.c | 19 +------
+ fs/smb/client/fs_context.h | 18 ++++++-
+ fs/smb/client/link.c | 13 ++---
+ fs/smb/client/reparse.c | 2 +-
+ fs/smb/client/smb1ops.c | 2 +-
+ fs/smb/client/smb2inode.c | 5 +-
+ fs/smb/client/smb2ops.c | 5 +-
+ fs/smb/client/smbdirect.c | 124 +++++++++++++++------------------------------
+ fs/smb/client/smbdirect.h | 4 --
+ 13 files changed, 78 insertions(+), 131 deletions(-)
+Merging configfs/configfs-next (c6b190822459 MAINTAINERS: add configfs Rust abstractions)
+$ git merge -m Merge branch 'configfs-next' of git://git.kernel.org/pub/scm/linux/kernel/git/a.hindborg/linux.git configfs/configfs-next
+Already up to date.
+Merging ecryptfs/next (fba133a34118 ecryptfs: Remove unused declartion ecryptfs_fill_zeros())
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/tyhicks/ecryptfs.git ecryptfs/next
+Auto-merging fs/ecryptfs/crypto.c
+Auto-merging fs/ecryptfs/ecryptfs_kernel.h
+Merge made by the 'ort' strategy.
+ fs/ecryptfs/crypto.c | 2 +-
+ fs/ecryptfs/ecryptfs_kernel.h | 1 -
+ fs/ecryptfs/keystore.c | 4 ++--
+ 3 files changed, 3 insertions(+), 4 deletions(-)
+Merging dlm/next (6f8b4788266c dlm: drop SCTP Kconfig dependency)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/teigland/linux-dlm.git dlm/next
+Already up to date.
+Merging erofs/dev (df0ce6cefa45 erofs: support to readahead dirent blocks in erofs_readdir())
+$ git merge -m Merge branch 'dev' of git://git.kernel.org/pub/scm/linux/kernel/git/xiang/erofs.git erofs/dev
+Already up to date.
+Merging exfat/dev (b33f91c62762 exfat: optimize allocation bitmap loading time)
+$ git merge -m Merge branch 'dev' of git://git.kernel.org/pub/scm/linux/kernel/git/linkinjeon/exfat.git exfat/dev
+Merge made by the 'ort' strategy.
+ fs/exfat/balloc.c | 12 +++++++++++-
+ fs/exfat/dir.c | 13 ++++++++++++-
+ fs/exfat/exfat_fs.h | 1 +
+ fs/exfat/fatent.c | 10 ++++++++++
+ fs/exfat/file.c | 5 ++---
+ fs/exfat/namei.c | 5 +++++
+ fs/exfat/super.c | 32 +++++++++++++++++++++-----------
+ 7 files changed, 62 insertions(+), 16 deletions(-)
+Merging exportfs/exportfs-next (adc218676eef Linux 6.12)
+$ git merge -m Merge branch 'exportfs-next' of git://git.kernel.org/pub/scm/linux/kernel/git/cel/linux exportfs/exportfs-next
+Already up to date.
+Merging ext3/for_next (17e58687367a Merge fsnotify changes with fixed up authorship.)
+$ git merge -m Merge branch 'for_next' of git://git.kernel.org/pub/scm/linux/kernel/git/jack/linux-fs.git ext3/for_next
+Merge made by the 'ort' strategy.
+Merging ext4/dev (261a2abe20b0 ext4: fix unused variable warning in ext4_init_new_dir)
+$ git merge -m Merge branch 'dev' of git://git.kernel.org/pub/scm/linux/kernel/git/tytso/ext4.git ext4/dev
+Merge made by the 'ort' strategy.
+ fs/ext4/namei.c | 2 --
+ 1 file changed, 2 deletions(-)
+Merging f2fs/dev (078cad8212ce f2fs: drop inode from the donation list when the last file is closed)
+$ git merge -m Merge branch 'dev' of git://git.kernel.org/pub/scm/linux/kernel/git/jaegeuk/f2fs.git f2fs/dev
+Auto-merging Documentation/filesystems/f2fs.rst
+Auto-merging fs/f2fs/data.c
+Auto-merging fs/f2fs/f2fs.h
+Auto-merging fs/f2fs/file.c
+Auto-merging include/linux/fscrypt.h
+Merge made by the 'ort' strategy.
+ Documentation/ABI/testing/sysfs-fs-f2fs | 22 +
+ Documentation/filesystems/f2fs.rst | 6 +-
+ fs/f2fs/checkpoint.c | 8 +-
+ fs/f2fs/compress.c | 120 +-
+ fs/f2fs/data.c | 183 +--
+ fs/f2fs/debug.c | 21 +-
+ fs/f2fs/dir.c | 4 +-
+ fs/f2fs/extent_cache.c | 10 +-
+ fs/f2fs/f2fs.h | 151 ++-
+ fs/f2fs/file.c | 107 +-
+ fs/f2fs/gc.c | 54 +-
+ fs/f2fs/gc.h | 5 +-
+ fs/f2fs/inline.c | 20 +-
+ fs/f2fs/inode.c | 84 +-
+ fs/f2fs/namei.c | 12 +-
+ fs/f2fs/node.c | 261 ++--
+ fs/f2fs/node.h | 77 +-
+ fs/f2fs/recovery.c | 116 +-
+ fs/f2fs/segment.c | 62 +-
+ fs/f2fs/segment.h | 59 +-
+ fs/f2fs/super.c | 2185 +++++++++++++++++--------------
+ fs/f2fs/sysfs.c | 48 +
+ include/linux/f2fs_fs.h | 2 +-
+ include/linux/fscrypt.h | 10 +-
+ 24 files changed, 2056 insertions(+), 1571 deletions(-)
+Merging fsverity/for-next (d0b3b7b22dfa Linux 6.16-rc4)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/fs/fsverity/linux.git fsverity/for-next
+Already up to date.
+Merging fuse/for-next (f0e84022479b virtio_fs: Remove redundant spinlock in virtio_fs_request_complete())
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/mszeredi/fuse.git fuse/for-next
+Auto-merging MAINTAINERS
+Auto-merging fs/fuse/file.c
+Auto-merging fs/fuse/virtio_fs.c
+Auto-merging include/linux/wait.h
+Auto-merging tools/testing/selftests/Makefile
+Merge made by the 'ort' strategy.
+ .../filesystems/{ => fuse}/fuse-io-uring.rst | 0
+ Documentation/filesystems/{ => fuse}/fuse-io.rst | 2 +-
+ .../filesystems/{ => fuse}/fuse-passthrough.rst | 0
+ Documentation/filesystems/{ => fuse}/fuse.rst | 20 ++-
+ Documentation/filesystems/fuse/index.rst | 14 ++
+ Documentation/filesystems/index.rst | 5 +-
+ MAINTAINERS | 3 +-
+ fs/fuse/dev.c | 5 +-
+ fs/fuse/file.c | 1 -
+ fs/fuse/virtio_fs.c | 3 -
+ include/linux/wait.h | 12 ++
+ tools/testing/selftests/Makefile | 1 +
+ .../testing/selftests/filesystems/fuse/.gitignore | 3 +
+ tools/testing/selftests/filesystems/fuse/Makefile | 21 +++
+ .../testing/selftests/filesystems/fuse/fuse_mnt.c | 146 +++++++++++++++++++++
+ .../selftests/filesystems/fuse/fusectl_test.c | 140 ++++++++++++++++++++
+ 16 files changed, 361 insertions(+), 15 deletions(-)
+ rename Documentation/filesystems/{ => fuse}/fuse-io-uring.rst (100%)
+ rename Documentation/filesystems/{ => fuse}/fuse-io.rst (99%)
+ rename Documentation/filesystems/{ => fuse}/fuse-passthrough.rst (100%)
+ rename Documentation/filesystems/{ => fuse}/fuse.rst (95%)
+ create mode 100644 Documentation/filesystems/fuse/index.rst
+ create mode 100644 tools/testing/selftests/filesystems/fuse/.gitignore
+ create mode 100644 tools/testing/selftests/filesystems/fuse/Makefile
+ create mode 100644 tools/testing/selftests/filesystems/fuse/fuse_mnt.c
+ create mode 100644 tools/testing/selftests/filesystems/fuse/fusectl_test.c
+Merging gfs2/for-next (a90f1b6ad664 Merge tag 'gfs2-for-6.17' of git://git.kernel.org/pub/scm/linux/kernel/git/gfs2/linux-gfs2)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/gfs2/linux-gfs2.git gfs2/for-next
+Already up to date.
+Merging jfs/jfs-next (856db3759202 jfs: fix metapage reference count leak in dbAllocCtl)
+$ git merge -m Merge branch 'jfs-next' of git://github.com/kleikamp/linux-shaggy.git jfs/jfs-next
+Already up to date.
+Merging ksmbd/ksmbd-for-next (e5cf61fa6e2f Merge tag 'v6.17-rc-smb3-server-fixes' of git://git.samba.org/ksmbd)
+$ git merge -m Merge branch 'ksmbd-for-next' of https://github.com/smfrench/smb3-kernel.git ksmbd/ksmbd-for-next
+Already up to date.
+Merging nfs/linux-next (99765233ab42 NFS: Fixup allocation flags for nfsiod's __GFP_NORETRY)
+$ git merge -m Merge branch 'linux-next' of git://git.linux-nfs.org/projects/trondmy/nfs-2.6.git nfs/linux-next
+Auto-merging fs/nfs/internal.h
+Auto-merging fs/nfs/nfs4file.c
+Auto-merging fs/nfs/write.c
+Auto-merging include/linux/sunrpc/xdr.h
+Auto-merging net/sunrpc/xdr.c
+Merge made by the 'ort' strategy.
+ fs/nfs/blocklayout/blocklayout.c | 4 +-
+ fs/nfs/blocklayout/dev.c | 5 +-
+ fs/nfs/blocklayout/extent_tree.c | 104 +++++++++++++++---
+ fs/nfs/client.c | 3 +-
+ fs/nfs/delegation.c | 114 ++++++++++++--------
+ fs/nfs/delegation.h | 3 +
+ fs/nfs/dir.c | 4 +-
+ fs/nfs/export.c | 11 +-
+ fs/nfs/flexfilelayout/flexfilelayout.c | 26 +++--
+ fs/nfs/flexfilelayout/flexfilelayoutdev.c | 6 +-
+ fs/nfs/fs_context.c | 42 ++++++++
+ fs/nfs/inode.c | 69 +++++++++++-
+ fs/nfs/internal.h | 10 +-
+ fs/nfs/mount_clnt.c | 68 ------------
+ fs/nfs/nfs4client.c | 165 ++++++++++++++---------------
+ fs/nfs/nfs4file.c | 25 +----
+ fs/nfs/nfs4proc.c | 50 +++++++--
+ fs/nfs/nfs4trace.c | 2 +
+ fs/nfs/nfs4trace.h | 168 +++++++++++++++++++++++++++++-
+ fs/nfs/nfs4xdr.c | 24 +++++
+ fs/nfs/nfstrace.h | 11 +-
+ fs/nfs/pnfs.c | 39 ++++---
+ fs/nfs/pnfs_nfs.c | 14 ++-
+ fs/nfs/write.c | 8 +-
+ include/linux/nfs_fs.h | 8 ++
+ include/linux/nfs_fs_sb.h | 8 +-
+ include/linux/nfs_xdr.h | 57 +++++-----
+ include/linux/sunrpc/xdr.h | 9 --
+ net/sunrpc/auth_gss/gss_krb5_crypto.c | 4 +-
+ net/sunrpc/xdr.c | 110 -------------------
+ 30 files changed, 715 insertions(+), 456 deletions(-)
+Merging nfs-anna/linux-next (38074de35b01 NFSv4/flexfiles: Fix handling of NFS level errors in I/O)
+$ git merge -m Merge branch 'linux-next' of git://git.linux-nfs.org/projects/anna/linux-nfs.git nfs-anna/linux-next
+Already up to date.
+Merging nfsd/nfsd-next (e339967eecf1 nfsd: Drop dprintk in blocklayout xdr functions)
+$ git merge -m Merge branch 'nfsd-next' of git://git.kernel.org/pub/scm/linux/kernel/git/cel/linux nfsd/nfsd-next
+Already up to date.
+Merging ntfs3/master (a49f0abd8959 Revert "fs/ntfs3: Replace inode_trylock with inode_lock")
+$ git merge -m Merge branch 'master' of https://github.com/Paragon-Software-Group/linux-ntfs3.git ntfs3/master
+Already up to date.
+Merging orangefs/for-next (2138e89cb066 fs/orangefs: Allow 2 more characters in do_c_string())
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/hubcap/linux orangefs/for-next
+Already up to date.
+Merging overlayfs/overlayfs-next (6f9ccdad0fea ovl: Annotate struct ovl_entry with __counted_by())
+$ git merge -m Merge branch 'overlayfs-next' of git://git.kernel.org/pub/scm/linux/kernel/git/overlayfs/vfs.git overlayfs/overlayfs-next
+Already up to date.
+Merging ubifs/next (99dbb2a1bd66 ubifs: stop using write_cache_pages)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/rw/ubifs.git ubifs/next
+Already up to date.
+Merging v9fs/9p-next (4210030d8bc4 docs: fs/9p: Add missing "not" in cache documentation)
+$ git merge -m Merge branch '9p-next' of git://github.com/martinetd/linux v9fs/9p-next
+Already up to date.
+Merging v9fs-ericvh/ericvh/for-next (2014c95afece Linux 6.14-rc1)
+$ git merge -m Merge branch 'ericvh/for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/ericvh/v9fs.git v9fs-ericvh/ericvh/for-next
+Already up to date.
+Merging xfs/for-next (ded74fddcaf6 xfs: don't use a xfs_log_iovec for ri_buf in log recovery)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/fs/xfs/xfs-linux.git xfs/for-next
+Already up to date.
+Merging zonefs/for-next (6982100bb829 zonefs: use ZONEFS_SUPER_SIZE instead of PAGE_SIZE)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/dlemoal/zonefs.git zonefs/for-next
+Already up to date.
+Merging vfs-brauner/vfs.all (66639db85811 Merge branch 'vfs-6.17.iomap' into vfs.all)
+$ git merge -m Merge branch 'vfs.all' of git://git.kernel.org/pub/scm/linux/kernel/git/vfs/vfs.git vfs-brauner/vfs.all
+Auto-merging Documentation/filesystems/porting.rst
+CONFLICT (content): Merge conflict in Documentation/filesystems/porting.rst
+Auto-merging fs/coredump.c
+CONFLICT (content): Merge conflict in fs/coredump.c
+Auto-merging fs/fuse/file.c
+Auto-merging net/unix/af_unix.c
+Auto-merging tools/testing/selftests/coredump/stackdump_test.c
+CONFLICT (content): Merge conflict in tools/testing/selftests/coredump/stackdump_test.c
+Resolved 'Documentation/filesystems/porting.rst' using previous resolution.
+Resolved 'fs/coredump.c' using previous resolution.
+Resolved 'tools/testing/selftests/coredump/stackdump_test.c' using previous resolution.
+Automatic merge failed; fix conflicts and then commit the result.
+$ git commit --no-edit -v -a
+[fs-next 3eae920dc7dd] Merge branch 'vfs.all' of git://git.kernel.org/pub/scm/linux/kernel/git/vfs/vfs.git
+$ git diff -M --stat --summary HEAD^..
+
+Merging vfs/for-next (dd589648208a Merge branch 'work.mount' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs.git vfs/for-next
+Auto-merging Documentation/filesystems/porting.rst
+CONFLICT (content): Merge conflict in Documentation/filesystems/porting.rst
+Resolved 'Documentation/filesystems/porting.rst' using previous resolution.
+Automatic merge failed; fix conflicts and then commit the result.
+$ git commit --no-edit -v -a
+[fs-next 0264e7f5188b] Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs.git
+$ git diff -M --stat --summary HEAD^..
+
+Merging mm-hotfixes/mm-hotfixes-unstable (415d5ad37461 mm/kmemleak: avoid soft lockup in __kmemleak_do_cleanup())
+$ git merge -m Merge branch 'mm-hotfixes-unstable' of git://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm mm-hotfixes/mm-hotfixes-unstable
+Auto-merging MAINTAINERS
+Auto-merging mm/debug_vm_pgtable.c
+Auto-merging mm/kasan/kasan_test_c.c
+Auto-merging mm/memory_hotplug.c
+Auto-merging mm/userfaultfd.c
+Merge made by the 'ort' strategy.
+ MAINTAINERS | 1 +
+ mm/debug_vm_pgtable.c | 9 +++++++--
+ mm/kasan/kasan_test_c.c | 4 +++-
+ mm/kmemleak.c | 10 +++++++++-
+ mm/memory_hotplug.c | 21 +++++++++++++--------
+ mm/userfaultfd.c | 9 +++++++--
+ 6 files changed, 40 insertions(+), 14 deletions(-)
+Merging fs-current (7d46dcab452b Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs.git)
+$ git merge -m Merge branch 'fs-current' of linux-next fs-current
+Merge made by the 'ort' strategy.
+ drivers/accel/habanalabs/common/memory.c | 23 +++++++----------------
+ 1 file changed, 7 insertions(+), 16 deletions(-)
+Merging kbuild-current/fixes (e04c78d86a96 Linux 6.16-rc2)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/masahiroy/linux-kbuild.git kbuild-current/fixes
+Already up to date.
+Merging arc-current/for-curr (d7b8f8e20813 Linux 6.16-rc5)
+$ git merge -m Merge branch 'for-curr' of git://git.kernel.org/pub/scm/linux/kernel/git/vgupta/arc.git arc-current/for-curr
+Already up to date.
+Merging arm-current/fixes (0c66c6f4e21c ARM: 9359/1: flush: check if the folio is reserved for no-mapping addresses)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/rmk/linux.git arm-current/fixes
+Already up to date.
+Merging arm64-fixes/for-next/fixes (d42e6c20de61 arm64/entry: Mask DAIF in cpu_switch_to(), call_on_irq_stack())
+$ git merge -m Merge branch 'for-next/fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/arm64/linux arm64-fixes/for-next/fixes
+Already up to date.
+Merging arm-soc-fixes/arm/fixes (9f9d41d64322 Merge tag 'arm-soc/for-6.17/drivers-part2' of https://github.com/Broadcom/stblinux into arm/fixes)
+$ git merge -m Merge branch 'arm/fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/soc/soc.git arm-soc-fixes/arm/fixes
+Merge made by the 'ort' strategy.
+ arch/arm/boot/dts/broadcom/bcm7445.dtsi | 9 +-
+ arch/arm/mach-s3c/gpio-samsung.c | 2 +-
+ drivers/clk/clk-rp1.c | 976 ++++++++++++++++++++-
+ include/dt-bindings/clock/raspberrypi,rp1-clocks.h | 4 +
+ 4 files changed, 979 insertions(+), 12 deletions(-)
+Merging davinci-current/davinci/for-current (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'davinci/for-current' of git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git davinci-current/davinci/for-current
+Already up to date.
+Merging drivers-memory-fixes/fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'fixes' of https://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux-mem-ctrl.git drivers-memory-fixes/fixes
+Already up to date.
+Merging sophgo-fixes/fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'fixes' of https://github.com/sophgo/linux.git sophgo-fixes/fixes
+Already up to date.
+Merging sophgo-soc-fixes/soc-fixes (0af2f6be1b42 Linux 6.15-rc1)
+$ git merge -m Merge branch 'soc-fixes' of https://github.com/sophgo/linux.git sophgo-soc-fixes/soc-fixes
+Already up to date.
+Merging m68k-current/for-linus (c8995932db2b m68k: mac: Improve clocksource driver commentary)
+$ git merge -m Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/geert/linux-m68k.git m68k-current/for-linus
+Already up to date.
+Merging powerpc-fixes/fixes (ab107276607a powerpc: Fix struct termio related ioctl macros)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/powerpc/linux.git powerpc-fixes/fixes
+Already up to date.
+Merging s390-fixes/fixes (62355f1f87b8 s390/pci: Allow automatic recovery with minimal driver support)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/s390/linux.git s390-fixes/fixes
+Already up to date.
+Merging net/main (1dbf1d590d10 net: Add locking to protect skb->dev access in ip_output)
+$ git merge -m Merge branch 'main' of git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net.git net/main
+Merge made by the 'ort' strategy.
+ Documentation/netlink/specs/ethtool.yaml | 6 ++---
+ drivers/dpll/zl3073x/Kconfig | 10 ++++-----
+ drivers/net/ethernet/airoha/airoha_ppe.c | 26 +++++++++++++++++-----
+ drivers/net/ethernet/freescale/dpaa/dpaa_ethtool.c | 4 +++-
+ drivers/net/ethernet/freescale/enetc/enetc_pf.c | 14 ++++++++++--
+ drivers/net/ethernet/freescale/gianfar_ethtool.c | 4 +++-
+ drivers/net/ethernet/mediatek/mtk_wed.c | 1 -
+ drivers/net/ethernet/mellanox/mlx5/core/en_rx.c | 1 +
+ drivers/net/ethernet/sfc/tc_encap_actions.c | 2 +-
+ drivers/net/ethernet/ti/icssg/icss_iep.c | 23 ++++++++++++++-----
+ drivers/net/ipa/ipa_sysfs.c | 6 ++++-
+ drivers/net/mdio/mdio-bcm-unimac.c | 5 ++---
+ drivers/net/phy/mdio_bus.c | 4 ++--
+ drivers/net/phy/mscc/mscc_ptp.c | 1 +
+ drivers/net/phy/mscc/mscc_ptp.h | 1 +
+ drivers/net/phy/smsc.c | 1 +
+ drivers/net/ppp/pptp.c | 15 ++++++++-----
+ include/linux/skbuff.h | 23 +++++++++++++++++++
+ include/net/dst.h | 12 ++++++++++
+ include/net/udp.h | 24 +++++++++++++++-----
+ net/core/netpoll.c | 7 ++++++
+ net/ipv4/ip_output.c | 15 ++++++++-----
+ net/ipv6/ip6_offload.c | 4 +++-
+ net/kcm/kcmsock.c | 6 +++++
+ net/netlink/af_netlink.c | 2 +-
+ net/sched/sch_taprio.c | 21 ++++++++++++++---
+ tools/testing/selftests/net/test_neigh.sh | 6 ++---
+ tools/testing/selftests/net/vlan_hw_filter.sh | 16 ++++++-------
+ 28 files changed, 196 insertions(+), 64 deletions(-)
+Merging bpf/master (1b30d4441727 bpf: Fix memory leak of bpf_scc_info objects)
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/bpf/bpf.git bpf/master
+Merge made by the 'ort' strategy.
+ kernel/bpf/verifier.c | 3 +++
+ 1 file changed, 3 insertions(+)
+Merging ipsec/master (28712d6ed320 Merge branch 'ipsec: fix splat due to ipcomp fallback tunnel')
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/klassert/ipsec.git ipsec/master
+Already up to date.
+Merging netfilter/main (eccf7a3480a0 Merge tag 'linux-can-fixes-for-6.16-20250725' of git://git.kernel.org/pub/scm/linux/kernel/git/mkl/linux-can)
+$ git merge -m Merge branch 'main' of git://git.kernel.org/pub/scm/linux/kernel/git/netfilter/nf.git netfilter/main
+Already up to date.
+Merging ipvs/main (eccf7a3480a0 Merge tag 'linux-can-fixes-for-6.16-20250725' of git://git.kernel.org/pub/scm/linux/kernel/git/mkl/linux-can)
+$ git merge -m Merge branch 'main' of git://git.kernel.org/pub/scm/linux/kernel/git/horms/ipvs.git ipvs/main
+Already up to date.
+Merging wireless/for-next (6832a9317eee Merge tag 'net-6.16-rc7' of git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/wireless/wireless.git wireless/for-next
+Already up to date.
+Merging ath/for-current (d9104cec3e8f Merge tag 'bpf-next-6.17' of git://git.kernel.org/pub/scm/linux/kernel/git/bpf/bpf-next)
+$ git merge -m Merge branch 'for-current' of git://git.kernel.org/pub/scm/linux/kernel/git/ath/ath.git ath/for-current
+Already up to date.
+Merging iwlwifi/fixes (6832a9317eee Merge tag 'net-6.16-rc7' of git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net)
+$ git merge -m Merge branch 'fixes' of https://git.kernel.org/pub/scm/linux/kernel/git/iwlwifi/iwlwifi-next.git iwlwifi/fixes
+Already up to date.
+Merging wpan/master (8ce4f287524c net: libwx: fix firmware mailbox abnormal return)
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/wpan/wpan.git wpan/master
+Already up to date.
+Merging rdma-fixes/for-rc (a9a9e68954f2 RDMA/mlx5: Fix vport loopback for MPV device)
+$ git merge -m Merge branch 'for-rc' of git://git.kernel.org/pub/scm/linux/kernel/git/rdma/rdma.git rdma-fixes/for-rc
+Already up to date.
+Merging sound-current/for-linus (dbe05428c4e5 ALSA: hda/realtek: add LG gram 16Z90R-A to alc269 fixup table)
+$ git merge -m Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tiwai/sound.git sound-current/for-linus
+Merge made by the 'ort' strategy.
+ sound/hda/codecs/realtek/alc269.c | 1 +
+ sound/usb/pcm.c | 9 ++++-----
+ 2 files changed, 5 insertions(+), 5 deletions(-)
+Merging sound-asoc-fixes/for-linus (282528da82a0 Merge remote-tracking branch 'asoc/for-6.16' into asoc-linus)
+$ git merge -m Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/broonie/sound.git sound-asoc-fixes/for-linus
+Merge made by the 'ort' strategy.
+ drivers/spi/spi-cs42l43.c | 2 +-
+ sound/soc/codecs/wm8962.c | 11 +++++++++++
+ sound/soc/intel/avs/core.c | 3 ++-
+ sound/soc/sof/amd/acp-loader.c | 6 +++---
+ 4 files changed, 17 insertions(+), 5 deletions(-)
+Merging regmap-fixes/for-linus (067aa458a064 Merge remote-tracking branch 'regmap/for-6.16' into regmap-linus)
+$ git merge -m Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/broonie/regmap.git regmap-fixes/for-linus
+Merge made by the 'ort' strategy.
+ drivers/base/regmap/regmap-irq.c | 30 +++++++++++++++++++++---------
+ 1 file changed, 21 insertions(+), 9 deletions(-)
+Merging regulator-fixes/for-linus (10dfd36f0784 regulator: core: correct convergence check in regulator_set_voltage())
+$ git merge -m Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/broonie/regulator.git regulator-fixes/for-linus
+Merge made by the 'ort' strategy.
+ drivers/regulator/core.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+Merging spi-fixes/for-linus (a49bfbecfde7 Merge remote-tracking branch 'spi/for-6.16' into spi-linus)
+$ git merge -m Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/broonie/spi.git spi-fixes/for-linus
+Auto-merging MAINTAINERS
+Merge made by the 'ort' strategy.
+ MAINTAINERS | 8 ++++++++
+ 1 file changed, 8 insertions(+)
+Merging pci-current/for-linus (0bd0a41a5120 Merge tag 'pci-v6.17-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/pci/pci)
+$ git merge -m Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/pci/pci.git pci-current/for-linus
+Already up to date.
+Merging driver-core.current/driver-core-linus (d632ab86aff2 Merge tag 'for-6.17/dm-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/device-mapper/linux-dm)
+$ git merge -m Merge branch 'driver-core-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/driver-core/driver-core.git driver-core.current/driver-core-linus
+Already up to date.
+Merging tty.current/tty-linus (55a984928bfa Revert "tty: vt: use _IO() to define ioctl numbers")
+$ git merge -m Merge branch 'tty-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/tty.git tty.current/tty-linus
+Merge made by the 'ort' strategy.
+ include/uapi/linux/vt.h | 34 +++++++++++++++++-----------------
+ 1 file changed, 17 insertions(+), 17 deletions(-)
+Merging usb.current/usb-linus (d632ab86aff2 Merge tag 'for-6.17/dm-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/device-mapper/linux-dm)
+$ git merge -m Merge branch 'usb-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/usb.git usb.current/usb-linus
+Already up to date.
+Merging usb-serial-fixes/usb-linus (ad1244e1ce18 USB: serial: option: add Foxconn T99W709)
+$ git merge -m Merge branch 'usb-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/johan/usb-serial.git usb-serial-fixes/usb-linus
+Already up to date.
+Merging phy/fixes (89be9a83ccf1 Linux 6.16-rc7)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/phy/linux-phy.git phy/fixes
+Already up to date.
+Merging staging.current/staging-linus (d632ab86aff2 Merge tag 'for-6.17/dm-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/device-mapper/linux-dm)
+$ git merge -m Merge branch 'staging-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/staging.git staging.current/staging-linus
+Already up to date.
+Merging iio-fixes/fixes-togreg (187d5553e33e iio: adc: ad7124: fix channel lookup in syscalib functions)
+$ git merge -m Merge branch 'fixes-togreg' of git://git.kernel.org/pub/scm/linux/kernel/git/jic23/iio.git iio-fixes/fixes-togreg
+Merge made by the 'ort' strategy.
+ drivers/iio/accel/sca3300.c | 2 +-
+ drivers/iio/adc/ad7124.c | 14 ++---
+ drivers/iio/adc/ad7173.c | 87 ++++++++++++++++++++++++----
+ drivers/iio/proximity/isl29501.c | 14 +++--
+ drivers/iio/temperature/maxim_thermocouple.c | 26 +++++----
+ 5 files changed, 109 insertions(+), 34 deletions(-)
+Merging counter-current/counter-current (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'counter-current' of git://git.kernel.org/pub/scm/linux/kernel/git/wbg/counter.git counter-current/counter-current
+Already up to date.
+Merging char-misc.current/char-misc-linus (d632ab86aff2 Merge tag 'for-6.17/dm-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/device-mapper/linux-dm)
+$ git merge -m Merge branch 'char-misc-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/char-misc.git char-misc.current/char-misc-linus
+Already up to date.
+Merging soundwire-fixes/fixes (89be9a83ccf1 Linux 6.16-rc7)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/vkoul/soundwire.git soundwire-fixes/fixes
+Already up to date.
+Merging thunderbolt-fixes/fixes (038d61fd6422 Linux 6.16)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/westeri/thunderbolt.git thunderbolt-fixes/fixes
+Already up to date.
+Merging input-current/for-linus (bcce05041b21 Input: xpad - set correct controller type for Acer NGR200)
+$ git merge -m Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/dtor/input.git input-current/for-linus
+Already up to date.
+Merging crypto-current/master (9d9b193ed73a crypto: hash - Increase HASH_MAX_DESCSIZE for hmac(sha3-224-s390))
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/herbert/crypto-2.6.git crypto-current/master
+Auto-merging include/crypto/hash.h
+Merge made by the 'ort' strategy.
+ include/crypto/hash.h | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+Merging libcrypto-fixes/libcrypto-fixes (68279380266a crypto: s390/sha - Fix uninitialized variable in SHA-1 and SHA-2)
+$ git merge -m Merge branch 'libcrypto-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/ebiggers/linux.git libcrypto-fixes/libcrypto-fixes
+Already up to date.
+Merging vfio-fixes/for-linus (c1d9dac0db16 vfio/pci: Align huge faults to order)
+$ git merge -m Merge branch 'for-linus' of git://github.com/awilliam/linux-vfio.git vfio-fixes/for-linus
+Already up to date.
+Merging kselftest-fixes/fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux-kselftest.git kselftest-fixes/fixes
+Already up to date.
+Merging dmaengine-fixes/fixes (89be9a83ccf1 Linux 6.16-rc7)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/vkoul/dmaengine.git dmaengine-fixes/fixes
+Already up to date.
+Merging backlight-fixes/for-backlight-fixes (1613e604df0c Linux 6.10-rc1)
+$ git merge -m Merge branch 'for-backlight-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/lee/backlight.git backlight-fixes/for-backlight-fixes
+Already up to date.
+Merging mtd-fixes/mtd/fixes (6463cbe08b0c mtd: spinand: fix memory leak of ECC engine conf)
+$ git merge -m Merge branch 'mtd/fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/mtd/linux.git mtd-fixes/mtd/fixes
+Already up to date.
+Merging mfd-fixes/for-mfd-fixes (d9d79e4f7dc9 mfd: Fix building without CONFIG_OF)
+$ git merge -m Merge branch 'for-mfd-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/lee/mfd.git mfd-fixes/for-mfd-fixes
+Already up to date.
+Merging v4l-dvb-fixes/fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'fixes' of git://linuxtv.org/media-ci/media-pending.git v4l-dvb-fixes/fixes
+Already up to date.
+Merging reset-fixes/reset/fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'reset/fixes' of https://git.pengutronix.de/git/pza/linux reset-fixes/reset/fixes
+Already up to date.
+Merging mips-fixes/mips-fixes (86731a2a651e Linux 6.16-rc3)
+$ git merge -m Merge branch 'mips-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/mips/linux.git mips-fixes/mips-fixes
+Already up to date.
+Merging at91-fixes/at91-fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'at91-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/at91/linux.git at91-fixes/at91-fixes
+Already up to date.
+Merging omap-fixes/fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/khilman/linux-omap.git omap-fixes/fixes
+Already up to date.
+Merging kvm-fixes/master (038d61fd6422 Linux 6.16)
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/virt/kvm/kvm.git kvm-fixes/master
+Already up to date.
+Merging kvms390-fixes/master (d8dfda5af0be KVM: s390: pv: fix race when making a page secure)
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/kvms390/linux.git kvms390-fixes/master
+Already up to date.
+Merging hwmon-fixes/hwmon (9c62e2282900 hwmon: (gsc-hwmon) fix fan pwm setpoint show functions)
+$ git merge -m Merge branch 'hwmon' of git://git.kernel.org/pub/scm/linux/kernel/git/groeck/linux-staging.git hwmon-fixes/hwmon
+Already up to date.
+Merging nvdimm-fixes/libnvdimm-fixes (d0b3b7b22dfa Linux 6.16-rc4)
+$ git merge -m Merge branch 'libnvdimm-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/nvdimm/nvdimm.git nvdimm-fixes/libnvdimm-fixes
+Already up to date.
+Merging cxl-fixes/fixes (d0b3b7b22dfa Linux 6.16-rc4)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/cxl/cxl.git cxl-fixes/fixes
+Already up to date.
+Merging dma-mapping-fixes/dma-mapping-fixes (aa807b9f22df dma-contiguous: hornor the cma address limit setup by user)
+$ git merge -m Merge branch 'dma-mapping-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/mszyprowski/linux.git dma-mapping-fixes/dma-mapping-fixes
+Already up to date.
+Merging drivers-x86-fixes/fixes (e2967b50b709 MAINTAINERS: Update entries for IFS and SBL drivers)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/pdx86/platform-drivers-x86.git drivers-x86-fixes/fixes
+Already up to date.
+Merging samsung-krzk-fixes/fixes (8d2c2fa2209e firmware: exynos-acpm: fix timeouts on xfers handling)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux.git samsung-krzk-fixes/fixes
+Already up to date.
+Merging pinctrl-samsung-fixes/fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/pinctrl/samsung.git pinctrl-samsung-fixes/fixes
+Already up to date.
+Merging devicetree-fixes/dt/linus (79aef1a3705b of: Clarify OF device context in of_match_device() comment)
+$ git merge -m Merge branch 'dt/linus' of git://git.kernel.org/pub/scm/linux/kernel/git/robh/linux.git devicetree-fixes/dt/linus
+Merge made by the 'ort' strategy.
+ drivers/of/device.c | 4 ++--
+ 1 file changed, 2 insertions(+), 2 deletions(-)
+Merging dt-krzk-fixes/fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux-dt.git dt-krzk-fixes/fixes
+Already up to date.
+Merging scsi-fixes/fixes (021f243627ea scsi: ufs: core: Fix spelling of a sysfs attribute name)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/mkp/scsi.git scsi-fixes/fixes
+Already up to date.
+Merging drm-fixes/drm-fixes (038d61fd6422 Linux 6.16)
+$ git merge -m Merge branch 'drm-fixes' of https://gitlab.freedesktop.org/drm/kernel.git drm-fixes/drm-fixes
+Already up to date.
+Merging drm-intel-fixes/for-linux-next-fixes (038d61fd6422 Linux 6.16)
+$ git merge -m Merge branch 'for-linux-next-fixes' of https://gitlab.freedesktop.org/drm/i915/kernel drm-intel-fixes/for-linux-next-fixes
+Already up to date.
+Merging mmc-fixes/fixes (4b290aae788e Merge tag 'sysctl-6.17-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/sysctl/sysctl)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/ulfh/mmc.git mmc-fixes/fixes
+Already up to date.
+Merging rtc-fixes/rtc-fixes (08d82d0cad51 rtc: pcf2127: add missing semicolon after statement)
+$ git merge -m Merge branch 'rtc-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/abelloni/linux.git rtc-fixes/rtc-fixes
+Already up to date.
+Merging gnss-fixes/gnss-linus (86731a2a651e Linux 6.16-rc3)
+$ git merge -m Merge branch 'gnss-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/johan/gnss.git gnss-fixes/gnss-linus
+Already up to date.
+Merging hyperv-fixes/hyperv-fixes (a4131a50d072 tools/hv: fcopy: Fix irregularities with size of ring buffer)
+$ git merge -m Merge branch 'hyperv-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/hyperv/linux.git hyperv-fixes/hyperv-fixes
+Already up to date.
+Merging risc-v-fixes/fixes (b65ca21835ed riscv: uaccess: Fix -Wuninitialized and -Wshadow in __put_user_nocheck)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/riscv/linux.git risc-v-fixes/fixes
+Already up to date.
+Merging riscv-dt-fixes/riscv-dt-fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'riscv-dt-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/conor/linux.git riscv-dt-fixes/riscv-dt-fixes
+Already up to date.
+Merging riscv-soc-fixes/riscv-soc-fixes (0af2f6be1b42 Linux 6.15-rc1)
+$ git merge -m Merge branch 'riscv-soc-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/conor/linux.git riscv-soc-fixes/riscv-soc-fixes
+Already up to date.
+Merging fpga-fixes/fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/fpga/linux-fpga.git fpga-fixes/fixes
+Already up to date.
+Merging spdx/spdx-linus (beb6c8326eb4 Merge tag 'uml-for-linux-6.17-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/uml/linux)
+$ git merge -m Merge branch 'spdx-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/spdx.git spdx/spdx-linus
+Already up to date.
+Merging gpio-brgl-fixes/gpio/for-current (89be9a83ccf1 Linux 6.16-rc7)
+$ git merge -m Merge branch 'gpio/for-current' of git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git gpio-brgl-fixes/gpio/for-current
+Already up to date.
+Merging gpio-intel-fixes/fixes (9ab29ed50555 gpiolib: acpi: Add a quirk for Acer Nitro V15)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/andy/linux-gpio-intel.git gpio-intel-fixes/fixes
+Already up to date.
+Merging pinctrl-intel-fixes/fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/pinctrl/intel.git pinctrl-intel-fixes/fixes
+Already up to date.
+Merging auxdisplay-fixes/fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/andy/linux-auxdisplay.git auxdisplay-fixes/fixes
+Already up to date.
+Merging kunit-fixes/kunit-fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'kunit-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux-kselftest.git kunit-fixes/kunit-fixes
+Already up to date.
+Merging memblock-fixes/fixes (da8bf5daa5e5 memblock: Accept allocated memory before use in memblock_double_array())
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/rppt/memblock.git memblock-fixes/fixes
+Already up to date.
+Merging renesas-fixes/fixes (379c590113ce ARM: shmobile: smp: Enforce shmobile_smp_* alignment)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/geert/renesas-devel.git renesas-fixes/fixes
+Already up to date.
+Merging perf-current/perf-tools (6235ce77749f perf record: Cache build-ID of hit DSOs only)
+$ git merge -m Merge branch 'perf-tools' of git://git.kernel.org/pub/scm/linux/kernel/git/perf/perf-tools perf-current/perf-tools
+Already up to date.
+Merging efi-fixes/urgent (64e135f1eaba efivarfs: Fix memory leak of efivarfs_fs_info in fs_context error paths)
+$ git merge -m Merge branch 'urgent' of git://git.kernel.org/pub/scm/linux/kernel/git/efi/efi.git efi-fixes/urgent
+Already up to date.
+Merging battery-fixes/fixes (0af2f6be1b42 Linux 6.15-rc1)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/sre/linux-power-supply.git battery-fixes/fixes
+Already up to date.
+Merging iommufd-fixes/for-rc (9a96876e3c65 iommufd/selftest: Fix build warnings due to uninitialized mfd)
+$ git merge -m Merge branch 'for-rc' of git://git.kernel.org/pub/scm/linux/kernel/git/jgg/iommufd.git iommufd-fixes/for-rc
+Already up to date.
+Merging rust-fixes/rust-fixes (d2eedaa3909b Merge tag 'rtc-6.17' of git://git.kernel.org/pub/scm/linux/kernel/git/abelloni/linux)
+$ git merge -m Merge branch 'rust-fixes' of https://github.com/Rust-for-Linux/linux.git rust-fixes/rust-fixes
+Already up to date.
+Merging w1-fixes/fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux-w1.git w1-fixes/fixes
+Already up to date.
+Merging pmdomain-fixes/fixes (621a88dbfe90 cpuidle: psci: Fix cpuhotplug routine with PREEMPT_RT=y)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/ulfh/linux-pm.git pmdomain-fixes/fixes
+Already up to date.
+Merging i2c-host-fixes/i2c/i2c-host-fixes (0ae982df6776 Merge tag 'i2c-for-6.17-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/wsa/linux)
+$ git merge -m Merge branch 'i2c/i2c-host-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/andi.shyti/linux.git i2c-host-fixes/i2c/i2c-host-fixes
+Already up to date.
+Merging sparc-fixes/for-linus (6613476e225e Linux 6.8-rc1)
+$ git merge -m Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/alarsson/linux-sparc.git sparc-fixes/for-linus
+Already up to date.
+Merging clk-fixes/clk-fixes (e4b2a0c2b9be Merge tag 'sunxi-clk-fixes-for-6.16' of https://git.kernel.org/pub/scm/linux/kernel/git/sunxi/linux into clk-fixes)
+$ git merge -m Merge branch 'clk-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/clk/linux.git clk-fixes/clk-fixes
+Already up to date.
+Merging thead-clk-fixes/thead-clk-fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'thead-clk-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/fustini/linux.git thead-clk-fixes/thead-clk-fixes
+Already up to date.
+Merging pwrseq-fixes/pwrseq/for-current (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'pwrseq/for-current' of git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git pwrseq-fixes/pwrseq/for-current
+Already up to date.
+Merging thead-dt-fixes/thead-dt-fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'thead-dt-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/fustini/linux.git thead-dt-fixes/thead-dt-fixes
+Already up to date.
+Merging ftrace-fixes/ftrace/fixes (327e28664307 fgraph: Do not enable function_graph tracer when setting funcgraph-args)
+$ git merge -m Merge branch 'ftrace/fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git ftrace-fixes/ftrace/fixes
+Already up to date.
+Merging ring-buffer-fixes/ring-buffer/fixes (e4d4b8670c44 ring-buffer: Use flush_kernel_vmap_range() over flush_dcache_folio())
+$ git merge -m Merge branch 'ring-buffer/fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git ring-buffer-fixes/ring-buffer/fixes
+Already up to date.
+Merging trace-fixes/trace/fixes (b5e8acc14dcb tracing: Add down_write(trace_event_sem) when adding trace event)
+$ git merge -m Merge branch 'trace/fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git trace-fixes/trace/fixes
+Already up to date.
+Merging tracefs-fixes/tracefs/fixes (8b55572e5180 tracing/selftests: Add tracefs mount options test)
+$ git merge -m Merge branch 'tracefs/fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git tracefs-fixes/tracefs/fixes
+Already up to date.
+Merging spacemit-fixes/fixes (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'fixes' of https://github.com/spacemit-com/linux spacemit-fixes/fixes
+Already up to date.
+Merging tip-fixes/tip/urgent (f88a000d5409 Merge branch into tip/master: 'x86/urgent')
+$ git merge -m Merge branch 'tip/urgent' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip.git tip-fixes/tip/urgent
+Auto-merging kernel/fork.c
+Merge made by the 'ort' strategy.
+ arch/x86/include/asm/hw_irq.h | 6 +--
+ arch/x86/include/asm/intel-family.h | 5 +++
+ arch/x86/kernel/irq.c | 63 +++++++++++++++++++++++-------
+ drivers/irqchip/irq-riscv-imsic-platform.c | 2 +-
+ kernel/fork.c | 2 +-
+ kernel/smp.c | 2 +-
+ 6 files changed, 59 insertions(+), 21 deletions(-)
+Merging slab-fixes/slab/for-next-fixes (be8250786ca9 mm, slab: clean up slab->obj_exts always)
+$ git merge -m Merge branch 'slab/for-next-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/vbabka/slab.git slab-fixes/slab/for-next-fixes
+Already up to date.
+Merging drm-msm-fixes/msm-fixes (8290d37ad2b0 drm/msm: Small function param doc fix)
+$ git merge -m Merge branch 'msm-fixes' of https://gitlab.freedesktop.org/drm/msm.git drm-msm-fixes/msm-fixes
+Already up to date.
+Merging uml-fixes/fixes (2dca89df0d11 Merge tag 'uml-for-6.16-rc4' of git://git.kernel.org/pub/scm/linux/kernel/git/uml/linux)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/uml/linux.git uml-fixes/fixes
+Already up to date.
+Merging fwctl-fixes/for-rc (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'for-rc' of git//git.kernel.org/pub/scm/linux/kernel/git/fwctl/fwctl.git fwctl-fixes/for-rc
+Already up to date.
+Merging devsec-tsm-fixes/fixes (fba4ceaa242d configfs-tsm-report: Fix NULL dereference of tsm_ops)
+$ git merge -m Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/devsec/tsm.git devsec-tsm-fixes/fixes
+Already up to date.
+Merging drm-misc-fixes/for-linux-next-fixes (038d61fd6422 Linux 6.16)
+$ git merge -m Merge branch 'for-linux-next-fixes' of https://gitlab.freedesktop.org/drm/misc/kernel.git drm-misc-fixes/for-linux-next-fixes
+Already up to date.
+Merging linus/for-next (ffd294d346d1 Linux 6.13)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git linus/for-next
+Already up to date.
+Merging mm-stable/mm-stable (a2152fef2902 mm: mempool: fix crash in mempool_free() for zero-minimum pools)
+$ git merge -m Merge branch 'mm-stable' of git://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm mm-stable/mm-stable
+Auto-merging Documentation/core-api/mm-api.rst
+Auto-merging arch/x86/kernel/alternative.c
+Auto-merging include/linux/mm.h
+Auto-merging kernel/fork.c
+Auto-merging kernel/module/main.c
+Auto-merging mm/internal.h
+Auto-merging mm/memory-failure.c
+Auto-merging mm/nommu.c
+Auto-merging mm/shmem.c
+Auto-merging mm/vma.c
+Auto-merging tools/testing/vma/vma_internal.h
+Merge made by the 'ort' strategy.
+ Documentation/core-api/mm-api.rst | 1 -
+ arch/arm64/mm/mmu.c | 4 +-
+ arch/x86/kernel/alternative.c | 3 +-
+ arch/x86/kernel/ftrace.c | 2 +-
+ arch/x86/kernel/kprobes/core.c | 18 --
+ arch/x86/mm/init.c | 24 +-
+ include/linux/execmem.h | 54 ++--
+ include/linux/io-mapping.h | 3 -
+ include/linux/mm.h | 6 +-
+ include/linux/mmap_lock.h | 30 ++
+ include/linux/page-flags.h | 2 -
+ include/linux/pgtable.h | 45 +++
+ include/linux/rmap.h | 22 ++
+ kernel/fork.c | 9 +-
+ kernel/module/main.c | 13 +-
+ mm/Kconfig | 4 -
+ mm/Makefile | 1 -
+ mm/damon/vaddr.c | 4 +
+ mm/execmem.c | 212 +++++++++----
+ mm/internal.h | 2 +-
+ mm/io-mapping.c | 30 --
+ mm/kasan/common.c | 25 +-
+ mm/khugepaged.c | 58 ++--
+ mm/madvise.c | 71 ++++-
+ mm/memory-failure.c | 12 +-
+ mm/mempool.c | 24 +-
+ mm/mincore.c | 3 +
+ mm/mmap_lock.c | 10 +-
+ mm/mprotect.c | 2 +-
+ mm/mremap.c | 4 +-
+ mm/mseal.c | 170 +++-------
+ mm/nommu.c | 2 +-
+ mm/rmap.c | 2 +-
+ mm/shmem.c | 281 +++++++++--------
+ mm/vma.c | 4 +-
+ mm/vma.h | 27 +-
+ tools/testing/selftests/cachestat/test_cachestat.c | 62 +++-
+ tools/testing/selftests/mm/.gitignore | 1 +
+ tools/testing/selftests/mm/Makefile | 1 +
+ tools/testing/selftests/mm/process_madv.c | 344 +++++++++++++++++++++
+ tools/testing/selftests/mm/run_vmtests.sh | 5 +
+ tools/testing/vma/vma_internal.h | 6 +-
+ 42 files changed, 1086 insertions(+), 517 deletions(-)
+ delete mode 100644 mm/io-mapping.c
+ create mode 100644 tools/testing/selftests/mm/process_madv.c
+Merging mm-nonmm-stable/mm-nonmm-stable (085dece6cc88 tools/getdelays: add backward compatibility for taskstats version)
+$ git merge -m Merge branch 'mm-nonmm-stable' of git://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm mm-nonmm-stable/mm-nonmm-stable
+Already up to date.
+Merging mm-unstable/mm-unstable (66b994de3cf1 mm-filemap-align-last_index-to-folio-size-fix)
+$ git merge -m Merge branch 'mm-unstable' of git://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm mm-unstable/mm-unstable
+Auto-merging include/linux/pagemap.h
+Auto-merging mm/filemap.c
+Merge made by the 'ort' strategy.
+ include/linux/pagemap.h | 6 ++++++
+ mm/filemap.c | 5 +++--
+ 2 files changed, 9 insertions(+), 2 deletions(-)
+Merging mm-nonmm-unstable/mm-nonmm-unstable (021cf32328d6 selftests/mm: use __auto_type in swap() macro)
+$ git merge -m Merge branch 'mm-nonmm-unstable' of git://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm mm-nonmm-unstable/mm-nonmm-unstable
+Auto-merging fs/ocfs2/super.c
+Merge made by the 'ort' strategy.
+ Documentation/dev-tools/kcov.rst | 7 ++-
+ fs/ocfs2/ocfs2.h | 2 -
+ fs/ocfs2/super.c | 2 -
+ fs/ocfs2/sysfile.c | 9 ++--
+ kernel/hung_task.c | 78 +++++++++++++++++---------------
+ kernel/kcov.c | 9 ++++
+ tools/testing/selftests/mm/uffd-stress.c | 2 +-
+ 7 files changed, 60 insertions(+), 49 deletions(-)
+Merging kbuild/for-next (dae742fa564b kheaders: make it possible to override TAR)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/masahiroy/linux-kbuild.git kbuild/for-next
+Auto-merging Makefile
+Auto-merging arch/s390/kernel/vmlinux.lds.S
+Auto-merging drivers/pinctrl/meson/pinctrl-amlogic-a4.c
+Auto-merging include/asm-generic/vmlinux.lds.h
+Auto-merging include/linux/module.h
+Auto-merging include/linux/moduleparam.h
+CONFLICT (content): Merge conflict in include/linux/moduleparam.h
+Auto-merging include/net/tcp.h
+Auto-merging kernel/Makefile
+Auto-merging rust/kernel/device_id.rs
+Resolved 'include/linux/moduleparam.h' using previous resolution.
+Automatic merge failed; fix conflicts and then commit the result.
+$ git commit --no-edit -v -a
+[master 0299ce683b8c] Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/masahiroy/linux-kbuild.git
+$ git diff -M --stat --summary HEAD^..
+ Documentation/kbuild/kconfig.rst | 8 +-
+ Makefile | 5 +-
+ arch/s390/kernel/vmlinux.lds.S | 10 +-
+ drivers/pinctrl/meson/pinctrl-amlogic-a4.c | 2 +-
+ drivers/scsi/BusLogic.c | 2 -
+ include/asm-generic/vmlinux.lds.h | 2 +-
+ include/crypto/algapi.h | 4 +-
+ include/linux/module.h | 21 +-
+ include/linux/moduleparam.h | 9 +-
+ include/net/tcp.h | 4 +-
+ kernel/.gitignore | 2 +
+ kernel/Makefile | 47 +-
+ kernel/gen_kheaders.sh | 93 +-
+ rust/kernel/device_id.rs | 8 +-
+ scripts/Makefile.vmlinux | 77 +-
+ scripts/Makefile.vmlinux_o | 26 +-
+ scripts/extract-vmlinux | 13 +-
+ scripts/gendwarfksyms/cache.c | 2 +-
+ scripts/gendwarfksyms/die.c | 4 +-
+ scripts/gendwarfksyms/dwarf.c | 2 +-
+ scripts/gendwarfksyms/kabi.c | 2 +-
+ scripts/gendwarfksyms/symbols.c | 2 +-
+ scripts/gendwarfksyms/types.c | 33 +-
+ scripts/kconfig/conf.c | 2 +-
+ scripts/kconfig/confdata.c | 2 +-
+ scripts/kconfig/gconf-cfg.sh | 11 +-
+ scripts/kconfig/gconf.c | 1783 +++++++++++++---------------
+ scripts/kconfig/{gconf.glade => gconf.ui} | 361 ++----
+ scripts/kconfig/lkc.h | 2 +
+ scripts/kconfig/lxdialog/inputbox.c | 6 +-
+ scripts/kconfig/lxdialog/menubox.c | 2 +-
+ scripts/kconfig/lxdialog/util.c | 3 +-
+ scripts/kconfig/menu.c | 94 ++
+ scripts/kconfig/nconf.c | 2 +
+ scripts/kconfig/nconf.gui.c | 1 +
+ scripts/kconfig/qconf.cc | 36 +-
+ scripts/kconfig/qconf.h | 1 +
+ scripts/kconfig/symbol.c | 4 +
+ scripts/link-vmlinux.sh | 5 +-
+ scripts/mksysmap | 6 +
+ scripts/mod/file2alias.c | 34 +-
+ scripts/mod/modpost.c | 17 +-
+ scripts/mod/modpost.h | 2 +
+ 43 files changed, 1342 insertions(+), 1410 deletions(-)
+ rename scripts/kconfig/{gconf.glade => gconf.ui} (57%)
+$ git am -3 ../patches/kbuild__modpost__Fix_the_order_of_includes_in_.vmlinux.export.c.patch
+Applying: kbuild: modpost: Fix the order of includes in .vmlinux.export.c
+$ git reset HEAD^
+Unstaged changes after reset:
+M scripts/mod/modpost.c
+$ git add -A .
+$ git commit -v -a --amend
+[master ae6e3eb8ab69] Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/masahiroy/linux-kbuild.git
+ Date: Tue Aug 5 10:32:21 2025 +1000
+Merging clang-format/clang-format (c147f663b6a5 clang-format: Update with v6.11-rc1's `for_each` macro list)
+$ git merge -m Merge branch 'clang-format' of https://github.com/ojeda/linux.git clang-format/clang-format
+Already up to date.
+Merging perf/perf-tools-next (6235ce77749f perf record: Cache build-ID of hit DSOs only)
+$ git merge -m Merge branch 'perf-tools-next' of git://git.kernel.org/pub/scm/linux/kernel/git/perf/perf-tools-next.git perf/perf-tools-next
+Already up to date.
+Merging compiler-attributes/compiler-attributes (98f7e32f20d2 Linux 6.11)
+$ git merge -m Merge branch 'compiler-attributes' of https://github.com/ojeda/linux.git compiler-attributes/compiler-attributes
+Already up to date.
+Merging dma-mapping/dma-mapping-for-next (fbf5e2234169 dma-mapping: properly calculate offset in the page)
+$ git merge -m Merge branch 'dma-mapping-for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/mszyprowski/linux.git dma-mapping/dma-mapping-for-next
+Auto-merging Documentation/core-api/dma-api.rst
+Auto-merging drivers/virtio/virtio_ring.c
+Auto-merging mm/hmm.c
+Merge made by the 'ort' strategy.
+ Documentation/core-api/dma-api.rst | 4 +--
+ arch/powerpc/kernel/dma-iommu.c | 4 +--
+ drivers/iommu/dma-iommu.c | 14 ++++----
+ drivers/virtio/virtio_ring.c | 4 +--
+ include/linux/dma-map-ops.h | 8 ++---
+ include/linux/dma-mapping.h | 13 ++++++++
+ include/linux/iommu-dma.h | 7 ++--
+ include/linux/kmsan.h | 12 ++++---
+ include/trace/events/dma.h | 4 +--
+ kernel/dma/debug.c | 28 ++++++++++------
+ kernel/dma/debug.h | 16 ++++-----
+ kernel/dma/direct.c | 6 ++--
+ kernel/dma/direct.h | 13 ++++----
+ kernel/dma/mapping.c | 68 +++++++++++++++++++++++++++-----------
+ kernel/dma/ops_helpers.c | 6 ++--
+ mm/hmm.c | 8 ++---
+ mm/kmsan/hooks.c | 36 ++++++++++++++++----
+ tools/virtio/linux/kmsan.h | 2 +-
+ 18 files changed, 160 insertions(+), 93 deletions(-)
+Merging asm-generic/master (582847f97024 Makefile.kcov: apply needed compiler option unconditionally in CFLAGS_KCOV)
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/arnd/asm-generic.git asm-generic/master
+Already up to date.
+Merging alpha/alpha-next (1523226edda5 alpha: Use str_yes_no() helper in pci_dac_dma_supported())
+$ git merge -m Merge branch 'alpha-next' of git://git.kernel.org/pub/scm/linux/kernel/git/mattst88/alpha.git alpha/alpha-next
+Already up to date.
+Merging arm/for-next (8dd85887ad83 Merge branches 'fixes' and 'misc' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/rmk/linux.git arm/for-next
+Merge made by the 'ort' strategy.
+ arch/arm/include/asm/cti.h | 160 ---------------------------------------------
+ 1 file changed, 160 deletions(-)
+ delete mode 100644 arch/arm/include/asm/cti.h
+Merging arm64/for-next/core (5b1ae9de7133 Merge branch 'for-next/feat_mte_store_only' into for-next/core)
+$ git merge -m Merge branch 'for-next/core' of git://git.kernel.org/pub/scm/linux/kernel/git/arm64/linux arm64/for-next/core
+Already up to date.
+Merging arm-perf/for-next/perf (e480898e767c drivers/perf: hisi: Support PMUs with no interrupt)
+$ git merge -m Merge branch 'for-next/perf' of git://git.kernel.org/pub/scm/linux/kernel/git/will/linux.git arm-perf/for-next/perf
+Already up to date.
+Merging arm-soc/for-next (9f9d41d64322 Merge tag 'arm-soc/for-6.17/drivers-part2' of https://github.com/Broadcom/stblinux into arm/fixes)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/soc/soc.git arm-soc/for-next
+Already up to date.
+Merging amlogic/for-next (58abdca0eb65 Merge branch 'v6.17/arm64-dt' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/amlogic/linux.git amlogic/for-next
+Merge made by the 'ort' strategy.
+Merging asahi-soc/asahi-soc/for-next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'asahi-soc/for-next' of https://github.com/AsahiLinux/linux.git asahi-soc/asahi-soc/for-next
+Already up to date.
+Merging at91/at91-next (e99113d11171 Merge branch 'clk-microchip' into at91-next)
+$ git merge -m Merge branch 'at91-next' of git://git.kernel.org/pub/scm/linux/kernel/git/at91/linux.git at91/at91-next
+Merge made by the 'ort' strategy.
+Merging bmc/for-next (acba3fae64fd Merge branches 'aspeed/drivers', 'aspeed/dt', 'nuvoton/arm/dt' and 'nuvoton/arm64/dt' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/bmc/linux.git bmc/for-next
+Auto-merging arch/arm64/boot/dts/nuvoton/nuvoton-common-npcm8xx.dtsi
+Merge made by the 'ort' strategy.
+ .../devicetree/bindings/arm/aspeed/aspeed.yaml | 3 +
+ arch/arm/boot/dts/aspeed/Makefile | 3 +
+ .../boot/dts/aspeed/aspeed-bmc-facebook-darwin.dts | 72 ++
+ .../boot/dts/aspeed/aspeed-bmc-facebook-elbert.dts | 12 +
+ .../dts/aspeed/aspeed-bmc-facebook-fuji-data64.dts | 1256 ++++++++++++++++++++
+ .../boot/dts/aspeed/aspeed-bmc-facebook-fuji.dts | 1247 +------------------
+ .../aspeed/aspeed-bmc-facebook-wedge400-data64.dts | 375 ++++++
+ .../dts/aspeed/aspeed-bmc-facebook-wedge400.dts | 366 +-----
+ .../arm/boot/dts/aspeed/aspeed-bmc-ibm-everest.dts | 24 +-
+ .../boot/dts/aspeed/aspeed-bmc-inspur-fp5280g2.dts | 3 +-
+ .../dts/aspeed/aspeed-bmc-nvidia-gb200nvl-bmc.dts | 54 +-
+ .../arm/boot/dts/aspeed/aspeed-bmc-opp-lanyang.dts | 2 +-
+ arch/arm/boot/dts/aspeed/aspeed-bmc-opp-mowgli.dts | 2 +-
+ arch/arm/boot/dts/aspeed/aspeed-bmc-opp-nicole.dts | 3 +-
+ .../boot/dts/aspeed/aspeed-bmc-opp-palmetto.dts | 2 +-
+ .../arm/boot/dts/aspeed/aspeed-bmc-opp-romulus.dts | 3 +-
+ .../boot/dts/aspeed/aspeed-bmc-opp-witherspoon.dts | 2 +-
+ arch/arm/boot/dts/aspeed/aspeed-bmc-opp-zaius.dts | 2 +-
+ arch/arm/boot/dts/aspeed/aspeed-g6.dtsi | 4 +-
+ .../dts/aspeed/ast2600-facebook-netbmc-common.dtsi | 22 +-
+ .../facebook-bmc-flash-layout-128-data64.dtsi | 60 +
+ arch/arm/boot/dts/aspeed/ibm-power10-dual.dtsi | 12 +-
+ arch/arm/boot/dts/aspeed/ibm-power10-quad.dtsi | 12 +-
+ .../boot/dts/nuvoton/nuvoton-common-npcm7xx.dtsi | 2 +-
+ arch/arm/boot/dts/nuvoton/nuvoton-npcm750.dtsi | 2 +-
+ .../boot/dts/nuvoton/nuvoton-common-npcm8xx.dtsi | 669 ++++++++++-
+ .../arm64/boot/dts/nuvoton/nuvoton-npcm845-evb.dts | 6 +
+ drivers/soc/aspeed/aspeed-lpc-ctrl.c | 14 +-
+ drivers/soc/aspeed/aspeed-p2a-ctrl.c | 14 +-
+ 29 files changed, 2561 insertions(+), 1687 deletions(-)
+ create mode 100644 arch/arm/boot/dts/aspeed/aspeed-bmc-facebook-darwin.dts
+ create mode 100644 arch/arm/boot/dts/aspeed/aspeed-bmc-facebook-fuji-data64.dts
+ create mode 100644 arch/arm/boot/dts/aspeed/aspeed-bmc-facebook-wedge400-data64.dts
+ create mode 100644 arch/arm/boot/dts/aspeed/facebook-bmc-flash-layout-128-data64.dtsi
+Merging broadcom/next (89abb622d518 Merge branch 'drivers/next' into next)
+$ git merge -m Merge branch 'next' of https://github.com/Broadcom/stblinux.git broadcom/next
+Merge made by the 'ort' strategy.
+Merging davinci/davinci/for-next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'davinci/for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git davinci/davinci/for-next
+Already up to date.
+Merging drivers-memory/for-next (93a7aedc4cc4 dt-bindings: memory: renesas,rzg3e-xspi: Document RZ/V2H(P) and RZ/V2N support)
+$ git merge -m Merge branch 'for-next' of https://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux-mem-ctrl.git drivers-memory/for-next
+Already up to date.
+Merging fsl/soc_fsl (8b3da0519ae6 soc: fsl: qe: convert set_multiple() to returning an integer)
+$ git merge -m Merge branch 'soc_fsl' of https://github.com/chleroy/linux.git fsl/soc_fsl
+Merge made by the 'ort' strategy.
+Merging imx-mxs/for-next (cdc22fb12eff Merge branch 'imx/defconfig' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/shawnguo/linux.git imx-mxs/for-next
+Merge made by the 'ort' strategy.
+Merging mediatek/for-next (6cbb623586d5 Merge branches 'v6.16-next/arm32', 'v6.16-next/dts32', 'v6.16-next/dts64' and 'v6.16-next/soc' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/mediatek/linux.git mediatek/for-next
+Merge made by the 'ort' strategy.
+Merging mvebu/for-next (88084e0358ff Merge branch 'mvebu/dt' into mvebu/for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/gclement/mvebu.git mvebu/for-next
+Merge made by the 'ort' strategy.
+Merging omap/for-next (db91121f001a Merge branch 'omap-for-v6.17/soc' into tmp/omap-next-20250707.142928)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/khilman/linux-omap.git omap/for-next
+Auto-merging arch/arm/configs/multi_v7_defconfig
+Auto-merging arch/arm/configs/omap2plus_defconfig
+Merge made by the 'ort' strategy.
+Merging qcom/for-next (ba94ec807b07 Merge branches 'arm32-for-6.17', 'arm64-defconfig-fixes-for-6.16', 'arm64-defconfig-for-6.17', 'arm64-fixes-for-6.16', 'arm64-for-6.17', 'clk-for-6.17' and 'drivers-for-6.17' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/qcom/linux.git qcom/for-next
+Merge made by the 'ort' strategy.
+ Documentation/devicetree/bindings/arm/qcom.yaml | 9 +
+ arch/arm/boot/dts/qcom/Makefile | 1 +
+ arch/arm/boot/dts/qcom/pm8921.dtsi | 6 +
+ arch/arm/boot/dts/qcom/qcom-msm8960-pins.dtsi | 40 +++
+ .../dts/qcom/qcom-msm8960-samsung-expressatt.dts | 5 +
+ .../boot/dts/qcom/qcom-msm8960-sony-huashan.dts | 361 +++++++++++++++++++++
+ arch/arm/boot/dts/qcom/qcom-msm8960.dtsi | 32 ++
+ arch/arm64/boot/dts/qcom/ipq5018.dtsi | 226 ++++++++++++-
+ arch/arm64/boot/dts/qcom/ipq5424-rdp466.dts | 26 +-
+ arch/arm64/boot/dts/qcom/ipq5424.dtsi | 27 +-
+ arch/arm64/boot/dts/qcom/msm8916.dtsi | 8 -
+ arch/arm64/boot/dts/qcom/qcs615-ride.dts | 4 +-
+ arch/arm64/boot/dts/qcom/sa8775p.dtsi | 2 +-
+ arch/arm64/boot/dts/qcom/sar2130p.dtsi | 23 +-
+ arch/arm64/boot/dts/qcom/sc7180.dtsi | 8 -
+ arch/arm64/boot/dts/qcom/sdm845.dtsi | 16 +-
+ .../boot/dts/qcom/sdm850-lenovo-yoga-c630.dts | 104 +++++-
+ .../boot/dts/qcom/{qcs615.dtsi => sm6150.dtsi} | 6 +
+ arch/arm64/boot/dts/qcom/sm6350.dtsi | 11 +
+ arch/arm64/boot/dts/qcom/sm7225-fairphone-fp4.dts | 36 ++
+ arch/arm64/boot/dts/qcom/sm8250.dtsi | 8 -
+ .../boot/dts/qcom/x1e80100-lenovo-yoga-slim7x.dts | 143 ++++++++
+ arch/arm64/boot/dts/qcom/x1e80100.dtsi | 7 +
+ arch/arm64/boot/dts/qcom/x1p42100-crd.dts | 4 +
+ arch/arm64/boot/dts/qcom/x1p42100.dtsi | 120 ++++++-
+ 25 files changed, 1173 insertions(+), 60 deletions(-)
+ create mode 100644 arch/arm/boot/dts/qcom/qcom-msm8960-sony-huashan.dts
+ rename arch/arm64/boot/dts/qcom/{qcs615.dtsi => sm6150.dtsi} (99%)
+Merging renesas/next (7a323accaf6b Merge branches 'renesas-arm-defconfig-for-v6.17', 'renesas-drivers-for-v6.17', 'renesas-dt-bindings-for-v6.17' and 'renesas-dts-for-v6.17' into renesas-next)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/geert/renesas-devel.git renesas/next
+Merge made by the 'ort' strategy.
+Merging reset/reset/next (335bb23abed3 MAINTAINERS: Use https:// protocol for Reset Controller Framework tree)
+$ git merge -m Merge branch 'reset/next' of https://git.pengutronix.de/git/pza/linux reset/reset/next
+Auto-merging MAINTAINERS
+Merge made by the 'ort' strategy.
+ MAINTAINERS | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+Merging rockchip/for-next (1f0c7abd8235 Merge branch 'v6.16-armsoc/dtsfixes' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/mmind/linux-rockchip.git rockchip/for-next
+Merge made by the 'ort' strategy.
+Merging samsung-krzk/for-next (94f19ac4670d Merge branch 'next/drivers' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux.git samsung-krzk/for-next
+Merge made by the 'ort' strategy.
+Merging scmi/for-linux-next (d2eedaa3909b Merge tag 'rtc-6.17' of git://git.kernel.org/pub/scm/linux/kernel/git/abelloni/linux)
+$ git merge -m Merge branch 'for-linux-next' of git://git.kernel.org/pub/scm/linux/kernel/git/sudeep.holla/linux.git scmi/for-linux-next
+Already up to date.
+Merging sophgo/for-next (349ae53a949c Merge branch 'dt/riscv' into for-next)
+$ git merge -m Merge branch 'for-next' of https://github.com/sophgo/linux.git sophgo/for-next
+Merge made by the 'ort' strategy.
+Merging sophgo-soc/soc-for-next (c8754c7deab4 soc: sophgo: cv1800: rtcsys: New driver (handling RTC only))
+$ git merge -m Merge branch 'soc-for-next' of https://github.com/sophgo/linux.git sophgo-soc/soc-for-next
+Already up to date.
+Merging spacemit/for-next (6be7a5a768aa Merge branch 'spacemit-clk-for-6.17' into spacemit-for-next)
+$ git merge -m Merge branch 'for-next' of https://github.com/spacemit-com/linux spacemit/for-next
+Merge made by the 'ort' strategy.
+Merging stm32/stm32-next (1a32f7427eb3 arm64: dts: st: remove empty line in stm32mp251.dtsi)
+$ git merge -m Merge branch 'stm32-next' of git://git.kernel.org/pub/scm/linux/kernel/git/atorgue/stm32.git stm32/stm32-next
+Already up to date.
+Merging sunxi/sunxi/for-next (cbe908fc8ebb Merge branch 'sunxi/dt-for-6.17' into sunxi/for-next)
+$ git merge -m Merge branch 'sunxi/for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/sunxi/linux.git sunxi/sunxi/for-next
+Merge made by the 'ort' strategy.
+Merging tee/next (84c5f44d24c6 Merge branch 'tee_fixes_for_v6.17' into next)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/jenswi/linux-tee.git tee/next
+Merge made by the 'ort' strategy.
+ drivers/tee/optee/core.c | 2 +-
+ drivers/tee/tee_core.c | 2 +-
+ drivers/tee/tee_shm.c | 14 ++++++++++----
+ 3 files changed, 12 insertions(+), 6 deletions(-)
+Merging tegra/for-next (499b75defe56 Merge branch for-6.17/arm64/defconfig into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/tegra/linux.git tegra/for-next
+Merge made by the 'ort' strategy.
+ Documentation/devicetree/bindings/arm/tegra/nvidia,tegra234-cbb.yaml | 4 ++++
+ arch/arm64/boot/dts/nvidia/tegra264.dtsi | 3 ---
+ drivers/firmware/tegra/bpmp-tegra186.c | 5 ++++-
+ 3 files changed, 8 insertions(+), 4 deletions(-)
+Merging thead-dt/thead-dt-for-next (c31f2899eab0 riscv: dts: thead: Add PVT node)
+$ git merge -m Merge branch 'thead-dt-for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/fustini/linux.git thead-dt/thead-dt-for-next
+Already up to date.
+Merging ti/ti-next (65f6e3eb6351 Merge branch 'ti-k3-dts-next' into ti-next)
+$ git merge -m Merge branch 'ti-next' of git://git.kernel.org/pub/scm/linux/kernel/git/ti/linux.git ti/ti-next
+Merge made by the 'ort' strategy.
+Merging xilinx/for-next (3a0e3f82b8ee Merge branch 'zynqmp/dt' into for-next)
+$ git merge -m Merge branch 'for-next' of git://github.com/Xilinx/linux-xlnx.git xilinx/for-next
+Merge made by the 'ort' strategy.
+ .../devicetree/bindings/soc/xilinx/xilinx.yaml | 81 ++++
+ arch/arm64/boot/dts/xilinx/Makefile | 24 ++
+ arch/arm64/boot/dts/xilinx/versal-net.dtsi | 2 +-
+ .../boot/dts/xilinx/zynqmp-sck-kd-g-revA.dtso | 390 ++++++++++++++++++
+ .../boot/dts/xilinx/zynqmp-sck-kr-g-revA.dtso | 438 ++++++++++++++++++++
+ .../boot/dts/xilinx/zynqmp-sck-kr-g-revB.dtso | 451 +++++++++++++++++++++
+ .../boot/dts/xilinx/zynqmp-sck-kv-g-revA.dtso | 19 +-
+ .../boot/dts/xilinx/zynqmp-sck-kv-g-revB.dtso | 35 +-
+ arch/arm64/boot/dts/xilinx/zynqmp-sm-k24-revA.dts | 23 ++
+ arch/arm64/boot/dts/xilinx/zynqmp-sm-k26-revA.dts | 7 +-
+ arch/arm64/boot/dts/xilinx/zynqmp-smk-k24-revA.dts | 21 +
+ .../boot/dts/xilinx/zynqmp-zc1751-xm016-dc2.dts | 1 -
+ .../boot/dts/xilinx/zynqmp-zc1751-xm017-dc3.dts | 1 -
+ arch/arm64/boot/dts/xilinx/zynqmp-zcu100-revC.dts | 21 +
+ arch/arm64/boot/dts/xilinx/zynqmp-zcu102-revA.dts | 18 +
+ arch/arm64/boot/dts/xilinx/zynqmp-zcu104-revA.dts | 18 +
+ arch/arm64/boot/dts/xilinx/zynqmp-zcu104-revC.dts | 18 +
+ arch/arm64/boot/dts/xilinx/zynqmp-zcu106-revA.dts | 10 +-
+ arch/arm64/boot/dts/xilinx/zynqmp-zcu111-revA.dts | 20 +-
+ arch/arm64/boot/dts/xilinx/zynqmp.dtsi | 14 +-
+ drivers/firmware/xilinx/zynqmp-debug.c | 13 +
+ drivers/firmware/xilinx/zynqmp.c | 114 ++++--
+ drivers/pinctrl/pinctrl-zynqmp.c | 7 +-
+ drivers/soc/xilinx/xlnx_event_manager.c | 8 +-
+ drivers/soc/xilinx/zynqmp_power.c | 10 +-
+ include/linux/firmware/xlnx-zynqmp.h | 30 +-
+ 26 files changed, 1713 insertions(+), 81 deletions(-)
+ create mode 100644 arch/arm64/boot/dts/xilinx/zynqmp-sck-kd-g-revA.dtso
+ create mode 100644 arch/arm64/boot/dts/xilinx/zynqmp-sck-kr-g-revA.dtso
+ create mode 100644 arch/arm64/boot/dts/xilinx/zynqmp-sck-kr-g-revB.dtso
+ create mode 100644 arch/arm64/boot/dts/xilinx/zynqmp-sm-k24-revA.dts
+ create mode 100644 arch/arm64/boot/dts/xilinx/zynqmp-smk-k24-revA.dts
+Merging clk/clk-next (64c21f253a37 Merge branch 'clk-fixes' into clk-next)
+$ git merge -m Merge branch 'clk-next' of git://git.kernel.org/pub/scm/linux/kernel/git/clk/linux.git clk/clk-next
+Already up to date.
+Merging clk-imx/for-next (c78865241ecf MAINTAINERS: Update i.MX Clock Entry)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/abelvesa/linux.git clk-imx/for-next
+Already up to date.
+Merging clk-renesas/renesas-clk (0ab2d84f94da clk: renesas: r9a08g045: Add MSTOP for coupled clocks as well)
+$ git merge -m Merge branch 'renesas-clk' of git://git.kernel.org/pub/scm/linux/kernel/git/geert/renesas-drivers.git clk-renesas/renesas-clk
+Already up to date.
+Merging thead-clk/thead-clk-for-next (54edba916e29 clk: thead: th1520-ap: Describe mux clocks with clk_mux)
+$ git merge -m Merge branch 'thead-clk-for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/fustini/linux.git thead-clk/thead-clk-for-next
+Already up to date.
+Merging csky/linux-next (2b48804336be csky: fix csky_cmpxchg_fixup not working)
+$ git merge -m Merge branch 'linux-next' of git://github.com/c-sky/csky-linux.git csky/linux-next
+Merge made by the 'ort' strategy.
+ arch/csky/mm/fault.c | 4 ++--
+ 1 file changed, 2 insertions(+), 2 deletions(-)
+Merging loongarch/loongarch-next (bcfdf97c1abc LoongArch: vDSO: Remove -nostdlib complier flag)
+$ git merge -m Merge branch 'loongarch-next' of git://git.kernel.org/pub/scm/linux/kernel/git/chenhuacai/linux-loongson.git loongarch/loongarch-next
+Auto-merging arch/loongarch/kernel/setup.c
+Merge made by the 'ort' strategy.
+ arch/loongarch/boot/dts/loongson-2k0500-ref.dts | 9 +
+ arch/loongarch/boot/dts/loongson-2k0500.dtsi | 28 +-
+ arch/loongarch/boot/dts/loongson-2k1000-ref.dts | 13 +
+ arch/loongarch/boot/dts/loongson-2k1000.dtsi | 24 +-
+ arch/loongarch/boot/dts/loongson-2k2000-ref.dts | 10 +
+ arch/loongarch/boot/dts/loongson-2k2000.dtsi | 18 +
+ arch/loongarch/include/asm/inst.h | 3 +
+ arch/loongarch/include/asm/loongarch.h | 7 +
+ arch/loongarch/kernel/env.c | 13 +-
+ arch/loongarch/kernel/inst.c | 55 ++
+ arch/loongarch/kernel/relocate_kernel.S | 2 +-
+ arch/loongarch/kernel/setup.c | 18 +-
+ arch/loongarch/kernel/unwind_orc.c | 2 +-
+ arch/loongarch/net/bpf_jit.c | 699 +++++++++++++++++++++---
+ arch/loongarch/net/bpf_jit.h | 6 +
+ arch/loongarch/vdso/Makefile | 2 +-
+ 16 files changed, 820 insertions(+), 89 deletions(-)
+Merging m68k/for-next (c8995932db2b m68k: mac: Improve clocksource driver commentary)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/geert/linux-m68k.git m68k/for-next
+Already up to date.
+Merging m68knommu/for-next (89be9a83ccf1 Linux 6.16-rc7)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/gerg/m68knommu.git m68knommu/for-next
+Already up to date.
+Merging microblaze/next (c0e7bb02f796 microblaze: Replace __ASSEMBLY__ with __ASSEMBLER__ in non-uapi headers)
+$ git merge -m Merge branch 'next' of git://git.monstr.eu/linux-2.6-microblaze.git microblaze/next
+Auto-merging arch/microblaze/include/asm/pgtable.h
+Merge made by the 'ort' strategy.
+ arch/microblaze/Kconfig.platform | 10 +++++-----
+ arch/microblaze/include/asm/asm-compat.h | 2 +-
+ arch/microblaze/include/asm/current.h | 4 ++--
+ arch/microblaze/include/asm/entry.h | 4 ++--
+ arch/microblaze/include/asm/exceptions.h | 4 ++--
+ arch/microblaze/include/asm/fixmap.h | 4 ++--
+ arch/microblaze/include/asm/ftrace.h | 2 +-
+ arch/microblaze/include/asm/kgdb.h | 4 ++--
+ arch/microblaze/include/asm/mmu.h | 4 ++--
+ arch/microblaze/include/asm/page.h | 8 ++++----
+ arch/microblaze/include/asm/pgtable.h | 18 +++++++++---------
+ arch/microblaze/include/asm/processor.h | 8 ++++----
+ arch/microblaze/include/asm/ptrace.h | 4 ++--
+ arch/microblaze/include/asm/sections.h | 4 ++--
+ arch/microblaze/include/asm/setup.h | 4 ++--
+ arch/microblaze/include/asm/thread_info.h | 4 ++--
+ arch/microblaze/include/asm/unistd.h | 4 ++--
+ arch/microblaze/include/asm/xilinx_mb_manager.h | 4 ++--
+ arch/microblaze/include/uapi/asm/ptrace.h | 4 ++--
+ 19 files changed, 50 insertions(+), 50 deletions(-)
+Merging mips/mips-next (3ebcbf079c26 MIPS: Don't use %pK through printk)
+$ git merge -m Merge branch 'mips-next' of git://git.kernel.org/pub/scm/linux/kernel/git/mips/linux.git mips/mips-next
+Already up to date.
+Merging openrisc/for-next (f0eedcf22581 openrisc: Replace __ASSEMBLY__ with __ASSEMBLER__ in non-uapi headers)
+$ git merge -m Merge branch 'for-next' of git://github.com/openrisc/linux.git openrisc/for-next
+Already up to date.
+Merging parisc-hd/for-next (89f686a0fb6e parisc: Revise __get_user() to probe user read access)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/deller/parisc-linux.git parisc-hd/for-next
+Already up to date.
+Merging powerpc/next (cf2a6de32cab powerpc64/bpf: Add jit support for load_acquire and store_release)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/powerpc/linux.git powerpc/next
+Already up to date.
+Merging risc-v/for-next (fda589c28604 Merge patch series "Move duplicated instructions macros into asm/insn.h")
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/riscv/linux.git risc-v/for-next
+Auto-merging arch/riscv/configs/defconfig
+Auto-merging arch/riscv/kernel/traps_misaligned.c
+Merge made by the 'ort' strategy.
+ arch/riscv/configs/defconfig | 5 +-
+ arch/riscv/include/asm/insn.h | 206 +++++++++++++++++++++++++++++----
+ arch/riscv/kernel/machine_kexec_file.c | 2 +-
+ arch/riscv/kernel/traps_misaligned.c | 144 +----------------------
+ arch/riscv/kernel/vector.c | 2 +-
+ arch/riscv/kvm/vcpu_insn.c | 128 +-------------------
+ 6 files changed, 190 insertions(+), 297 deletions(-)
+Merging riscv-dt/riscv-dt-for-next (28fa0dcb571a dt-bindings: riscv: cpus: Add AMD MicroBlaze V 64bit compatible)
+$ git merge -m Merge branch 'riscv-dt-for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/conor/linux.git riscv-dt/riscv-dt-for-next
+Already up to date.
+Merging riscv-soc/riscv-soc-for-next (bd4d5d3faadc riscv: defconfig: spacemit: enable sdhci driver for K1 SoC)
+$ git merge -m Merge branch 'riscv-soc-for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/conor/linux.git riscv-soc/riscv-soc-for-next
+Already up to date.
+Merging s390/for-next (d3a0de1a9dbc Merge branch 'features' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/s390/linux.git s390/for-next
+Auto-merging arch/s390/Kconfig
+Auto-merging arch/s390/kernel/setup.c
+Merge made by the 'ort' strategy.
+ arch/s390/Kconfig | 3 +++
+ arch/s390/include/asm/ap.h | 2 +-
+ arch/s390/include/asm/pgtable.h | 45 +++++++++++++++++++++++++++++++++++++++++
+ arch/s390/kernel/setup.c | 6 ++++++
+ drivers/s390/crypto/ap_bus.h | 2 +-
+ 5 files changed, 56 insertions(+), 2 deletions(-)
+Merging sh/for-next (c32969d0362a sh: Do not use hyphen in exported variable name)
+$ git merge -m Merge branch 'for-next' of git:git.kernel.org/pub/scm/linux/kernel/git/glaubitz/sh-linux.git sh/for-next
+Already up to date.
+Merging sparc/for-next (2cec2c4dc90c sparc/irq: Remove unneeded if check in sun4v_cookie_only_virqs())
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/alarsson/linux-sparc.git sparc/for-next
+Already up to date.
+Merging uml/next (fc9ed2f6589d um: Replace __ASSEMBLY__ with __ASSEMBLER__ in the usermode headers)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/uml/linux.git uml/next
+Already up to date.
+Merging xtensa/xtensa-for-next (44a4ef59d550 xtensa: Replace __ASSEMBLY__ with __ASSEMBLER__ in non-uapi headers)
+$ git merge -m Merge branch 'xtensa-for-next' of git://github.com/jcmvbkbc/linux-xtensa.git xtensa/xtensa-for-next
+Auto-merging arch/xtensa/include/asm/pgtable.h
+Auto-merging arch/xtensa/include/asm/ptrace.h
+Merge made by the 'ort' strategy.
+ arch/xtensa/include/asm/bootparam.h | 2 +-
+ arch/xtensa/include/asm/cmpxchg.h | 4 ++--
+ arch/xtensa/include/asm/coprocessor.h | 8 ++++----
+ arch/xtensa/include/asm/current.h | 2 +-
+ arch/xtensa/include/asm/ftrace.h | 8 ++++----
+ arch/xtensa/include/asm/initialize_mmu.h | 4 ++--
+ arch/xtensa/include/asm/jump_label.h | 4 ++--
+ arch/xtensa/include/asm/kasan.h | 2 +-
+ arch/xtensa/include/asm/kmem_layout.h | 2 +-
+ arch/xtensa/include/asm/page.h | 4 ++--
+ arch/xtensa/include/asm/pgtable.h | 8 ++++----
+ arch/xtensa/include/asm/processor.h | 4 ++--
+ arch/xtensa/include/asm/ptrace.h | 6 +++---
+ arch/xtensa/include/asm/signal.h | 4 ++--
+ arch/xtensa/include/asm/thread_info.h | 8 ++++----
+ arch/xtensa/include/asm/tlbflush.h | 4 ++--
+ arch/xtensa/include/uapi/asm/ptrace.h | 2 +-
+ arch/xtensa/include/uapi/asm/signal.h | 6 +++---
+ arch/xtensa/include/uapi/asm/types.h | 4 ++--
+ 19 files changed, 43 insertions(+), 43 deletions(-)
+Merging fs-next (0264e7f5188b Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs.git)
+$ git merge -m Merge branch 'fs-next' of linux-next fs-next
+Auto-merging MAINTAINERS
+Merge made by the 'ort' strategy.
+ Documentation/ABI/testing/sysfs-fs-f2fs | 22 +
+ Documentation/filesystems/f2fs.rst | 6 +-
+ .../filesystems/{ => fuse}/fuse-io-uring.rst | 0
+ Documentation/filesystems/{ => fuse}/fuse-io.rst | 2 +-
+ .../filesystems/{ => fuse}/fuse-passthrough.rst | 0
+ Documentation/filesystems/{ => fuse}/fuse.rst | 20 +-
+ Documentation/filesystems/fuse/index.rst | 14 +
+ Documentation/filesystems/index.rst | 5 +-
+ MAINTAINERS | 3 +-
+ fs/bcachefs/acl.c | 29 +-
+ fs/bcachefs/alloc_background.c | 570 +++--
+ fs/bcachefs/alloc_background.h | 9 +-
+ fs/bcachefs/alloc_foreground.c | 258 +--
+ fs/bcachefs/alloc_foreground.h | 9 +-
+ fs/bcachefs/async_objs.c | 29 +-
+ fs/bcachefs/async_objs.h | 7 +-
+ fs/bcachefs/async_objs_types.h | 2 +-
+ fs/bcachefs/backpointers.c | 167 +-
+ fs/bcachefs/bcachefs.h | 91 +-
+ fs/bcachefs/bcachefs_format.h | 42 +-
+ fs/bcachefs/bkey.c | 4 +-
+ fs/bcachefs/bkey_methods.c | 6 +-
+ fs/bcachefs/bkey_types.h | 5 +
+ fs/bcachefs/bset.c | 74 +-
+ fs/bcachefs/btree_cache.c | 44 +-
+ fs/bcachefs/btree_cache.h | 19 +
+ fs/bcachefs/btree_gc.c | 258 +--
+ fs/bcachefs/btree_io.c | 123 +-
+ fs/bcachefs/btree_iter.c | 424 ++--
+ fs/bcachefs/btree_iter.h | 348 ++--
+ fs/bcachefs/btree_journal_iter.c | 20 +-
+ fs/bcachefs/btree_key_cache.c | 69 +-
+ fs/bcachefs/btree_locking.c | 17 +-
+ fs/bcachefs/btree_node_scan.c | 36 +-
+ fs/bcachefs/btree_trans_commit.c | 125 +-
+ fs/bcachefs/btree_types.h | 43 +-
+ fs/bcachefs/btree_update.c | 339 +--
+ fs/bcachefs/btree_update.h | 150 +-
+ fs/bcachefs/btree_update_interior.c | 387 ++--
+ fs/bcachefs/btree_update_interior.h | 12 +-
+ fs/bcachefs/btree_write_buffer.c | 78 +-
+ fs/bcachefs/btree_write_buffer.h | 8 +-
+ fs/bcachefs/buckets.c | 258 +--
+ fs/bcachefs/buckets_waiting_for_journal.c | 30 +-
+ fs/bcachefs/chardev.c | 120 +-
+ fs/bcachefs/checksum.c | 54 +-
+ fs/bcachefs/clock.c | 17 +-
+ fs/bcachefs/compress.c | 29 +-
+ fs/bcachefs/compress.h | 36 +-
+ fs/bcachefs/data_update.c | 58 +-
+ fs/bcachefs/data_update.h | 1 +
+ fs/bcachefs/debug.c | 88 +-
+ fs/bcachefs/dirent.c | 88 +-
+ fs/bcachefs/dirent.h | 4 +-
+ fs/bcachefs/disk_accounting.c | 270 ++-
+ fs/bcachefs/disk_accounting.h | 19 +-
+ fs/bcachefs/disk_groups.c | 27 +-
+ fs/bcachefs/ec.c | 396 ++--
+ fs/bcachefs/ec.h | 2 +-
+ fs/bcachefs/enumerated_ref.c | 4 +-
+ fs/bcachefs/errcode.c | 3 +-
+ fs/bcachefs/errcode.h | 14 +
+ fs/bcachefs/error.c | 65 +-
+ fs/bcachefs/error.h | 3 +-
+ fs/bcachefs/extent_update.c | 67 +-
+ fs/bcachefs/extent_update.h | 2 -
+ fs/bcachefs/extents.c | 55 +-
+ fs/bcachefs/extents.h | 4 +
+ fs/bcachefs/fast_list.c | 32 +-
+ fs/bcachefs/fast_list.h | 2 +-
+ fs/bcachefs/fs-io-buffered.c | 96 +-
+ fs/bcachefs/fs-io-direct.c | 26 +-
+ fs/bcachefs/fs-io-pagecache.c | 55 +-
+ fs/bcachefs/fs-io.c | 141 +-
+ fs/bcachefs/fs-io.h | 19 +-
+ fs/bcachefs/fs-ioctl.c | 33 +-
+ fs/bcachefs/fs.c | 254 +--
+ fs/bcachefs/fsck.c | 649 +++---
+ fs/bcachefs/inode.c | 252 +--
+ fs/bcachefs/io_misc.c | 83 +-
+ fs/bcachefs/io_read.c | 235 ++-
+ fs/bcachefs/io_read.h | 24 +-
+ fs/bcachefs/io_write.c | 97 +-
+ fs/bcachefs/journal.c | 253 ++-
+ fs/bcachefs/journal.h | 3 +-
+ fs/bcachefs/journal_io.c | 248 +--
+ fs/bcachefs/journal_io.h | 7 +
+ fs/bcachefs/journal_reclaim.c | 220 +-
+ fs/bcachefs/journal_seq_blacklist.c | 56 +-
+ fs/bcachefs/journal_seq_blacklist.h | 3 +
+ fs/bcachefs/logged_ops.c | 16 +-
+ fs/bcachefs/logged_ops.h | 2 +-
+ fs/bcachefs/lru.c | 48 +-
+ fs/bcachefs/lru.h | 10 +
+ fs/bcachefs/migrate.c | 31 +-
+ fs/bcachefs/move.c | 316 ++-
+ fs/bcachefs/move.h | 14 +-
+ fs/bcachefs/movinggc.c | 218 +-
+ fs/bcachefs/namei.c | 154 +-
+ fs/bcachefs/nocow_locking.c | 10 +-
+ fs/bcachefs/opts.c | 33 +-
+ fs/bcachefs/opts.h | 8 +-
+ fs/bcachefs/printbuf.h | 4 +
+ fs/bcachefs/progress.c | 6 +-
+ fs/bcachefs/progress.h | 3 +
+ fs/bcachefs/quota.c | 103 +-
+ fs/bcachefs/rebalance.c | 216 +-
+ fs/bcachefs/recovery.c | 412 +---
+ fs/bcachefs/recovery_passes.c | 68 +-
+ fs/bcachefs/recovery_passes.h | 9 +-
+ fs/bcachefs/reflink.c | 137 +-
+ fs/bcachefs/replicas.c | 161 +-
+ fs/bcachefs/sb-clean.c | 36 +-
+ fs/bcachefs/sb-counters_format.h | 12 +-
+ fs/bcachefs/sb-downgrade.c | 19 +-
+ fs/bcachefs/sb-errors.c | 45 +-
+ fs/bcachefs/sb-errors_format.h | 11 +-
+ fs/bcachefs/sb-members.c | 164 +-
+ fs/bcachefs/sb-members.h | 44 +-
+ fs/bcachefs/sb-members_format.h | 2 +-
+ fs/bcachefs/six.c | 21 +-
+ fs/bcachefs/snapshot.c | 435 ++--
+ fs/bcachefs/snapshot.h | 32 +-
+ fs/bcachefs/snapshot_types.h | 2 +-
+ fs/bcachefs/str_hash.c | 57 +-
+ fs/bcachefs/str_hash.h | 47 +-
+ fs/bcachefs/subvolume.c | 246 +--
+ fs/bcachefs/subvolume.h | 20 +-
+ fs/bcachefs/super-io.c | 112 +-
+ fs/bcachefs/super.c | 871 ++++----
+ fs/bcachefs/sysfs.c | 28 +-
+ fs/bcachefs/tests.c | 340 ++-
+ fs/bcachefs/thread_with_file.c | 48 +-
+ fs/bcachefs/time_stats.c | 7 +-
+ fs/bcachefs/trace.h | 157 +-
+ fs/bcachefs/util.c | 28 +-
+ fs/bcachefs/util.h | 10 +-
+ fs/bcachefs/xattr.c | 58 +-
+ fs/ecryptfs/crypto.c | 2 +-
+ fs/ecryptfs/ecryptfs_kernel.h | 1 -
+ fs/ecryptfs/keystore.c | 4 +-
+ fs/exfat/balloc.c | 12 +-
+ fs/exfat/dir.c | 13 +-
+ fs/exfat/exfat_fs.h | 1 +
+ fs/exfat/fatent.c | 10 +
+ fs/exfat/file.c | 5 +-
+ fs/exfat/namei.c | 5 +
+ fs/exfat/super.c | 32 +-
+ fs/ext4/namei.c | 2 -
+ fs/f2fs/checkpoint.c | 8 +-
+ fs/f2fs/compress.c | 120 +-
+ fs/f2fs/data.c | 183 +-
+ fs/f2fs/debug.c | 21 +-
+ fs/f2fs/dir.c | 4 +-
+ fs/f2fs/extent_cache.c | 10 +-
+ fs/f2fs/f2fs.h | 151 +-
+ fs/f2fs/file.c | 107 +-
+ fs/f2fs/gc.c | 54 +-
+ fs/f2fs/gc.h | 5 +-
+ fs/f2fs/inline.c | 20 +-
+ fs/f2fs/inode.c | 84 +-
+ fs/f2fs/namei.c | 12 +-
+ fs/f2fs/node.c | 261 ++-
+ fs/f2fs/node.h | 77 +-
+ fs/f2fs/recovery.c | 116 +-
+ fs/f2fs/segment.c | 62 +-
+ fs/f2fs/segment.h | 59 +-
+ fs/f2fs/super.c | 2185 +++++++++++---------
+ fs/f2fs/sysfs.c | 48 +
+ fs/fuse/dev.c | 5 +-
+ fs/fuse/file.c | 1 -
+ fs/fuse/virtio_fs.c | 3 -
+ fs/nfs/blocklayout/blocklayout.c | 4 +-
+ fs/nfs/blocklayout/dev.c | 5 +-
+ fs/nfs/blocklayout/extent_tree.c | 104 +-
+ fs/nfs/client.c | 3 +-
+ fs/nfs/delegation.c | 114 +-
+ fs/nfs/delegation.h | 3 +
+ fs/nfs/dir.c | 4 +-
+ fs/nfs/export.c | 11 +-
+ fs/nfs/flexfilelayout/flexfilelayout.c | 26 +-
+ fs/nfs/flexfilelayout/flexfilelayoutdev.c | 6 +-
+ fs/nfs/fs_context.c | 42 +
+ fs/nfs/inode.c | 69 +-
+ fs/nfs/internal.h | 10 +-
+ fs/nfs/mount_clnt.c | 68 -
+ fs/nfs/nfs4client.c | 165 +-
+ fs/nfs/nfs4file.c | 25 +-
+ fs/nfs/nfs4proc.c | 50 +-
+ fs/nfs/nfs4trace.c | 2 +
+ fs/nfs/nfs4trace.h | 168 +-
+ fs/nfs/nfs4xdr.c | 24 +
+ fs/nfs/nfstrace.h | 11 +-
+ fs/nfs/pnfs.c | 39 +-
+ fs/nfs/pnfs_nfs.c | 14 +-
+ fs/nfs/write.c | 8 +-
+ fs/smb/client/cifs_debug.c | 6 +-
+ fs/smb/client/cifsfs.c | 2 +-
+ fs/smb/client/cifsglob.h | 5 +
+ fs/smb/client/cifssmb.c | 4 +-
+ fs/smb/client/fs_context.c | 19 +-
+ fs/smb/client/fs_context.h | 18 +-
+ fs/smb/client/link.c | 13 +-
+ fs/smb/client/reparse.c | 2 +-
+ fs/smb/client/smb1ops.c | 2 +-
+ fs/smb/client/smb2inode.c | 5 +-
+ fs/smb/client/smb2ops.c | 5 +-
+ fs/smb/client/smbdirect.c | 124 +-
+ fs/smb/client/smbdirect.h | 4 -
+ include/linux/f2fs_fs.h | 2 +-
+ include/linux/fscrypt.h | 10 +-
+ include/linux/nfs_fs.h | 8 +
+ include/linux/nfs_fs_sb.h | 8 +-
+ include/linux/nfs_xdr.h | 57 +-
+ include/linux/sunrpc/xdr.h | 9 -
+ include/linux/wait.h | 12 +
+ lib/closure.c | 12 +-
+ net/sunrpc/auth_gss/gss_krb5_crypto.c | 4 +-
+ net/sunrpc/xdr.c | 110 -
+ tools/testing/selftests/Makefile | 1 +
+ .../testing/selftests/filesystems/fuse/.gitignore | 3 +
+ tools/testing/selftests/filesystems/fuse/Makefile | 21 +
+ .../testing/selftests/filesystems/fuse/fuse_mnt.c | 146 ++
+ .../selftests/filesystems/fuse/fusectl_test.c | 140 ++
+ 224 files changed, 9632 insertions(+), 8985 deletions(-)
+ rename Documentation/filesystems/{ => fuse}/fuse-io-uring.rst (100%)
+ rename Documentation/filesystems/{ => fuse}/fuse-io.rst (99%)
+ rename Documentation/filesystems/{ => fuse}/fuse-passthrough.rst (100%)
+ rename Documentation/filesystems/{ => fuse}/fuse.rst (95%)
+ create mode 100644 Documentation/filesystems/fuse/index.rst
+ create mode 100644 tools/testing/selftests/filesystems/fuse/.gitignore
+ create mode 100644 tools/testing/selftests/filesystems/fuse/Makefile
+ create mode 100644 tools/testing/selftests/filesystems/fuse/fuse_mnt.c
+ create mode 100644 tools/testing/selftests/filesystems/fuse/fusectl_test.c
+Merging printk/for-next (dcc3191a3dde Merge branch 'rework/ringbuffer-kunit-test' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/printk/linux.git printk/for-next
+Auto-merging init/Kconfig
+Merge made by the 'ort' strategy.
+ init/Kconfig | 12 +
+ kernel/printk/.kunitconfig | 3 +
+ kernel/printk/Makefile | 2 +
+ kernel/printk/printk_ringbuffer.c | 5 +
+ kernel/printk/printk_ringbuffer_kunit_test.c | 315 +++++++++++++++++++++++++++
+ 5 files changed, 337 insertions(+)
+ create mode 100644 kernel/printk/.kunitconfig
+ create mode 100644 kernel/printk/printk_ringbuffer_kunit_test.c
+Merging pci/next (0bd0a41a5120 Merge tag 'pci-v6.17-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/pci/pci)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/pci/pci.git pci/next
+Already up to date.
+Merging pstore/for-next/pstore (d679c2e1e8d9 pstore/zone: rewrite some comments for better understanding)
+$ git merge -m Merge branch 'for-next/pstore' of git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux.git pstore/for-next/pstore
+Merge made by the 'ort' strategy.
+ fs/pstore/zone.c | 21 +++++++++++----------
+ 1 file changed, 11 insertions(+), 10 deletions(-)
+Merging hid/for-next (1330eb33bddc Merge branch 'for-6.17/core' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/hid/hid.git hid/for-next
+Merge made by the 'ort' strategy.
+Merging i2c/i2c/for-next (976990f4120c Merge branch 'i2c/for-mergewindow' into i2c/for-next)
+$ git merge -m Merge branch 'i2c/for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/wsa/linux.git i2c/i2c/for-next
+Merge made by the 'ort' strategy.
+ .../devicetree/bindings/i2c/apple,i2c.yaml | 5 ++
+ drivers/i2c/busses/Kconfig | 1 -
+ drivers/i2c/busses/i2c-qcom-geni.c | 6 +-
+ drivers/i2c/busses/i2c-stm32f7.c | 32 +++++++----
+ drivers/i2c/busses/i2c-tegra.c | 64 +++++++++++++++-------
+ drivers/i2c/i2c-core-acpi.c | 1 +
+ drivers/i2c/muxes/i2c-mux-mule.c | 3 +-
+ 7 files changed, 75 insertions(+), 37 deletions(-)
+Merging i2c-host/i2c/i2c-host (85c34532849d i2c: qcom-geni: fix I2C frequency table to achieve accurate bus rates)
+$ git merge -m Merge branch 'i2c/i2c-host' of git://git.kernel.org/pub/scm/linux/kernel/git/andi.shyti/linux.git i2c-host/i2c/i2c-host
+Already up to date.
+Merging i3c/i3c/next (3b661ca549b9 i3c: add missing include to internal header)
+$ git merge -m Merge branch 'i3c/next' of git://git.kernel.org/pub/scm/linux/kernel/git/i3c/linux.git i3c/i3c/next
+Already up to date.
+Merging dmi/dmi-for-next (4d1b28a8119c firmware: dmi: Add info message for number of populated and total memory slots)
+$ git merge -m Merge branch 'dmi-for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/jdelvare/staging.git dmi/dmi-for-next
+Already up to date.
+Merging hwmon-staging/hwmon-next (de1fffd88600 dt-bindings: hwmon: Replace bouncing Alexandru Tachici emails)
+$ git merge -m Merge branch 'hwmon-next' of git://git.kernel.org/pub/scm/linux/kernel/git/groeck/linux-staging.git hwmon-staging/hwmon-next
+Already up to date.
+Merging jc_docs/docs-next (35293ebbb65e scripts: add origin commit identification based on specific patterns)
+$ git merge -m Merge branch 'docs-next' of git://git.lwn.net/linux.git jc_docs/docs-next
+Already up to date.
+Merging v4l-dvb/next (d968e50b5c26 media: rkvdec: Unstage the driver)
+$ git merge -m Merge branch 'next' of git://linuxtv.org/media-ci/media-pending.git v4l-dvb/next
+Already up to date.
+Merging v4l-dvb-next/master (b36c41c51e9d media: atomisp: set lock before calling vb2_queue_init())
+$ git merge -m Merge branch 'master' of git://linuxtv.org/mchehab/media-next.git v4l-dvb-next/master
+Already up to date.
+Merging pm/linux-next (77d832285656 Merge branch 'pm-cpufreq' into linux-next)
+$ git merge -m Merge branch 'linux-next' of git://git.kernel.org/pub/scm/linux/kernel/git/rafael/linux-pm.git pm/linux-next
+Merge made by the 'ort' strategy.
+Merging cpufreq-arm/cpufreq/arm/linux-next (bbd67be5546d cpufreq: mediatek-hw: Add support for MT8196)
+$ git merge -m Merge branch 'cpufreq/arm/linux-next' of git://git.kernel.org/pub/scm/linux/kernel/git/vireshk/pm.git cpufreq-arm/cpufreq/arm/linux-next
+Merge made by the 'ort' strategy.
+ .../cpufreq/mediatek,mt8196-cpufreq-hw.yaml | 82 +++++++++++++
+ drivers/cpufreq/mediatek-cpufreq-hw.c | 132 +++++++++++++++++----
+ 2 files changed, 191 insertions(+), 23 deletions(-)
+ create mode 100644 Documentation/devicetree/bindings/cpufreq/mediatek,mt8196-cpufreq-hw.yaml
+Merging cpupower/cpupower (e6c3f96141eb cpupower: Allow control of boost feature on non-x86 based systems with boost support.)
+$ git merge -m Merge branch 'cpupower' of git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux.git cpupower/cpupower
+Merge made by the 'ort' strategy.
+ tools/power/cpupower/man/cpupower-set.1 | 7 +--
+ tools/power/cpupower/utils/cpufreq-info.c | 16 +++++-
+ tools/power/cpupower/utils/cpupower-set.c | 5 +-
+ tools/power/cpupower/utils/helpers/helpers.h | 14 ++---
+ tools/power/cpupower/utils/helpers/misc.c | 76 ++++++++++++++++++++--------
+ 5 files changed, 83 insertions(+), 35 deletions(-)
+Merging devfreq/devfreq-next (7da2fdaaa1e6 PM / devfreq: Add HiSilicon uncore frequency scaling driver)
+$ git merge -m Merge branch 'devfreq-next' of git://git.kernel.org/pub/scm/linux/kernel/git/chanwoo/linux.git devfreq/devfreq-next
+Already up to date.
+Merging pmdomain/next (05e35bd07d56 pmdomain: qcom: rpmhpd: Add Glymur RPMh Power Domains)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/ulfh/linux-pm.git pmdomain/next
+Already up to date.
+Merging opp/opp/linux-next (22679d807dea rust: opp: use c_* types via kernel prelude)
+$ git merge -m Merge branch 'opp/linux-next' of git://git.kernel.org/pub/scm/linux/kernel/git/vireshk/pm.git opp/opp/linux-next
+Already up to date.
+Merging thermal/thermal/linux-next (1d264d3a1988 dt-bindings: thermal: tegra: Document Tegra210B01)
+$ git merge -m Merge branch 'thermal/linux-next' of git://git.kernel.org/pub/scm/linux/kernel/git/thermal/linux.git thermal/thermal/linux-next
+Already up to date.
+Merging rdma/for-next (ee235923d205 RDMA/siw: Change maintainer email address)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/rdma/rdma.git rdma/for-next
+Already up to date.
+Merging net-next/main (d9104cec3e8f Merge tag 'bpf-next-6.17' of git://git.kernel.org/pub/scm/linux/kernel/git/bpf/bpf-next)
+$ git merge -m Merge branch 'main' of git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net-next.git net-next/main
+Already up to date.
+Merging bpf-next/for-next (821c9e515db5 Merge tag 'for_linus' of git://git.kernel.org/pub/scm/linux/kernel/git/mst/vhost)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/bpf/bpf-next.git bpf-next/for-next
+Already up to date.
+Merging ipsec-next/master (95cfe23285a6 xfrm: Skip redundant statistics update for crypto offload)
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/klassert/ipsec-next.git ipsec-next/master
+Already up to date.
+Merging mlx5-next/mlx5-next (888a7776f4fb net/mlx5: Add support for device steering tag)
+$ git merge -m Merge branch 'mlx5-next' of git://git.kernel.org/pub/scm/linux/kernel/git/mellanox/linux.git mlx5-next/mlx5-next
+Already up to date.
+Merging netfilter-next/main (e3f96b3556e4 Merge branch 'net-dsa-microchip-add-ksz8463-switch-support')
+$ git merge -m Merge branch 'main' of git://git.kernel.org/pub/scm/linux/kernel/git/netfilter/nf-next.git netfilter-next/main
+Already up to date.
+Merging ipvs-next/main (e3f96b3556e4 Merge branch 'net-dsa-microchip-add-ksz8463-switch-support')
+$ git merge -m Merge branch 'main' of git://git.kernel.org/pub/scm/linux/kernel/git/horms/ipvs-next.git ipvs-next/main
+Already up to date.
+Merging bluetooth/master (df18778595f9 Bluetooth: btintel_pcie: Define hdev->wakeup() callback)
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/bluetooth/bluetooth-next.git bluetooth/master
+Merge made by the 'ort' strategy.
+ drivers/bluetooth/btintel.c | 3 ++
+ drivers/bluetooth/btintel_pcie.c | 103 +++++++++++++++++++++++++++++++++++++++
+ drivers/bluetooth/btmtk.c | 7 +--
+ drivers/bluetooth/btusb.c | 2 +
+ net/bluetooth/hci_conn.c | 14 +++++-
+ net/bluetooth/hci_event.c | 7 ++-
+ net/bluetooth/hci_sync.c | 9 ++--
+ net/bluetooth/iso.c | 2 +-
+ 8 files changed, 134 insertions(+), 13 deletions(-)
+Merging wireless-next/for-next (126d85fb0405 Merge tag 'wireless-next-2025-07-24' of https://git.kernel.org/pub/scm/linux/kernel/git/wireless/wireless-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/wireless/wireless-next.git wireless-next/for-next
+Already up to date.
+Merging ath-next/for-next (708243c62efd wifi: mac80211: fix unassigned variable access)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/ath/ath.git ath-next/for-next
+Already up to date.
+Merging iwlwifi-next/next (d2af710d6d50 wifi: iwlwifi: mvm/fw: Avoid -Wflex-array-member-not-at-end warnings)
+$ git merge -m Merge branch 'next' of https://git.kernel.org/pub/scm/linux/kernel/git/iwlwifi/iwlwifi-next.git iwlwifi-next/next
+Already up to date.
+Merging wpan-next/master (1dd9291eb903 ieee802154: Remove WARN_ON() in cfg802154_pernet_exit())
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/wpan/wpan-next.git wpan-next/master
+Merge made by the 'ort' strategy.
+ net/ieee802154/core.c | 49 ++++++++++++++++++++++++++++---------------------
+ 1 file changed, 28 insertions(+), 21 deletions(-)
+Merging wpan-staging/staging (1dd9291eb903 ieee802154: Remove WARN_ON() in cfg802154_pernet_exit())
+$ git merge -m Merge branch 'staging' of git://git.kernel.org/pub/scm/linux/kernel/git/wpan/wpan-next.git wpan-staging/staging
+Already up to date.
+Merging mtd/mtd/next (9cf9db888f38 Merge tag 'nand/for-6.17' into mtd/next)
+$ git merge -m Merge branch 'mtd/next' of git://git.kernel.org/pub/scm/linux/kernel/git/mtd/linux.git mtd/mtd/next
+Already up to date.
+Merging nand/nand/next (fb2fae70e7e9 mtd: spinand: winbond: Add comment about the maximum frequency)
+$ git merge -m Merge branch 'nand/next' of git://git.kernel.org/pub/scm/linux/kernel/git/mtd/linux.git nand/nand/next
+Already up to date.
+Merging spi-nor/spi-nor/next (2e3a7476ec39 mtd: spi-nor: Fix spi_nor_try_unlock_all())
+$ git merge -m Merge branch 'spi-nor/next' of git://git.kernel.org/pub/scm/linux/kernel/git/mtd/linux.git spi-nor/spi-nor/next
+Already up to date.
+Merging crypto/master (9d9b193ed73a crypto: hash - Increase HASH_MAX_DESCSIZE for hmac(sha3-224-s390))
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/herbert/cryptodev-2.6.git crypto/master
+Already up to date.
+Merging libcrypto/libcrypto-next (2a1a127aecf6 Merge branches 'libcrypto-conversions' and 'libcrypto-tests' into libcrypto-next)
+$ git merge -m Merge branch 'libcrypto-next' of git://git.kernel.org/pub/scm/linux/kernel/git/ebiggers/linux.git libcrypto/libcrypto-next
+Merge made by the 'ort' strategy.
+Merging drm/drm-next (6531a2cf07ef Merge tag 'drm-xe-next-fixes-2025-07-31' of https://gitlab.freedesktop.org/drm/xe/kernel into drm-next)
+$ git merge -m Merge branch 'drm-next' of https://gitlab.freedesktop.org/drm/kernel.git drm/drm-next
+Already up to date.
+Merging drm-exynos/for-linux-next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'for-linux-next' of git://git.kernel.org/pub/scm/linux/kernel/git/daeinki/drm-exynos.git drm-exynos/for-linux-next
+Already up to date.
+Merging drm-misc/for-linux-next (584460393efb drm/bridge: Describe the newly introduced drm_connector parameter for drm_bridge_detect)
+$ git merge -m Merge branch 'for-linux-next' of https://gitlab.freedesktop.org/drm/misc/kernel.git drm-misc/for-linux-next
+Merge made by the 'ort' strategy.
+ drivers/gpu/drm/bridge/aux-bridge.c | 2 ++
+ drivers/gpu/drm/drm_bridge.c | 1 +
+ 2 files changed, 3 insertions(+)
+Merging amdgpu/drm-next (1c2efae2f855 drm/amd/pm: Make static table support conditional)
+$ git merge -m Merge branch 'drm-next' of https://gitlab.freedesktop.org/agd5f/linux amdgpu/drm-next
+Auto-merging drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
+Auto-merging drivers/gpu/drm/amd/amdgpu/amdgpu_ras.c
+Auto-merging drivers/gpu/drm/amd/amdgpu/amdgpu_vram_mgr.c
+Auto-merging drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_hdcp.c
+Merge made by the 'ort' strategy.
+ .../gpu/amdgpu/amd-hardware-list-info.rst | 4 +-
+ Documentation/gpu/amdgpu/apu-asic-info-table.csv | 34 +--
+ Documentation/gpu/amdgpu/dgpu-asic-info-table.csv | 58 +++--
+ Documentation/gpu/amdgpu/display/dc-glossary.rst | 2 +-
+ .../gpu/amdgpu/display/display-contributing.rst | 4 +-
+ drivers/gpu/drm/amd/amdgpu/amdgpu_aca.c | 51 ++--
+ drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c | 7 +-
+ drivers/gpu/drm/amd/amdgpu/amdgpu_cper.c | 8 +-
+ drivers/gpu/drm/amd/amdgpu/amdgpu_cs.c | 20 +-
+ drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 45 ++--
+ drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c | 26 +-
+ drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c | 2 +-
+ drivers/gpu/drm/amd/amdgpu/amdgpu_gem.c | 37 +--
+ drivers/gpu/drm/amd/amdgpu/amdgpu_gem.h | 1 -
+ drivers/gpu/drm/amd/amdgpu/amdgpu_gmc.h | 15 +-
+ drivers/gpu/drm/amd/amdgpu/amdgpu_job.c | 7 -
+ drivers/gpu/drm/amd/amdgpu/amdgpu_nbio.c | 3 +-
+ drivers/gpu/drm/amd/amdgpu/amdgpu_object.h | 2 +-
+ drivers/gpu/drm/amd/amdgpu/amdgpu_ras.c | 282 +++++++++++++++++----
+ drivers/gpu/drm/amd/amdgpu/amdgpu_ras.h | 21 ++
+ drivers/gpu/drm/amd/amdgpu/amdgpu_ras_eeprom.c | 6 +-
+ drivers/gpu/drm/amd/amdgpu/amdgpu_reset.h | 11 +
+ drivers/gpu/drm/amd/amdgpu/amdgpu_seq64.c | 8 +-
+ drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c | 87 +++++++
+ drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.h | 8 +
+ drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c | 17 +-
+ drivers/gpu/drm/amd/amdgpu/amdgpu_vm.h | 4 +-
+ drivers/gpu/drm/amd/amdgpu/amdgpu_vram_mgr.c | 38 +++
+ drivers/gpu/drm/amd/amdgpu/amdgpu_vram_mgr.h | 17 ++
+ drivers/gpu/drm/amd/amdgpu/amdgpu_xcp.c | 1 +
+ drivers/gpu/drm/amd/amdgpu/aqua_vanjaram.c | 5 +-
+ drivers/gpu/drm/amd/amdgpu/gfx_v9_0.c | 3 +
+ drivers/gpu/drm/amd/amdgpu/gfx_v9_4_2.c | 12 +
+ drivers/gpu/drm/amd/amdgpu/gfx_v9_4_2.h | 1 +
+ drivers/gpu/drm/amd/amdgpu/gmc_v10_0.c | 57 ++---
+ drivers/gpu/drm/amd/amdgpu/gmc_v11_0.c | 57 ++---
+ drivers/gpu/drm/amd/amdgpu/gmc_v12_0.c | 47 ++--
+ drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c | 4 +-
+ drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c | 4 +-
+ drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c | 10 +-
+ drivers/gpu/drm/amd/amdgpu/gmc_v9_0.c | 61 +++--
+ drivers/gpu/drm/amd/amdgpu/jpeg_v4_0_3.c | 2 +-
+ drivers/gpu/drm/amd/amdgpu/jpeg_v5_0_1.c | 23 +-
+ drivers/gpu/drm/amd/amdgpu/mmhub_v3_0_1.c | 57 +++--
+ drivers/gpu/drm/amd/amdgpu/mmhub_v3_3.c | 121 ++++++++-
+ drivers/gpu/drm/amd/amdgpu/sdma_v7_0.c | 2 +-
+ drivers/gpu/drm/amd/amdgpu/soc15.c | 2 +
+ drivers/gpu/drm/amd/amdgpu/vcn_v2_0.c | 89 +------
+ drivers/gpu/drm/amd/amdgpu/vcn_v2_5.c | 93 ++-----
+ drivers/gpu/drm/amd/amdgpu/vcn_v3_0.c | 88 +------
+ drivers/gpu/drm/amd/amdgpu/vcn_v4_0.c | 90 +------
+ drivers/gpu/drm/amd/amdgpu/vcn_v4_0_3.c | 92 +------
+ drivers/gpu/drm/amd/amdgpu/vcn_v4_0_5.c | 90 +------
+ drivers/gpu/drm/amd/amdgpu/vcn_v5_0_0.c | 96 +------
+ drivers/gpu/drm/amd/amdgpu/vcn_v5_0_0.h | 5 -
+ drivers/gpu/drm/amd/amdgpu/vcn_v5_0_1.c | 72 +++++-
+ .../gpu/drm/amd/amdkfd/kfd_device_queue_manager.c | 2 +-
+ drivers/gpu/drm/amd/amdkfd/kfd_mqd_manager_v9.c | 61 ++++-
+ .../gpu/drm/amd/amdkfd/kfd_process_queue_manager.c | 20 +-
+ drivers/gpu/drm/amd/amdkfd/kfd_svm.c | 13 +-
+ drivers/gpu/drm/amd/amdxcp/amdgpu_xcp_drv.c | 56 +++-
+ drivers/gpu/drm/amd/amdxcp/amdgpu_xcp_drv.h | 1 +
+ drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 105 +++++---
+ drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h | 15 ++
+ .../drm/amd/display/amdgpu_dm/amdgpu_dm_color.c | 2 +-
+ .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c | 1 +
+ .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.h | 1 +
+ .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crtc.c | 9 +
+ .../drm/amd/display/amdgpu_dm/amdgpu_dm_debugfs.c | 35 ++-
+ .../drm/amd/display/amdgpu_dm/amdgpu_dm_debugfs.h | 1 +
+ .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_hdcp.c | 1 +
+ .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_hdcp.h | 1 +
+ .../drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c | 1 +
+ .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_irq.c | 1 +
+ .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_irq.h | 1 +
+ .../amd/display/amdgpu_dm/amdgpu_dm_irq_params.h | 1 +
+ .../amd/display/amdgpu_dm/amdgpu_dm_mst_types.c | 10 +-
+ .../amd/display/amdgpu_dm/amdgpu_dm_mst_types.h | 1 +
+ .../drm/amd/display/amdgpu_dm/amdgpu_dm_pp_smu.c | 1 +
+ .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_psr.c | 2 +-
+ .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_psr.h | 1 +
+ .../drm/amd/display/amdgpu_dm/amdgpu_dm_replay.c | 1 +
+ .../drm/amd/display/amdgpu_dm/amdgpu_dm_replay.h | 1 +
+ .../drm/amd/display/amdgpu_dm/amdgpu_dm_services.c | 1 +
+ .../drm/amd/display/amdgpu_dm/amdgpu_dm_trace.h | 1 +
+ drivers/gpu/drm/amd/display/dc/clk_mgr/clk_mgr.c | 1 -
+ .../amd/display/dc/clk_mgr/dce100/dce_clk_mgr.c | 5 +
+ .../drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c | 16 ++
+ drivers/gpu/drm/amd/display/dc/core/dc.c | 182 ++++---------
+ .../gpu/drm/amd/display/dc/core/dc_link_exports.c | 7 +
+ drivers/gpu/drm/amd/display/dc/core/dc_resource.c | 8 +-
+ drivers/gpu/drm/amd/display/dc/dc.h | 73 +++++-
+ drivers/gpu/drm/amd/display/dc/dc_dmub_srv.c | 4 +-
+ drivers/gpu/drm/amd/display/dc/dc_dp_types.h | 16 +-
+ drivers/gpu/drm/amd/display/dc/dc_helper.c | 2 +-
+ drivers/gpu/drm/amd/display/dc/dc_types.h | 14 +
+ drivers/gpu/drm/amd/display/dc/dce/dmub_replay.c | 56 ++--
+ drivers/gpu/drm/amd/display/dc/dce/dmub_replay.h | 2 +-
+ .../gpu/drm/amd/display/dc/dml/dcn301/dcn301_fpu.c | 20 +-
+ .../drm/amd/display/dc/hubbub/dcn30/dcn30_hubbub.c | 31 +++
+ .../drm/amd/display/dc/hubbub/dcn30/dcn30_hubbub.h | 6 +
+ .../drm/amd/display/dc/hubbub/dcn31/dcn31_hubbub.c | 2 +
+ .../drm/amd/display/dc/hubbub/dcn32/dcn32_hubbub.c | 2 +
+ .../drm/amd/display/dc/hubbub/dcn35/dcn35_hubbub.c | 2 +
+ .../amd/display/dc/hubbub/dcn401/dcn401_hubbub.c | 2 +
+ .../gpu/drm/amd/display/dc/hubp/dcn10/dcn10_hubp.h | 9 +-
+ .../gpu/drm/amd/display/dc/hubp/dcn20/dcn20_hubp.h | 1 +
+ .../gpu/drm/amd/display/dc/hubp/dcn30/dcn30_hubp.c | 26 ++
+ .../gpu/drm/amd/display/dc/hubp/dcn30/dcn30_hubp.h | 8 +-
+ .../gpu/drm/amd/display/dc/hubp/dcn31/dcn31_hubp.c | 15 ++
+ .../gpu/drm/amd/display/dc/hubp/dcn31/dcn31_hubp.h | 6 +-
+ .../gpu/drm/amd/display/dc/hubp/dcn32/dcn32_hubp.c | 3 +
+ .../gpu/drm/amd/display/dc/hubp/dcn35/dcn35_hubp.c | 3 +
+ .../drm/amd/display/dc/hubp/dcn401/dcn401_hubp.c | 41 +++
+ .../drm/amd/display/dc/hubp/dcn401/dcn401_hubp.h | 8 +-
+ .../drm/amd/display/dc/hwss/dce110/dce110_hwseq.c | 39 ++-
+ .../drm/amd/display/dc/hwss/dce110/dce110_hwseq.h | 7 +
+ .../drm/amd/display/dc/hwss/dcn10/dcn10_hwseq.c | 63 ++++-
+ .../drm/amd/display/dc/hwss/dcn20/dcn20_hwseq.c | 2 +
+ .../drm/amd/display/dc/hwss/dcn30/dcn30_hwseq.c | 48 ++++
+ .../drm/amd/display/dc/hwss/dcn30/dcn30_hwseq.h | 5 +
+ .../gpu/drm/amd/display/dc/hwss/dcn30/dcn30_init.c | 1 +
+ .../gpu/drm/amd/display/dc/hwss/dcn31/dcn31_init.c | 1 +
+ .../drm/amd/display/dc/hwss/dcn314/dcn314_init.c | 1 +
+ .../gpu/drm/amd/display/dc/hwss/dcn32/dcn32_init.c | 1 +
+ .../gpu/drm/amd/display/dc/hwss/dcn35/dcn35_init.c | 1 +
+ .../drm/amd/display/dc/hwss/dcn351/dcn351_init.c | 1 +
+ .../drm/amd/display/dc/hwss/dcn401/dcn401_hwseq.c | 34 ++-
+ .../drm/amd/display/dc/hwss/dcn401/dcn401_init.c | 1 +
+ drivers/gpu/drm/amd/display/dc/hwss/hw_sequencer.h | 4 +
+ drivers/gpu/drm/amd/display/dc/inc/core_types.h | 7 +-
+ drivers/gpu/drm/amd/display/dc/inc/hw/dchubbub.h | 2 +
+ drivers/gpu/drm/amd/display/dc/inc/hw/hubp.h | 21 +-
+ drivers/gpu/drm/amd/display/dc/inc/hw/mpc.h | 11 +
+ drivers/gpu/drm/amd/display/dc/inc/link.h | 5 +-
+ .../amd/display/dc/link/accessories/link_dp_cts.c | 30 ++-
+ drivers/gpu/drm/amd/display/dc/link/link_dpms.c | 3 -
+ drivers/gpu/drm/amd/display/dc/link/link_factory.c | 2 +
+ .../gpu/drm/amd/display/dc/link/link_validation.c | 6 +-
+ .../display/dc/link/protocols/link_dp_capability.c | 37 +++
+ .../display/dc/link/protocols/link_dp_capability.h | 6 +
+ .../display/dc/link/protocols/link_dp_dpia_bw.c | 71 +++---
+ .../display/dc/link/protocols/link_dp_training.c | 9 +-
+ .../dc/link/protocols/link_edp_panel_control.c | 10 +-
+ .../amd/display/dc/resource/dce60/dce60_resource.c | 34 ++-
+ .../amd/display/dc/resource/dcn31/dcn31_resource.c | 5 +-
+ .../amd/display/dc/resource/dcn31/dcn31_resource.h | 3 +-
+ .../amd/display/dc/resource/dcn32/dcn32_resource.h | 3 +-
+ .../display/dc/resource/dcn401/dcn401_resource.c | 1 +
+ .../display/dc/resource/dcn401/dcn401_resource.h | 3 +-
+ .../display/dc/virtual/virtual_stream_encoder.c | 7 +
+ drivers/gpu/drm/amd/display/dmub/dmub_srv.h | 1 +
+ drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h | 114 ++++++---
+ drivers/gpu/drm/amd/display/dmub/src/dmub_dcn31.c | 1 +
+ drivers/gpu/drm/amd/display/include/dal_asic_id.h | 5 +
+ drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c | 16 ++
+ drivers/gpu/drm/amd/pm/swsmu/smu11/arcturus_ppt.c | 2 +-
+ drivers/gpu/drm/amd/pm/swsmu/smu13/aldebaran_ppt.c | 2 +-
+ .../gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_6_ppt.c | 30 ++-
+ 159 files changed, 2171 insertions(+), 1412 deletions(-)
+Merging drm-intel/for-linux-next (5a569ef4d4ab drm/i915/display: Set C10_VDR_CTRL_MSGBUS_ACCESS before phy reg read)
+$ git merge -m Merge branch 'for-linux-next' of https://gitlab.freedesktop.org/drm/i915/kernel drm-intel/for-linux-next
+Merge made by the 'ort' strategy.
+ drivers/gpu/drm/i915/display/intel_cx0_phy.c | 21 +++++++++++++++------
+ 1 file changed, 15 insertions(+), 6 deletions(-)
+Merging drm-msm/msm-next (8290d37ad2b0 drm/msm: Small function param doc fix)
+$ git merge -m Merge branch 'msm-next' of https://gitlab.freedesktop.org/drm/msm.git drm-msm/msm-next
+Already up to date.
+Merging drm-msm-lumag/msm-next-lumag (cd86e80b77b2 drm/msm/dp: add linux/io.h header to fix build errors)
+$ git merge -m Merge branch 'msm-next-lumag' of https://gitlab.freedesktop.org/lumag/msm.git drm-msm-lumag/msm-next-lumag
+Already up to date.
+Merging drm-nova/nova-next (14ae91a81ec8 gpu: nova-core: fix bounds check in PmuLookupTableEntry::new)
+$ git merge -m Merge branch 'nova-next' of https://gitlab.freedesktop.org/drm/nova.git drm-nova/nova-next
+Already up to date.
+Merging drm-xe/drm-xe-next (bcddb12c0274 drm/xe: Extend wa_13012615864 to additional Xe2 and Xe3 platforms)
+$ git merge -m Merge branch 'drm-xe-next' of https://gitlab.freedesktop.org/drm/xe/kernel drm-xe/drm-xe-next
+Auto-merging drivers/gpu/drm/xe/Makefile
+Auto-merging drivers/gpu/drm/xe/display/xe_fb_pin.c
+Auto-merging drivers/gpu/drm/xe/display/xe_plane_initial.c
+Auto-merging drivers/gpu/drm/xe/xe_configfs.c
+Auto-merging drivers/gpu/drm/xe/xe_device.c
+Auto-merging drivers/gpu/drm/xe/xe_guc_submit.c
+Auto-merging drivers/gpu/drm/xe/xe_hw_engine_group.c
+Merge made by the 'ort' strategy.
+ drivers/gpu/drm/xe/Kconfig | 1 +
+ drivers/gpu/drm/xe/Makefile | 4 +
+ drivers/gpu/drm/xe/abi/guc_actions_abi.h | 8 +
+ drivers/gpu/drm/xe/abi/guc_errors_abi.h | 3 +
+ drivers/gpu/drm/xe/abi/guc_klvs_abi.h | 1 +
+ drivers/gpu/drm/xe/display/xe_fb_pin.c | 5 +-
+ drivers/gpu/drm/xe/display/xe_plane_initial.c | 3 +-
+ drivers/gpu/drm/xe/instructions/xe_mi_commands.h | 1 +
+ drivers/gpu/drm/xe/regs/xe_engine_regs.h | 3 +
+ drivers/gpu/drm/xe/regs/xe_gt_regs.h | 2 +-
+ drivers/gpu/drm/xe/regs/xe_pmt.h | 10 +
+ drivers/gpu/drm/xe/xe_assert.h | 4 +-
+ drivers/gpu/drm/xe/xe_bb.c | 35 +++
+ drivers/gpu/drm/xe/xe_bb.h | 3 +
+ drivers/gpu/drm/xe/xe_bo.c | 52 +++-
+ drivers/gpu/drm/xe/xe_bo.h | 4 +-
+ drivers/gpu/drm/xe/xe_bo_types.h | 4 +
+ drivers/gpu/drm/xe/xe_configfs.c | 15 +-
+ drivers/gpu/drm/xe/xe_debugfs.c | 107 +++++++
+ drivers/gpu/drm/xe/xe_dep_job_types.h | 29 ++
+ drivers/gpu/drm/xe/xe_dep_scheduler.c | 143 +++++++++
+ drivers/gpu/drm/xe/xe_dep_scheduler.h | 21 ++
+ drivers/gpu/drm/xe/xe_device.c | 32 +-
+ drivers/gpu/drm/xe/xe_device_types.h | 69 +----
+ drivers/gpu/drm/xe/xe_exec_queue.c | 96 ++++++
+ drivers/gpu/drm/xe/xe_exec_queue.h | 4 +
+ drivers/gpu/drm/xe/xe_exec_queue_types.h | 15 +
+ drivers/gpu/drm/xe/xe_ggtt.c | 3 +-
+ drivers/gpu/drm/xe/xe_gpu_scheduler.c | 13 +
+ drivers/gpu/drm/xe/xe_gpu_scheduler.h | 1 +
+ drivers/gpu/drm/xe/xe_gt.c | 16 +-
+ drivers/gpu/drm/xe/xe_gt_debugfs.c | 56 +++-
+ drivers/gpu/drm/xe/xe_gt_mcr.c | 4 +-
+ drivers/gpu/drm/xe/xe_gt_pagefault.c | 13 +-
+ drivers/gpu/drm/xe/xe_gt_sriov_pf.c | 79 ++++-
+ drivers/gpu/drm/xe/xe_gt_sriov_pf.h | 1 +
+ drivers/gpu/drm/xe/xe_gt_sriov_pf_config.c | 13 +-
+ drivers/gpu/drm/xe/xe_gt_sriov_pf_debugfs.c | 4 +-
+ drivers/gpu/drm/xe/xe_gt_sriov_vf.c | 14 +
+ drivers/gpu/drm/xe/xe_gt_sriov_vf.h | 1 +
+ drivers/gpu/drm/xe/xe_gt_tlb_inval_job.c | 274 +++++++++++++++++
+ drivers/gpu/drm/xe/xe_gt_tlb_inval_job.h | 34 +++
+ drivers/gpu/drm/xe/xe_gt_tlb_invalidation.c | 8 +
+ drivers/gpu/drm/xe/xe_gt_types.h | 2 +
+ drivers/gpu/drm/xe/xe_guc.c | 19 +-
+ drivers/gpu/drm/xe/xe_guc_ads.c | 35 +++
+ drivers/gpu/drm/xe/xe_guc_buf.c | 2 +-
+ drivers/gpu/drm/xe/xe_guc_capture.c | 6 +
+ drivers/gpu/drm/xe/xe_guc_fwif.h | 5 +
+ drivers/gpu/drm/xe/xe_guc_submit.c | 209 ++++++++++++-
+ drivers/gpu/drm/xe/xe_guc_submit.h | 10 +
+ drivers/gpu/drm/xe/xe_guc_types.h | 6 +
+ drivers/gpu/drm/xe/xe_hw_engine_group.c | 4 +-
+ drivers/gpu/drm/xe/xe_lrc.c | 172 ++++++++++-
+ drivers/gpu/drm/xe/xe_lrc.h | 9 +
+ drivers/gpu/drm/xe/xe_migrate.c | 301 +++++++++++++++---
+ drivers/gpu/drm/xe/xe_migrate.h | 24 +-
+ drivers/gpu/drm/xe/xe_mmio_gem.c | 226 ++++++++++++++
+ drivers/gpu/drm/xe/xe_mmio_gem.h | 20 ++
+ drivers/gpu/drm/xe/xe_module.c | 8 +-
+ drivers/gpu/drm/xe/xe_pci.c | 11 +
+ drivers/gpu/drm/xe/xe_pci_sriov.c | 7 +-
+ drivers/gpu/drm/xe/xe_pm.c | 4 +
+ drivers/gpu/drm/xe/xe_pt.c | 178 +++++------
+ drivers/gpu/drm/xe/xe_query.c | 9 +-
+ drivers/gpu/drm/xe/xe_ring_ops.c | 8 +-
+ drivers/gpu/drm/xe/xe_sa.c | 1 -
+ drivers/gpu/drm/xe/xe_sa.h | 15 +-
+ drivers/gpu/drm/xe/xe_sa_types.h | 1 -
+ drivers/gpu/drm/xe/xe_sriov.c | 19 ++
+ drivers/gpu/drm/xe/xe_sriov.h | 1 +
+ drivers/gpu/drm/xe/xe_sriov_pf.c | 27 ++
+ drivers/gpu/drm/xe/xe_sriov_pf.h | 1 +
+ drivers/gpu/drm/xe/xe_sriov_vf.c | 78 ++++-
+ drivers/gpu/drm/xe/xe_sriov_vf_ccs.c | 372 +++++++++++++++++++++++
+ drivers/gpu/drm/xe/xe_sriov_vf_ccs.h | 17 ++
+ drivers/gpu/drm/xe/xe_sriov_vf_ccs_types.h | 53 ++++
+ drivers/gpu/drm/xe/xe_sriov_vf_types.h | 6 +
+ drivers/gpu/drm/xe/xe_svm.c | 63 ++--
+ drivers/gpu/drm/xe/xe_tile.c | 62 ++--
+ drivers/gpu/drm/xe/xe_tile.h | 14 +-
+ drivers/gpu/drm/xe/xe_trace.h | 16 -
+ drivers/gpu/drm/xe/xe_ttm_stolen_mgr.c | 10 +-
+ drivers/gpu/drm/xe/xe_ttm_vram_mgr.c | 22 +-
+ drivers/gpu/drm/xe/xe_ttm_vram_mgr.h | 3 +-
+ drivers/gpu/drm/xe/xe_vm.c | 6 +-
+ drivers/gpu/drm/xe/xe_vram.c | 211 +++++++++----
+ drivers/gpu/drm/xe/xe_vram.h | 11 +
+ drivers/gpu/drm/xe/xe_vram_types.h | 85 ++++++
+ drivers/gpu/drm/xe/xe_wa.c | 13 +-
+ drivers/gpu/drm/xe/xe_wa_oob.rules | 3 +
+ include/uapi/drm/xe_drm.h | 6 +-
+ 92 files changed, 3133 insertions(+), 466 deletions(-)
+ create mode 100644 drivers/gpu/drm/xe/xe_dep_job_types.h
+ create mode 100644 drivers/gpu/drm/xe/xe_dep_scheduler.c
+ create mode 100644 drivers/gpu/drm/xe/xe_dep_scheduler.h
+ create mode 100644 drivers/gpu/drm/xe/xe_gt_tlb_inval_job.c
+ create mode 100644 drivers/gpu/drm/xe/xe_gt_tlb_inval_job.h
+ create mode 100644 drivers/gpu/drm/xe/xe_mmio_gem.c
+ create mode 100644 drivers/gpu/drm/xe/xe_mmio_gem.h
+ create mode 100644 drivers/gpu/drm/xe/xe_sriov_vf_ccs.c
+ create mode 100644 drivers/gpu/drm/xe/xe_sriov_vf_ccs.h
+ create mode 100644 drivers/gpu/drm/xe/xe_sriov_vf_ccs_types.h
+ create mode 100644 drivers/gpu/drm/xe/xe_vram_types.h
+Merging etnaviv/etnaviv/next (6bde14ba5f7e drm/etnaviv: add optional reset support)
+$ git merge -m Merge branch 'etnaviv/next' of https://git.pengutronix.de/git/lst/linux etnaviv/etnaviv/next
+Already up to date.
+Merging fbdev/for-next (e4fc307d8e24 Revert "vgacon: Add check for vc_origin address range in vgacon_scroll()")
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/deller/linux-fbdev.git fbdev/for-next
+Auto-merging drivers/video/fbdev/core/fbcon.c
+Merge made by the 'ort' strategy.
+ drivers/video/console/vgacon.c | 2 +-
+ drivers/video/fbdev/core/fbcon.c | 9 +++++----
+ 2 files changed, 6 insertions(+), 5 deletions(-)
+Merging regmap/for-next (067aa458a064 Merge remote-tracking branch 'regmap/for-6.16' into regmap-linus)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/broonie/regmap.git regmap/for-next
+Already up to date.
+Merging sound/for-next (dbe05428c4e5 ALSA: hda/realtek: add LG gram 16Z90R-A to alc269 fixup table)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/tiwai/sound.git sound/for-next
+Already up to date.
+Merging ieee1394/for-next (95a042a0c8ec firewire: ohci: reduce the size of common context structure by extracting members into AT structure)
+$ git merge -m Merge branch 'for-next' of https://git.kernel.org/pub/scm/linux/kernel/git/ieee1394/linux1394.git ieee1394/for-next
+Already up to date.
+Merging sound-asoc/for-next (282528da82a0 Merge remote-tracking branch 'asoc/for-6.16' into asoc-linus)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/broonie/sound.git sound-asoc/for-next
+Already up to date.
+Merging modules/modules-next (40a826bd6c82 module: Rename MAX_PARAM_PREFIX_LEN to __MODULE_NAME_LEN)
+$ git merge -m Merge branch 'modules-next' of git://git.kernel.org/pub/scm/linux/kernel/git/modules/linux.git modules/modules-next
+Already up to date.
+Merging input/next (a7bee4e7f780 Merge tag 'ib-mfd-gpio-input-pwm-v6.17' of git://git.kernel.org/pub/scm/linux/kernel/git/lee/mfd into next)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/dtor/input.git input/next
+Auto-merging MAINTAINERS
+Auto-merging drivers/hid/hid-debug.c
+Auto-merging drivers/input/joystick/xpad.c
+Auto-merging drivers/input/keyboard/atkbd.c
+Auto-merging drivers/input/misc/cs40l50-vibra.c
+Merge made by the 'ort' strategy.
+ .../devicetree/bindings/input/syna,rmi4.yaml | 20 ++
+ .../bindings/input/touchscreen/edt-ft5x06.yaml | 1 +
+ .../bindings/input/touchscreen/lpc32xx-tsc.txt | 16 --
+ .../input/touchscreen/nxp,lpc3220-tsc.yaml | 43 ++++
+ .../input/touchscreen/sitronix,st1232.yaml | 29 +++
+ .../bindings/input/touchscreen/ti.tsc2007.yaml | 75 ++++++
+ .../bindings/input/touchscreen/touchscreen.yaml | 119 +++++++++
+ .../bindings/input/touchscreen/tsc2007.txt | 39 ---
+ Documentation/input/devices/edt-ft5x06.rst | 21 +-
+ Documentation/input/gamepad.rst | 19 +-
+ Documentation/userspace-api/media/rc/rc-protos.rst | 4 +-
+ MAINTAINERS | 7 +
+ drivers/hid/hid-debug.c | 2 +
+ drivers/input/Makefile | 2 +-
+ drivers/input/evdev.c | 8 +-
+ drivers/input/input.c | 2 +-
+ drivers/input/joystick/xpad.c | 64 ++---
+ drivers/input/keyboard/adp5588-keys.c | 9 +-
+ drivers/input/keyboard/atkbd.c | 12 +-
+ drivers/input/keyboard/mtk-pmic-keys.c | 17 ++
+ drivers/input/keyboard/samsung-keypad.c | 137 +++++-----
+ drivers/input/misc/Kconfig | 7 -
+ drivers/input/misc/Makefile | 1 -
+ drivers/input/misc/cs40l50-vibra.c | 1 -
+ drivers/input/misc/max77693-haptic.c | 41 ++-
+ drivers/input/misc/max8997_haptic.c | 98 ++++----
+ drivers/input/misc/pcf50633-input.c | 113 ---------
+ drivers/input/rmi4/Kconfig | 15 ++
+ drivers/input/rmi4/Makefile | 2 +
+ drivers/input/rmi4/rmi_bus.c | 6 +
+ drivers/input/rmi4/rmi_driver.h | 2 +
+ drivers/input/rmi4/rmi_f1a.c | 143 +++++++++++
+ drivers/input/rmi4/rmi_f21.c | 179 +++++++++++++
+ drivers/input/touch-overlay.c | 277 +++++++++++++++++++++
+ drivers/input/touchscreen/ad7879.c | 11 +-
+ drivers/input/touchscreen/edt-ft5x06.c | 26 +-
+ drivers/input/touchscreen/goodix.c | 50 +++-
+ drivers/input/touchscreen/st1232.c | 35 ++-
+ include/linux/input/touch-overlay.h | 25 ++
+ include/uapi/linux/input-event-codes.h | 5 +
+ 40 files changed, 1277 insertions(+), 406 deletions(-)
+ delete mode 100644 Documentation/devicetree/bindings/input/touchscreen/lpc32xx-tsc.txt
+ create mode 100644 Documentation/devicetree/bindings/input/touchscreen/nxp,lpc3220-tsc.yaml
+ create mode 100644 Documentation/devicetree/bindings/input/touchscreen/ti.tsc2007.yaml
+ delete mode 100644 Documentation/devicetree/bindings/input/touchscreen/tsc2007.txt
+ delete mode 100644 drivers/input/misc/pcf50633-input.c
+ create mode 100644 drivers/input/rmi4/rmi_f1a.c
+ create mode 100644 drivers/input/rmi4/rmi_f21.c
+ create mode 100644 drivers/input/touch-overlay.c
+ create mode 100644 include/linux/input/touch-overlay.h
+Merging block/for-next (20c74c073217 Merge branch 'block-6.17' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.dk/linux-block.git block/for-next
+Auto-merging drivers/md/dm-raid.c
+Merge made by the 'ort' strategy.
+ block/bfq-iosched.c | 31 +-----
+ block/bfq-iosched.h | 10 +-
+ block/blk-ioc.c | 16 ++-
+ block/blk-mq-sched.c | 223 ++++++++++++++++++++++++++++-------------
+ block/blk-mq-sched.h | 12 ++-
+ block/blk-mq.c | 16 ++-
+ block/blk-settings.c | 33 ++++--
+ block/blk.h | 4 +-
+ block/elevator.c | 38 +++++--
+ block/elevator.h | 16 ++-
+ block/kyber-iosched.c | 11 +-
+ block/mq-deadline.c | 14 +--
+ drivers/block/zloop.c | 3 +-
+ drivers/md/dm-raid.c | 42 ++++----
+ drivers/md/md-bitmap.c | 8 +-
+ drivers/md/md-cluster.c | 16 +--
+ drivers/md/md.c | 73 ++++++++------
+ drivers/md/md.h | 2 +-
+ drivers/md/raid0.c | 6 +-
+ drivers/md/raid1-10.c | 2 +-
+ drivers/md/raid1.c | 94 +++++++----------
+ drivers/md/raid1.h | 22 +---
+ drivers/md/raid10.c | 16 +--
+ drivers/md/raid5-ppl.c | 6 +-
+ drivers/md/raid5.c | 30 +++---
+ drivers/nvme/host/auth.c | 4 +-
+ drivers/nvme/host/core.c | 16 +++
+ drivers/nvme/host/fc.c | 4 +-
+ drivers/nvme/host/pci.c | 2 +-
+ drivers/nvme/host/tcp.c | 2 +-
+ drivers/nvme/target/core.c | 16 +--
+ drivers/nvme/target/fc.c | 6 +-
+ drivers/nvme/target/passthru.c | 2 +
+ drivers/nvme/target/rdma.c | 6 +-
+ include/linux/ioprio.h | 3 +-
+ include/uapi/linux/io_uring.h | 4 +
+ include/uapi/linux/raid/md_p.h | 2 +-
+ io_uring/net.c | 9 +-
+ 38 files changed, 465 insertions(+), 355 deletions(-)
+Merging device-mapper/for-next (55a0fbd2ac3f dm: set DM_TARGET_PASSES_CRYPTO feature for dm-thin)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/device-mapper/linux-dm.git device-mapper/for-next
+Already up to date.
+Merging libata/for-next (6cb43739b93c ata: pata_pdc2027x: Remove space before newline and abbreviations)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/libata/linux libata/for-next
+Merge made by the 'ort' strategy.
+ drivers/ata/ata_piix.c | 1 +
+ drivers/ata/libahci.c | 1 +
+ drivers/ata/libata-core.c | 2 +-
+ drivers/ata/libata-sata.c | 53 +++++++++++++++++++++++++++++++++++----------
+ drivers/ata/libata-scsi.c | 38 ++++++++++++++++----------------
+ drivers/ata/pata_macio.c | 2 +-
+ drivers/ata/pata_pdc2027x.c | 12 +++++-----
+ include/linux/libata.h | 1 +
+ 8 files changed, 71 insertions(+), 39 deletions(-)
+Merging pcmcia/pcmcia-next (0630e3bc0e91 pcmcia: add missing MODULE_DESCRIPTION() macros)
+$ git merge -m Merge branch 'pcmcia-next' of git://git.kernel.org/pub/scm/linux/kernel/git/brodo/linux.git pcmcia/pcmcia-next
+Already up to date.
+Merging mmc/next (4b290aae788e Merge tag 'sysctl-6.17-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/sysctl/sysctl)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/ulfh/mmc.git mmc/next
+Already up to date.
+Merging mfd/for-mfd-next (b6bf74c82178 mfd: dt-bindings: Convert TPS65910 to DT schema)
+$ git merge -m Merge branch 'for-mfd-next' of git://git.kernel.org/pub/scm/linux/kernel/git/lee/mfd.git mfd/for-mfd-next
+Auto-merging drivers/mfd/Kconfig
+Merge made by the 'ort' strategy.
+ drivers/mfd/Kconfig | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+Merging backlight/for-backlight-next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'for-backlight-next' of git://git.kernel.org/pub/scm/linux/kernel/git/lee/backlight.git backlight/for-backlight-next
+Already up to date.
+Merging battery/for-next (7b41a2341fa6 power: supply: core: fix static checker warning)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/sre/linux-power-supply.git battery/for-next
+Already up to date.
+Merging regulator/for-next (10dfd36f0784 regulator: core: correct convergence check in regulator_set_voltage())
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/broonie/regulator.git regulator/for-next
+Already up to date.
+Merging security/next (5d8b97c94677 MAINTAINERS: Add Xiu and myself as Lockdown maintainers)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/pcmoore/lsm.git security/next
+Already up to date.
+Merging apparmor/apparmor-next (5f49c2d1f422 apparmor: fix: oops when trying to free null ruleset)
+$ git merge -m Merge branch 'apparmor-next' of git://git.kernel.org/pub/scm/linux/kernel/git/jj/linux-apparmor apparmor/apparmor-next
+Already up to date.
+Merging integrity/next-integrity (aa9bb1b32594 ima: add a knob ima= to allow disabling IMA in kdump kernel)
+$ git merge -m Merge branch 'next-integrity' of git://git.kernel.org/pub/scm/linux/kernel/git/zohar/linux-integrity integrity/next-integrity
+Already up to date.
+Merging selinux/next (850dada4b3af Automated merge of 'dev' into 'next')
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/pcmoore/selinux.git selinux/next
+Merge made by the 'ort' strategy.
+Merging smack/next (6ddd169d0288 smack: fix kernel-doc warnings for smk_import_valid_label())
+$ git merge -m Merge branch 'next' of git://github.com/cschaufler/smack-next smack/next
+Merge made by the 'ort' strategy.
+ Documentation/admin-guide/LSM/Smack.rst | 16 +-
+ security/smack/smack.h | 3 +
+ security/smack/smack_access.c | 95 ++++++++---
+ security/smack/smack_lsm.c | 277 +++++++++++++++++++++-----------
+ 4 files changed, 273 insertions(+), 118 deletions(-)
+Merging tomoyo/master (038d61fd6422 Linux 6.16)
+$ git merge -m Merge branch 'master' of git://git.code.sf.net/p/tomoyo/tomoyo.git tomoyo/master
+Already up to date.
+Merging tpmdd/next (7f0c6675b319 tpm_crb_ffa: handle tpm busy return code)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/jarkko/linux-tpmdd.git tpmdd/next
+Already up to date.
+Merging watchdog/master (48defdf6b083 watchdog: sbsa: Adjust keepalive timeout to avoid MediaTek WS0 race condition)
+$ git merge -m Merge branch 'master' of git://www.linux-watchdog.org/linux-watchdog-next.git watchdog/master
+Already up to date.
+Merging iommu/next (b9e6e8ae0a5f Merge branch 'arm/smmu/updates' into next)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/iommu/linux.git iommu/next
+Already up to date.
+Merging audit/next (ae1ae11fb277 audit,module: restore audit logging in load failure case)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/pcmoore/audit.git audit/next
+Already up to date.
+Merging devicetree/for-next (0121898ec05f dt-bindings: Correct indentation and style in DTS example)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/robh/linux.git devicetree/for-next
+Already up to date.
+Merging dt-krzk/for-next (6cd594ed969d ARM: dts: vt8500: Add L2 cache controller on WM8850/WM8950)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux-dt.git dt-krzk/for-next
+Already up to date.
+Merging mailbox/for-next (872798f61d8b dt-bindings: mailbox: qcom-ipcc: document the SM7635 Inter-Processor Communication Controller)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/jassibrar/mailbox.git mailbox/for-next
+Auto-merging Documentation/devicetree/bindings/mailbox/nvidia,tegra186-hsp.yaml
+Auto-merging drivers/mailbox/Kconfig
+CONFLICT (content): Merge conflict in drivers/mailbox/Kconfig
+Auto-merging drivers/mailbox/Makefile
+CONFLICT (content): Merge conflict in drivers/mailbox/Makefile
+Resolved 'drivers/mailbox/Kconfig' using previous resolution.
+Resolved 'drivers/mailbox/Makefile' using previous resolution.
+Automatic merge failed; fix conflicts and then commit the result.
+$ git commit --no-edit -v -a
+[master 8f18ef7a57ef] Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/jassibrar/mailbox.git
+$ git diff -M --stat --summary HEAD^..
+ .../mailbox/allwinner,sun6i-a31-msgbox.yaml | 14 +-
+ .../bindings/mailbox/amlogic,meson-gxbb-mhu.yaml | 10 +-
+ .../devicetree/bindings/mailbox/apple,mailbox.yaml | 16 +-
+ .../bindings/mailbox/brcm,bcm74110-mbox.yaml | 64 ++
+ .../bindings/mailbox/nvidia,tegra186-hsp.yaml | 9 +-
+ .../bindings/mailbox/qcom,apcs-kpss-global.yaml | 9 +-
+ .../devicetree/bindings/mailbox/qcom-ipcc.yaml | 2 +
+ .../bindings/mailbox/ti,omap-mailbox.yaml | 10 +-
+ .../bindings/mailbox/ti,secure-proxy.yaml | 18 +-
+ drivers/mailbox/Kconfig | 10 +
+ drivers/mailbox/Makefile | 2 +
+ drivers/mailbox/bcm74110-mailbox.c | 656 +++++++++++++++++++++
+ drivers/mailbox/mtk-cmdq-mailbox.c | 10 +-
+ drivers/mailbox/qcom-ipcc.c | 3 +-
+ 14 files changed, 774 insertions(+), 59 deletions(-)
+ create mode 100644 Documentation/devicetree/bindings/mailbox/brcm,bcm74110-mbox.yaml
+ create mode 100644 drivers/mailbox/bcm74110-mailbox.c
+Merging spi/for-next (a49bfbecfde7 Merge remote-tracking branch 'spi/for-6.16' into spi-linus)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/broonie/spi.git spi/for-next
+Already up to date.
+Merging tip/master (40d6e791ba3a Merge branch into tip/master: 'timers/clocksource')
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip.git tip/master
+Auto-merging arch/riscv/include/asm/bug.h
+CONFLICT (content): Merge conflict in arch/riscv/include/asm/bug.h
+Auto-merging arch/x86/include/asm/bug.h
+CONFLICT (content): Merge conflict in arch/x86/include/asm/bug.h
+Auto-merging drivers/of/irq.c
+Auto-merging kernel/panic.c
+Auto-merging lib/Kconfig.debug
+Resolved 'arch/riscv/include/asm/bug.h' using previous resolution.
+Resolved 'arch/x86/include/asm/bug.h' using previous resolution.
+Automatic merge failed; fix conflicts and then commit the result.
+$ git commit --no-edit -v -a
+[master c5ecd1e52ab4] Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip.git
+$ git diff -M --stat --summary HEAD^..
+ .../devicetree/bindings/timer/faraday,fttmr010.txt | 38 ---------
+ .../bindings/timer/faraday,fttmr010.yaml | 89 ++++++++++++++++++++
+ .../devicetree/bindings/timer/fsl,ftm-timer.yaml | 7 +-
+ .../devicetree/bindings/timer/fsl,timrot.yaml | 48 +++++++++++
+ .../devicetree/bindings/timer/mediatek,timer.yaml | 2 +
+ arch/arm64/include/asm/bug.h | 2 +-
+ arch/loongarch/include/asm/bug.h | 27 +++---
+ arch/parisc/include/asm/bug.h | 6 +-
+ arch/powerpc/include/asm/bug.h | 12 +--
+ arch/riscv/include/asm/bug.h | 10 +--
+ arch/s390/include/asm/bug.h | 96 +++++++++-------------
+ arch/sh/include/asm/bug.h | 4 +-
+ arch/x86/include/asm/bug.h | 12 +--
+ drivers/clocksource/exynos_mct.c | 24 ++++--
+ drivers/clocksource/scx200_hrt.c | 1 +
+ drivers/clocksource/timer-cs5535.c | 1 +
+ drivers/clocksource/timer-econet-en751221.c | 2 +-
+ drivers/clocksource/timer-nxp-stm.c | 2 +
+ drivers/clocksource/timer-stm32-lp.c | 1 +
+ drivers/clocksource/timer-sun5i.c | 2 +
+ drivers/clocksource/timer-tegra186.c | 30 ++++---
+ drivers/of/irq.c | 1 +
+ include/asm-generic/bug.h | 13 ++-
+ kernel/panic.c | 16 ++--
+ kernel/time/sched_clock.c | 4 +-
+ lib/Kconfig.debug | 10 +++
+ 26 files changed, 299 insertions(+), 161 deletions(-)
+ delete mode 100644 Documentation/devicetree/bindings/timer/faraday,fttmr010.txt
+ create mode 100644 Documentation/devicetree/bindings/timer/faraday,fttmr010.yaml
+ create mode 100644 Documentation/devicetree/bindings/timer/fsl,timrot.yaml
+Merging clockevents/timers/drivers/next (d7b8f8e20813 Linux 6.16-rc5)
+$ git merge -m Merge branch 'timers/drivers/next' of git://git.kernel.org/pub/scm/linux/kernel/git/daniel.lezcano/linux.git clockevents/timers/drivers/next
+Already up to date.
+Merging edac/edac-for-next (1fb0ddddf5d1 Merge branch 'edac-drivers' into edac-for-next)
+$ git merge -m Merge branch 'edac-for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/ras/ras.git edac/edac-for-next
+Auto-merging drivers/edac/mem_repair.c
+CONFLICT (content): Merge conflict in drivers/edac/mem_repair.c
+Resolved 'drivers/edac/mem_repair.c' using previous resolution.
+Automatic merge failed; fix conflicts and then commit the result.
+$ git commit --no-edit -v -a
+[master a94726fef172] Merge branch 'edac-for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/ras/ras.git
+$ git diff -M --stat --summary HEAD^..
+
+Merging ftrace/for-next (39f069d5a466 Merge unwind/for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git ftrace/for-next
+Merge made by the 'ort' strategy.
+Merging rcu/next (cc1d1365f0f4 Merge branches 'rcu-exp.23.07.2025', 'rcu.22.07.2025', 'torture-scripts.16.07.2025', 'srcu.19.07.2025', 'rcu.nocb.18.07.2025' and 'refscale.07.07.2025' into rcu.merge.23.07.2025)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/rcu/linux.git rcu/next
+Already up to date.
+Merging paulmck/non-rcu/next (b706eec9304f Merge branches 'lkmm.2025.07.09a', 'ratelimit.2025.06.24a' and 'stop-machine.2025.07.17a' into HEAD)
+$ git merge -m Merge branch 'non-rcu/next' of git://git.kernel.org/pub/scm/linux/kernel/git/paulmck/linux-rcu.git paulmck/non-rcu/next
+Merge made by the 'ort' strategy.
+Merging kvm/next (196d9e72c4b0 Merge tag 'kvm-s390-next-6.17-1' of https://git.kernel.org/pub/scm/linux/kernel/git/kvms390/linux into HEAD)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/virt/kvm/kvm.git kvm/next
+Already up to date.
+Merging kvm-arm/next (7b8346bd9fce KVM: arm64: Don't attempt vLPI mappings when vPE allocation is disabled)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/kvmarm/kvmarm.git kvm-arm/next
+Merge made by the 'ort' strategy.
+ arch/arm64/kvm/vgic/vgic-mmio-v3.c | 8 ++++++++
+ arch/arm64/kvm/vgic/vgic.h | 10 +---------
+ 2 files changed, 9 insertions(+), 9 deletions(-)
+Merging kvms390/next (57d88f02eb44 KVM: s390: Rework guest entry logic)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/kvms390/linux.git kvms390/next
+Already up to date.
+Merging kvm-ppc/topic/ppc-kvm (fac04efc5c79 Linux 6.13-rc2)
+$ git merge -m Merge branch 'topic/ppc-kvm' of git://git.kernel.org/pub/scm/linux/kernel/git/powerpc/linux.git kvm-ppc/topic/ppc-kvm
+Already up to date.
+Merging kvm-riscv/riscv_kvm_next (07a289a03140 RISC-V: KVM: Avoid re-acquiring memslot in kvm_riscv_gstage_map())
+$ git merge -m Merge branch 'riscv_kvm_next' of https://github.com/kvm-riscv/linux.git kvm-riscv/riscv_kvm_next
+Already up to date.
+Merging kvm-x86/next (33f843444e28 Merge branch 'vmx')
+$ git merge -m Merge branch 'next' of https://github.com/kvm-x86/linux.git kvm-x86/next
+Merge made by the 'ort' strategy.
+ Documentation/virt/kvm/x86/intel-tdx.rst | 22 ++++++++++++++++++-
+ arch/x86/include/uapi/asm/kvm.h | 7 ++++++-
+ arch/x86/kvm/vmx/tdx.c | 36 +++++++++++++++++++++++++-------
+ 3 files changed, 55 insertions(+), 10 deletions(-)
+Merging xen-tip/linux-next (114a2de6fa86 xen/netfront: Fix TX response spurious interrupts)
+$ git merge -m Merge branch 'linux-next' of git://git.kernel.org/pub/scm/linux/kernel/git/xen/tip.git xen-tip/linux-next
+Already up to date.
+Merging percpu/for-next (87d6aab2389e Merge tag 'for_linus' of git://git.kernel.org/pub/scm/linux/kernel/git/mst/vhost)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/dennis/percpu.git percpu/for-next
+Already up to date.
+Merging workqueues/for-next (324cee0c272c Merge branch 'for-6.17' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/tj/wq.git workqueues/for-next
+Merge made by the 'ort' strategy.
+Merging sched-ext/for-next (9f0744a0e87e Merge branch 'for-6.17' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/tj/sched_ext.git sched-ext/for-next
+Merge made by the 'ort' strategy.
+Merging drivers-x86/for-next (1798561befd8 platform/x86: oxpec: Add support for OneXPlayer X1 Mini Pro (Strix Point))
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/pdx86/platform-drivers-x86.git drivers-x86/for-next
+Already up to date.
+Merging chrome-platform/for-next (cc2d5b72b13b platform/chrome: Fix typo in CROS_USBPD_NOTIFY help text)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/chrome-platform/linux.git chrome-platform/for-next
+Already up to date.
+Merging chrome-platform-firmware/for-firmware-next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'for-firmware-next' of git://git.kernel.org/pub/scm/linux/kernel/git/chrome-platform/linux.git chrome-platform-firmware/for-firmware-next
+Already up to date.
+Merging hsi/for-next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/sre/linux-hsi.git hsi/for-next
+Already up to date.
+Merging leds-lj/for-leds-next (4903924ac7ef dt-bindings: leds: ncp5623: Add 0x39 as a valid I2C address)
+$ git merge -m Merge branch 'for-leds-next' of git://git.kernel.org/pub/scm/linux/kernel/git/lee/leds.git leds-lj/for-leds-next
+Already up to date.
+Merging ipmi/for-next (ec50ec378e3f ipmi: Use dev_warn_ratelimited() for incorrect message warnings)
+$ git merge -m Merge branch 'for-next' of git://github.com/cminyard/linux-ipmi.git ipmi/for-next
+Auto-merging drivers/char/ipmi/ipmi_si_intf.c
+Merge made by the 'ort' strategy.
+ drivers/char/ipmi/ipmi_msghandler.c | 8 ++---
+ drivers/char/ipmi/ipmi_si_intf.c | 4 ---
+ drivers/char/ipmi/ipmi_watchdog.c | 59 ++++++++++++++++++++++++++-----------
+ 3 files changed, 46 insertions(+), 25 deletions(-)
+Merging driver-core/driver-core-next (d632ab86aff2 Merge tag 'for-6.17/dm-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/device-mapper/linux-dm)
+$ git merge -m Merge branch 'driver-core-next' of git://git.kernel.org/pub/scm/linux/kernel/git/driver-core/driver-core.git driver-core/driver-core-next
+Already up to date.
+Merging usb/usb-next (d632ab86aff2 Merge tag 'for-6.17/dm-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/device-mapper/linux-dm)
+$ git merge -m Merge branch 'usb-next' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/usb.git usb/usb-next
+Already up to date.
+Merging thunderbolt/next (2d1beba54fda thunderbolt: Fix typos in documentation comments)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/westeri/thunderbolt.git thunderbolt/next
+Already up to date.
+Merging usb-serial/usb-next (bdf2ab177e2f USB: serial: cp210x: use new GPIO line value setter callbacks)
+$ git merge -m Merge branch 'usb-next' of git://git.kernel.org/pub/scm/linux/kernel/git/johan/usb-serial.git usb-serial/usb-next
+Already up to date.
+Merging tty/tty-next (89748acdf226 Merge tag 'drm-next-2025-08-01' of https://gitlab.freedesktop.org/drm/kernel)
+$ git merge -m Merge branch 'tty-next' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/tty.git tty/tty-next
+Already up to date.
+Merging char-misc/char-misc-next (d632ab86aff2 Merge tag 'for-6.17/dm-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/device-mapper/linux-dm)
+$ git merge -m Merge branch 'char-misc-next' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/char-misc.git char-misc/char-misc-next
+Already up to date.
+Merging accel/habanalabs-next (f03eee5fc922 Merge tag 'drm-xe-next-fixes-2024-05-02' of https://gitlab.freedesktop.org/drm/xe/kernel into drm-next)
+$ git merge -m Merge branch 'habanalabs-next' of git://git.kernel.org/pub/scm/linux/kernel/git/ogabbay/linux.git accel/habanalabs-next
+Already up to date.
+Merging coresight/next (a80198ba650f coresight: fix indentation error in cscfg_remove_owned_csdev_configs())
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/coresight/linux.git coresight/next
+Merge made by the 'ort' strategy.
+ .../bindings/arm/qcom,coresight-tnoc.yaml | 113 ++++++++++
+ drivers/hwtracing/coresight/Kconfig | 12 +
+ drivers/hwtracing/coresight/Makefile | 1 +
+ drivers/hwtracing/coresight/coresight-core.c | 6 +-
+ drivers/hwtracing/coresight/coresight-etm-perf.c | 4 +-
+ drivers/hwtracing/coresight/coresight-etm4x-core.c | 1 +
+ .../hwtracing/coresight/coresight-etm4x-sysfs.c | 1 +
+ drivers/hwtracing/coresight/coresight-stm.c | 8 +-
+ drivers/hwtracing/coresight/coresight-syscfg.c | 2 +-
+ drivers/hwtracing/coresight/coresight-tmc-core.c | 22 +-
+ drivers/hwtracing/coresight/coresight-tnoc.c | 242 +++++++++++++++++++++
+ drivers/hwtracing/coresight/coresight-trbe.c | 1 +
+ drivers/hwtracing/coresight/ultrasoc-smb.h | 1 +
+ 13 files changed, 389 insertions(+), 25 deletions(-)
+ create mode 100644 Documentation/devicetree/bindings/arm/qcom,coresight-tnoc.yaml
+ create mode 100644 drivers/hwtracing/coresight/coresight-tnoc.c
+Merging fastrpc/for-next (0af2f6be1b42 Linux 6.15-rc1)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/srini/fastrpc.git fastrpc/for-next
+Already up to date.
+Merging fpga/for-next (37e00703228a zynq_fpga: use sgtable-based scatterlist wrappers)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/fpga/linux-fpga.git fpga/for-next
+Already up to date.
+Merging icc/icc-next (ca652cf0c261 Merge branch 'icc-milos' into icc-next)
+$ git merge -m Merge branch 'icc-next' of git://git.kernel.org/pub/scm/linux/kernel/git/djakov/icc.git icc/icc-next
+Already up to date.
+Merging iio/togreg (0a686b9c4f84 iio: adc: ad_sigma_delta: Select IIO_BUFFER_DMAENGINE and SPI_OFFLOAD)
+$ git merge -m Merge branch 'togreg' of git://git.kernel.org/pub/scm/linux/kernel/git/jic23/iio.git iio/togreg
+Already up to date.
+Merging phy-next/next (4a3556b81b99 phy: qcom: phy-qcom-m31: Update IPQ5332 M31 USB phy initialization sequence)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/phy/linux-phy.git phy-next/next
+Already up to date.
+Merging soundwire/next (34b1cb4ec286 soundwire: amd: Add support for acp7.2 platform)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/vkoul/soundwire.git soundwire/next
+Already up to date.
+Merging extcon/extcon-next (5f09caafc652 extcon: fsa9480: Avoid buffer overflow in fsa9480_handle_change())
+$ git merge -m Merge branch 'extcon-next' of git://git.kernel.org/pub/scm/linux/kernel/git/chanwoo/extcon.git extcon/extcon-next
+Merge made by the 'ort' strategy.
+ .../devicetree/bindings/extcon/maxim,max14526.yaml | 80 ++++++
+ drivers/extcon/Kconfig | 13 +
+ drivers/extcon/Makefile | 1 +
+ drivers/extcon/extcon-adc-jack.c | 2 +
+ drivers/extcon/extcon-axp288.c | 2 +-
+ drivers/extcon/extcon-fsa9480.c | 6 +-
+ drivers/extcon/extcon-max14526.c | 302 +++++++++++++++++++++
+ drivers/extcon/extcon-qcom-spmi-misc.c | 2 +-
+ 8 files changed, 404 insertions(+), 4 deletions(-)
+ create mode 100644 Documentation/devicetree/bindings/extcon/maxim,max14526.yaml
+ create mode 100644 drivers/extcon/extcon-max14526.c
+Merging gnss/gnss-next (e326371f3002 dt-bindings: gnss: u-blox: add u-blox,neo-9m compatible)
+$ git merge -m Merge branch 'gnss-next' of git://git.kernel.org/pub/scm/linux/kernel/git/johan/gnss.git gnss/gnss-next
+Already up to date.
+Merging vfio/next (d2272d898186 vfio/type1: correct logic of vfio_find_vpfn())
+$ git merge -m Merge branch 'next' of git://github.com/awilliam/linux-vfio.git vfio/next
+Auto-merging MAINTAINERS
+Auto-merging drivers/vfio/pci/vfio_pci_core.c
+Auto-merging include/linux/mm.h
+Merge made by the 'ort' strategy.
+ MAINTAINERS | 1 -
+ drivers/vfio/device_cdev.c | 38 +++++++-
+ drivers/vfio/group.c | 7 +-
+ drivers/vfio/iommufd.c | 4 +
+ drivers/vfio/pci/hisilicon/hisi_acc_vfio_pci.c | 1 +
+ drivers/vfio/pci/mlx5/cmd.c | 4 +-
+ drivers/vfio/pci/mlx5/main.c | 1 +
+ drivers/vfio/pci/nvgrace-gpu/main.c | 2 +
+ drivers/vfio/pci/pds/vfio_dev.c | 2 +
+ drivers/vfio/pci/qat/main.c | 5 +-
+ drivers/vfio/pci/vfio_pci.c | 1 +
+ drivers/vfio/pci/vfio_pci_core.c | 24 +++--
+ drivers/vfio/pci/virtio/main.c | 3 +
+ drivers/vfio/vfio_iommu_type1.c | 118 ++++++++++++++++++++-----
+ drivers/vfio/vfio_main.c | 3 +-
+ include/linux/mm.h | 23 +++++
+ include/linux/vfio.h | 4 +
+ include/linux/vfio_pci_core.h | 2 +
+ include/uapi/linux/vfio.h | 12 ++-
+ 19 files changed, 212 insertions(+), 43 deletions(-)
+Merging w1/for-next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux-w1.git w1/for-next
+Already up to date.
+Merging spmi/spmi-next (0ff41df1cb26 Linux 6.15)
+$ git merge -m Merge branch 'spmi-next' of git://git.kernel.org/pub/scm/linux/kernel/git/sboyd/spmi.git spmi/spmi-next
+Already up to date.
+Merging staging/staging-next (d632ab86aff2 Merge tag 'for-6.17/dm-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/device-mapper/linux-dm)
+$ git merge -m Merge branch 'staging-next' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/staging.git staging/staging-next
+Already up to date.
+Merging counter-next/counter-next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'counter-next' of git://git.kernel.org/pub/scm/linux/kernel/git/wbg/counter.git counter-next/counter-next
+Already up to date.
+Merging siox/siox/for-next (db418d5f1ca5 siox: bus-gpio: Simplify using devm_siox_* functions)
+$ git merge -m Merge branch 'siox/for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/ukleinek/linux.git siox/siox/for-next
+Already up to date.
+Merging mux/for-next (59b723cd2adb Linux 6.12-rc6)
+$ git merge -m Merge branch 'for-next' of https://gitlab.com/peda-linux/mux.git mux/for-next
+Already up to date.
+Merging dmaengine/next (e3a9ccd21897 dt-bindings: dma: fsl-mxs-dma: allow interrupt-names for fsl,imx23-dma-apbx)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/vkoul/dmaengine.git dmaengine/next
+Already up to date.
+Merging cgroup/for-next (d445d2ab8129 Merge branch 'for-6.17' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/tj/cgroup.git cgroup/for-next
+Merge made by the 'ort' strategy.
+Merging scsi/for-next (b3a40acce7b3 Merge branch 'misc' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/jejb/scsi.git scsi/for-next
+Auto-merging MAINTAINERS
+Auto-merging drivers/scsi/libsas/sas_ata.c
+Auto-merging drivers/scsi/sd.c
+Auto-merging drivers/ufs/host/ufs-qcom.c
+Merge made by the 'ort' strategy.
+ .../devicetree/bindings/ufs/mediatek,ufs.yaml | 46 ++-
+ MAINTAINERS | 2 +-
+ arch/arm64/boot/dts/mediatek/mt8195.dtsi | 25 ++
+ drivers/scsi/aacraid/comminit.c | 3 +-
+ drivers/scsi/libsas/sas_ata.c | 10 +-
+ drivers/scsi/libsas/sas_discover.c | 2 +-
+ drivers/scsi/libsas/sas_internal.h | 78 ++++-
+ drivers/scsi/libsas/sas_phy.c | 6 +-
+ drivers/scsi/libsas/sas_port.c | 13 +-
+ drivers/scsi/mpt3sas/mpt3sas_scsih.c | 3 +-
+ drivers/scsi/scsi_scan.c | 2 +-
+ drivers/scsi/scsi_transport_iscsi.c | 2 +
+ drivers/scsi/scsi_transport_sas.c | 62 +++-
+ drivers/scsi/sd.c | 4 +-
+ drivers/target/target_core_fabric_lib.c | 65 +++-
+ drivers/target/target_core_iblock.c | 33 ++-
+ drivers/target/target_core_iblock.h | 1 +
+ drivers/target/target_core_internal.h | 4 +-
+ drivers/target/target_core_pr.c | 18 +-
+ drivers/ufs/core/ufs-sysfs.c | 3 +-
+ drivers/ufs/core/ufshcd.c | 105 +++----
+ drivers/ufs/host/ufs-mediatek.c | 330 ++++++++++++++++++---
+ drivers/ufs/host/ufs-mediatek.h | 32 ++
+ drivers/ufs/host/ufs-qcom.c | 8 -
+ drivers/ufs/host/ufshcd-pci.c | 33 +--
+ include/scsi/sas_ata.h | 91 +-----
+ 26 files changed, 703 insertions(+), 278 deletions(-)
+Merging scsi-mkp/for-next (383cd6d879a1 scsi: scsi_debug: Make read-only arrays static const)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/mkp/scsi.git scsi-mkp/for-next
+Auto-merging drivers/scsi/scsi_sysfs.c
+Merge made by the 'ort' strategy.
+ drivers/scsi/scsi_debug.c | 91 +++++++++++++++++++++++++++++------------------
+ drivers/scsi/scsi_sysfs.c | 4 +--
+ 2 files changed, 59 insertions(+), 36 deletions(-)
+Merging vhost/linux-next (06a1fa9a0b79 vhost: initialize vq->nheads properly)
+$ git merge -m Merge branch 'linux-next' of git://git.kernel.org/pub/scm/linux/kernel/git/mst/vhost.git vhost/linux-next
+Auto-merging drivers/pci/pci.h
+Auto-merging drivers/vhost/vhost.c
+Auto-merging drivers/virtio/virtio.c
+Auto-merging drivers/virtio/virtio_pci_modern.c
+Auto-merging include/linux/pci.h
+Auto-merging include/linux/virtio.h
+Auto-merging include/linux/virtio_config.h
+Merge made by the 'ort' strategy.
+ drivers/pci/pci.h | 6 +++++
+ drivers/vhost/vhost.c | 1 +
+ drivers/virtio/virtio.c | 18 ++++++++++++++-
+ drivers/virtio/virtio_pci_common.c | 45 ++++++++++++++++++++++++++++++++++++++
+ drivers/virtio/virtio_pci_common.h | 3 +++
+ drivers/virtio/virtio_pci_legacy.c | 2 ++
+ drivers/virtio/virtio_pci_modern.c | 2 ++
+ include/linux/pci.h | 45 ++++++++++++++++++++++++++++++++++++++
+ include/linux/virtio.h | 11 +++++++---
+ include/linux/virtio_config.h | 32 +++++++++++++++++++++++++++
+ 10 files changed, 161 insertions(+), 4 deletions(-)
+Merging rpmsg/for-next (01d7d9241256 Merge branches 'rproc-next' and 'rpmsg-next' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/remoteproc/linux.git rpmsg/for-next
+Merge made by the 'ort' strategy.
+ drivers/rpmsg/qcom_glink_native.c | 2 +-
+ drivers/rpmsg/qcom_smd.c | 2 +-
+ drivers/rpmsg/rpmsg_char.c | 3 ++-
+ 3 files changed, 4 insertions(+), 3 deletions(-)
+Merging gpio-brgl/gpio/for-next (63c7bc53a35e gpio: mlxbf2: use platform_get_irq_optional())
+$ git merge -m Merge branch 'gpio/for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git gpio-brgl/gpio/for-next
+Merge made by the 'ort' strategy.
+ drivers/gpio/gpio-mlxbf2.c | 2 +-
+ drivers/gpio/gpio-pxa.c | 8 +-------
+ 2 files changed, 2 insertions(+), 8 deletions(-)
+Merging gpio-intel/for-next (9ab29ed50555 gpiolib: acpi: Add a quirk for Acer Nitro V15)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/andy/linux-gpio-intel.git gpio-intel/for-next
+Already up to date.
+Merging pinctrl/for-next (a3fe1324c3c5 pinctrl: mediatek: Add pinctrl driver for mt8189)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/linusw/linux-pinctrl.git pinctrl/for-next
+Already up to date.
+Merging pinctrl-intel/for-next (3b4408038da9 pinctrl: intel: fix build warnings about export.h)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/pinctrl/intel.git pinctrl-intel/for-next
+Already up to date.
+Merging pinctrl-renesas/renesas-pinctrl (7000167796a0 pinctrl: renesas: Simplify PINCTRL_RZV2M logic)
+$ git merge -m Merge branch 'renesas-pinctrl' of git://git.kernel.org/pub/scm/linux/kernel/git/geert/renesas-drivers.git pinctrl-renesas/renesas-pinctrl
+Already up to date.
+Merging pinctrl-samsung/for-next (683d532dfc96 pinctrl: samsung: Fix gs101 irq chip)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/pinctrl/samsung.git pinctrl-samsung/for-next
+Already up to date.
+Merging pwm/pwm/for-next (65c6f742ab14 pwm: imx-tpm: Reset counter if CMOD is 0)
+$ git merge -m Merge branch 'pwm/for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/ukleinek/linux.git pwm/pwm/for-next
+Already up to date.
+Merging ktest/for-next (a5e71638ddd7 ktest.pl: Add new PATCHCHECK_SKIP option to skip testing individual commits)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/rostedt/linux-ktest.git ktest/for-next
+Already up to date.
+Merging kselftest/next (30fb5e134f05 selftests/pidfd: Fix duplicate-symbol warnings for SCHED_ CPP symbols)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux-kselftest.git kselftest/next
+Already up to date.
+Merging kunit/test (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'test' of git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux-kselftest.git kunit/test
+Already up to date.
+Merging kunit-next/kunit (34db4fba8191 kunit: fix longest symbol length test)
+$ git merge -m Merge branch 'kunit' of git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux-kselftest.git kunit-next/kunit
+Already up to date.
+Merging livepatching/for-next (a8e905a819fd Merge branch 'for-6.15/ftrace-test' into for-next)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/livepatching/livepatching livepatching/for-next
+Merge made by the 'ort' strategy.
+Merging rtc/rtc-next (bb5b0b4317c9 rtc: ds1685: Update Joshua Kinard's email address.)
+$ git merge -m Merge branch 'rtc-next' of git://git.kernel.org/pub/scm/linux/kernel/git/abelloni/linux.git rtc/rtc-next
+Already up to date.
+Merging nvdimm/libnvdimm-for-next (9f97e61bde6a cxl: Include range.h in cxl.h)
+$ git merge -m Merge branch 'libnvdimm-for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/nvdimm/nvdimm.git nvdimm/libnvdimm-for-next
+Already up to date.
+Merging at24/at24/for-next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'at24/for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git at24/at24/for-next
+Already up to date.
+Merging ntb/ntb-next (0cadf92e93d4 NTB/msi: Remove unused functions)
+$ git merge -m Merge branch 'ntb-next' of https://github.com/jonmason/ntb.git ntb/ntb-next
+Auto-merging drivers/ntb/msi.c
+Merge made by the 'ort' strategy.
+ drivers/ntb/hw/mscc/ntb_hw_switchtec.c | 14 ++++++--
+ drivers/ntb/msi.c | 64 ----------------------------------
+ include/linux/ntb.h | 14 --------
+ 3 files changed, 11 insertions(+), 81 deletions(-)
+Merging seccomp/for-next/seccomp (b0c9bfbab925 selftests/seccomp: Add a test for the WAIT_KILLABLE_RECV fast reply race)
+$ git merge -m Merge branch 'for-next/seccomp' of git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux.git seccomp/for-next/seccomp
+Merge made by the 'ort' strategy.
+ kernel/seccomp.c | 12 +--
+ tools/testing/selftests/seccomp/seccomp_bpf.c | 131 ++++++++++++++++++++++++++
+ 2 files changed, 136 insertions(+), 7 deletions(-)
+Merging slimbus/for-next (0af2f6be1b42 Linux 6.15-rc1)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/srini/slimbus.git slimbus/for-next
+Already up to date.
+Merging nvmem/for-next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/srini/nvmem.git nvmem/for-next
+Already up to date.
+Merging xarray/main (6684aba0780d XArray: Add extra debugging check to xas_lock and friends)
+$ git merge -m Merge branch 'main' of git://git.infradead.org/users/willy/xarray.git xarray/main
+Auto-merging include/linux/xarray.h
+Auto-merging lib/xarray.c
+Merge made by the 'ort' strategy.
+ include/linux/xarray.h | 60 +++++++++++++++++++++++++++-----------------------
+ lib/xarray.c | 3 +--
+ 2 files changed, 34 insertions(+), 29 deletions(-)
+Merging hyperv/hyperv-next (d9016a249be5 hv/hv_kvp_daemon: Prevent similar logs in kvp_key_add_or_modify())
+$ git merge -m Merge branch 'hyperv-next' of git://git.kernel.org/pub/scm/linux/kernel/git/hyperv/linux.git hyperv/hyperv-next
+Merge made by the 'ort' strategy.
+ tools/hv/hv_get_dhcp_info.sh | 87 ++++++++++++++++++++++++++++++++++++++------
+ tools/hv/hv_kvp_daemon.c | 18 ++++-----
+ 2 files changed, 82 insertions(+), 23 deletions(-)
+Merging auxdisplay/for-next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/andy/linux-auxdisplay.git auxdisplay/for-next
+Already up to date.
+Merging kgdb/kgdb/for-next (afdbe49276ac kdb: Remove optional size arguments from strscpy() calls)
+$ git merge -m Merge branch 'kgdb/for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/danielt/linux.git kgdb/kgdb/for-next
+Already up to date.
+Merging hmm/hmm (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'hmm' of git://git.kernel.org/pub/scm/linux/kernel/git/rdma/rdma.git hmm/hmm
+Already up to date.
+Merging cfi/cfi/next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'cfi/next' of git://git.kernel.org/pub/scm/linux/kernel/git/mtd/linux.git cfi/cfi/next
+Already up to date.
+Merging mhi/mhi-next (00559ba3ae74 bus: mhi: host: pci_generic: Add Telit FN990B40 modem support)
+$ git merge -m Merge branch 'mhi-next' of git://git.kernel.org/pub/scm/linux/kernel/git/mani/mhi.git mhi/mhi-next
+Already up to date.
+Merging memblock/for-next (3b394dff15e1 memblock tests: add test for memblock_set_node)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/rppt/memblock.git memblock/for-next
+Already up to date.
+Merging cxl/next (f11a5f89910a Documentation/ABI/testing/debugfs-cxl: Add 'cxl' to clear_poison path)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/cxl/cxl.git cxl/next
+Already up to date.
+Merging zstd/zstd-next (65d1f5507ed2 zstd: Import upstream v1.5.7)
+$ git merge -m Merge branch 'zstd-next' of https://github.com/terrelln/linux.git zstd/zstd-next
+Already up to date.
+Merging efi/next (02eb7a8eee20 efi: add API doc entry for ovmf_debug_log)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/efi/efi.git efi/next
+Auto-merging drivers/firmware/efi/Kconfig
+Auto-merging include/linux/efi.h
+Merge made by the 'ort' strategy.
+ Documentation/ABI/testing/sysfs-firmware-efi | 7 ++
+ drivers/firmware/efi/Kconfig | 8 ++
+ drivers/firmware/efi/Makefile | 1 +
+ drivers/firmware/efi/efi.c | 8 ++
+ drivers/firmware/efi/libstub/printk.c | 4 +-
+ drivers/firmware/efi/ovmf-debug-log.c | 111 +++++++++++++++++++++++++++
+ include/linux/efi.h | 4 +
+ 7 files changed, 141 insertions(+), 2 deletions(-)
+ create mode 100644 drivers/firmware/efi/ovmf-debug-log.c
+Merging unicode/for-next (6b56a63d286f MAINTAINERS: Add Unicode tree)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/krisman/unicode.git unicode/for-next
+Already up to date.
+Merging slab/slab/for-next (8185696483dc MAINTAINERS: add missing files to slab section)
+$ git merge -m Merge branch 'slab/for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/vbabka/slab.git slab/slab/for-next
+Already up to date.
+Merging random/master (3778dcb2dcc1 random: use offstack cpumask when necessary)
+$ git merge -m Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/crng/random.git random/master
+Auto-merging drivers/media/test-drivers/vivid/vivid-vid-cap.c
+Merge made by the 'ort' strategy.
+ drivers/char/random.c | 23 ++++++++++++++---------
+ drivers/media/test-drivers/vivid/vivid-vid-cap.c | 4 +++-
+ include/linux/prandom.h | 6 ------
+ 3 files changed, 17 insertions(+), 16 deletions(-)
+Merging landlock/next (6dde339a3df8 landlock: Minor comments improvements)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/mic/linux.git landlock/next
+Auto-merging fs/namei.c
+Auto-merging include/linux/fs.h
+Merge made by the 'ort' strategy.
+ fs/namei.c | 2 +-
+ include/linux/fs.h | 1 +
+ security/landlock/errata/abi-1.h | 16 +
+ security/landlock/fs.c | 194 +++-
+ security/landlock/ruleset.c | 12 +-
+ security/landlock/ruleset.h | 2 +-
+ tools/testing/selftests/landlock/fs_test.c | 1317 +++++++++++++++++++++++++++-
+ 7 files changed, 1503 insertions(+), 41 deletions(-)
+ create mode 100644 security/landlock/errata/abi-1.h
+Merging rust/rust-next (d2eedaa3909b Merge tag 'rtc-6.17' of git://git.kernel.org/pub/scm/linux/kernel/git/abelloni/linux)
+$ git merge -m Merge branch 'rust-next' of https://github.com/Rust-for-Linux/linux.git rust/rust-next
+Already up to date.
+Merging rust-alloc/alloc-next (d49ac7744f57 MAINTAINERS: add mm folks as reviewers to rust alloc)
+$ git merge -m Merge branch 'alloc-next' of https://github.com/Rust-for-Linux/linux.git rust-alloc/alloc-next
+Already up to date.
+Merging rust-io/io-next (86731a2a651e Linux 6.16-rc3)
+$ git merge -m Merge branch 'io-next' of https://github.com/Rust-for-Linux/linux.git rust-io/io-next
+Already up to date.
+Merging rust-pin-init/pin-init-next (fc3870dc5cad rust: pin-init: examples, tests: use `ignore` instead of conditionally compiling tests)
+$ git merge -m Merge branch 'pin-init-next' of https://github.com/Rust-for-Linux/linux.git rust-pin-init/pin-init-next
+Already up to date.
+Merging rust-timekeeping/timekeeping-next (d4b29ddf82a4 rust: time: Add wrapper for fsleep() function)
+$ git merge -m Merge branch 'timekeeping-next' of https://github.com/Rust-for-Linux/linux.git rust-timekeeping/timekeeping-next
+Already up to date.
+Merging rust-xarray/xarray-next (fa616196fbea MAINTAINERS: add entry for Rust XArray API)
+$ git merge -m Merge branch 'xarray-next' of https://github.com/Rust-for-Linux/linux.git rust-xarray/xarray-next
+Already up to date.
+Merging sysctl/sysctl-next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'sysctl-next' of git://git.kernel.org/pub/scm/linux/kernel/git/sysctl/sysctl.git sysctl/sysctl-next
+Already up to date.
+Merging execve/for-next/execve (7f71195c15dc fork: reorder function qualifiers for copy_clone_args_from_user)
+$ git merge -m Merge branch 'for-next/execve' of git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux.git execve/for-next/execve
+Already up to date.
+Merging bitmap/bitmap-for-next (89748acdf226 Merge tag 'drm-next-2025-08-01' of https://gitlab.freedesktop.org/drm/kernel)
+$ git merge -m Merge branch 'bitmap-for-next' of https://github.com/norov/linux.git bitmap/bitmap-for-next
+Already up to date.
+Merging hte/for-next (9e4259716f60 hte: tegra-194: add missing MODULE_DESCRIPTION() macro)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/pateldipen1984/linux.git hte/for-next
+Already up to date.
+Merging kspp/for-next/kspp (f627b51aaa04 compiler_types: Provide __no_kstack_erase to disable coverage only on Clang)
+$ git merge -m Merge branch 'for-next/kspp' of git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux.git kspp/for-next/kspp
+Already up to date.
+Merging nolibc/for-next (b9e50363178a selftests/nolibc: add x32 test configuration)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/nolibc/linux-nolibc.git nolibc/for-next
+Already up to date.
+Merging iommufd/for-next (2c78e74493d3 iommu/arm-smmu-v3: Replace vsmmu_size/type with get_viommu_size)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/jgg/iommufd.git iommufd/for-next
+Already up to date.
+Merging turbostat/next (447c98c1ca4a tools/power turbostat: Add idle governor statistics reporting)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/lenb/linux.git turbostat/next
+Auto-merging tools/power/x86/turbostat/turbostat.8
+CONFLICT (content): Merge conflict in tools/power/x86/turbostat/turbostat.8
+Auto-merging tools/power/x86/turbostat/turbostat.c
+CONFLICT (content): Merge conflict in tools/power/x86/turbostat/turbostat.c
+Resolved 'tools/power/x86/turbostat/turbostat.8' using previous resolution.
+Resolved 'tools/power/x86/turbostat/turbostat.c' using previous resolution.
+Automatic merge failed; fix conflicts and then commit the result.
+$ git commit --no-edit -v -a
+[master 8c553edd403c] Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/lenb/linux.git
+$ git diff -M --stat --summary HEAD^..
+ tools/power/x86/turbostat/turbostat.8 | 17 +-
+ tools/power/x86/turbostat/turbostat.c | 534 ++++++++--------------------------
+ 2 files changed, 131 insertions(+), 420 deletions(-)
+Merging pwrseq/pwrseq/for-next (07d59dec6795 power: sequencing: qcom-wcn: fix bluetooth-wifi copypasta for WCN6855)
+$ git merge -m Merge branch 'pwrseq/for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git pwrseq/pwrseq/for-next
+Already up to date.
+Merging capabilities-next/caps-next (cdd73b166607 uapi: fix broken link in linux/capability.h)
+$ git merge -m Merge branch 'caps-next' of git://git.kernel.org/pub/scm/linux/kernel/git/sergeh/linux.git capabilities-next/caps-next
+Already up to date.
+Merging ipe/next (038d61fd6422 Linux 6.16)
+$ git merge -m Merge branch 'next' of https://git.kernel.org/pub/scm/linux/kernel/git/wufan/ipe.git ipe/next
+Already up to date.
+Merging kcsan/next (9872916ad1a1 kcsan: test: Initialize dummy variable)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/melver/linux.git kcsan/next
+Already up to date.
+Merging crc/crc-next (118da22eb6fb lib/crc: x86/crc32c: Enable VPCLMULQDQ optimization where beneficial)
+$ git merge -m Merge branch 'crc-next' of git://git.kernel.org/pub/scm/linux/kernel/git/ebiggers/linux.git crc/crc-next
+Already up to date.
+Merging fwctl/for-next (19272b37aa4f Linux 6.16-rc1)
+$ git merge -m Merge branch 'for-next' of git//git.kernel.org/pub/scm/linux/kernel/git/fwctl/fwctl.git fwctl/for-next
+Already up to date.
+Merging devsec-tsm/next (9d948b880409 Merge branch 'for-6.16/tsm-mr' into tsm-next)
+$ git merge -m Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/devsec/tsm.git devsec-tsm/next
+Already up to date.
+Merging hisilicon/for-next (b1136432c972 soc: hisilicon: kunpeng_hccs: Fix incorrect log information)
+$ git merge -m Merge branch 'for-next' of https://github.com/hisilicon/linux-hisi.git hisilicon/for-next
+Already up to date.
+Merging kthread/for-next (d8b4bf4ea04d kthread: modify kernel-doc function name to match code)
+$ git merge -m Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/frederic/linux-dynticks.git kthread/for-next
+Already up to date.
diff --git a/arch/arm/boot/dts/aspeed/aspeed-bmc-ibm-everest.dts b/arch/arm/boot/dts/aspeed/aspeed-bmc-ibm-everest.dts
index 4d9e2cd11f44..9f144f527f03 100644
--- a/arch/arm/boot/dts/aspeed/aspeed-bmc-ibm-everest.dts
+++ b/arch/arm/boot/dts/aspeed/aspeed-bmc-ibm-everest.dts
@@ -2808,6 +2808,7 @@
#size-cells = <0>;
cfam4_spi0: spi@0 {
+ compatible = "ibm,spi-fsi";
reg = <0x0>;
#address-cells = <1>;
#size-cells = <0>;
@@ -2824,6 +2825,7 @@
};
cfam4_spi1: spi@20 {
+ compatible = "ibm,spi-fsi";
reg = <0x20>;
#address-cells = <1>;
#size-cells = <0>;
@@ -2840,8 +2842,8 @@
};
cfam4_spi2: spi@40 {
+ compatible = "ibm,spi-fsi";
reg = <0x40>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
@@ -2857,8 +2859,8 @@
};
cfam4_spi3: spi@60 {
+ compatible = "ibm,spi-fsi";
reg = <0x60>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
@@ -3181,6 +3183,7 @@
#size-cells = <0>;
cfam5_spi0: spi@0 {
+ compatible = "ibm,spi-fsi";
reg = <0x0>;
#address-cells = <1>;
#size-cells = <0>;
@@ -3197,6 +3200,7 @@
};
cfam5_spi1: spi@20 {
+ compatible = "ibm,spi-fsi";
reg = <0x20>;
#address-cells = <1>;
#size-cells = <0>;
@@ -3213,8 +3217,8 @@
};
cfam5_spi2: spi@40 {
+ compatible = "ibm,spi-fsi";
reg = <0x40>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
@@ -3230,8 +3234,8 @@
};
cfam5_spi3: spi@60 {
+ compatible = "ibm,spi-fsi";
reg = <0x60>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
@@ -3554,6 +3558,7 @@
#size-cells = <0>;
cfam6_spi0: spi@0 {
+ compatible = "ibm,spi-fsi";
reg = <0x0>;
#address-cells = <1>;
#size-cells = <0>;
@@ -3570,6 +3575,7 @@
};
cfam6_spi1: spi@20 {
+ compatible = "ibm,spi-fsi";
reg = <0x20>;
#address-cells = <1>;
#size-cells = <0>;
@@ -3586,8 +3592,8 @@
};
cfam6_spi2: spi@40 {
+ compatible = "ibm,spi-fsi";
reg = <0x40>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
@@ -3603,8 +3609,8 @@
};
cfam6_spi3: spi@60 {
+ compatible = "ibm,spi-fsi";
reg = <0x60>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
@@ -3927,6 +3933,7 @@
#size-cells = <0>;
cfam7_spi0: spi@0 {
+ compatible = "ibm,spi-fsi";
reg = <0x0>;
#address-cells = <1>;
#size-cells = <0>;
@@ -3943,6 +3950,7 @@
};
cfam7_spi1: spi@20 {
+ compatible = "ibm,spi-fsi";
reg = <0x20>;
#address-cells = <1>;
#size-cells = <0>;
@@ -3959,8 +3967,8 @@
};
cfam7_spi2: spi@40 {
+ compatible = "ibm,spi-fsi";
reg = <0x40>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
@@ -3976,8 +3984,8 @@
};
cfam7_spi3: spi@60 {
+ compatible = "ibm,spi-fsi";
reg = <0x60>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
diff --git a/arch/arm/boot/dts/aspeed/aspeed-bmc-inspur-fp5280g2.dts b/arch/arm/boot/dts/aspeed/aspeed-bmc-inspur-fp5280g2.dts
index 78a5656ef75d..79c6919b3570 100644
--- a/arch/arm/boot/dts/aspeed/aspeed-bmc-inspur-fp5280g2.dts
+++ b/arch/arm/boot/dts/aspeed/aspeed-bmc-inspur-fp5280g2.dts
@@ -54,10 +54,9 @@
};
fsi: gpio-fsi {
- compatible = "aspeed,ast2500-cf-fsi-master", "fsi-master";
+ compatible = "aspeed,ast2500-cf-fsi-master";
#address-cells = <2>;
#size-cells = <0>;
- no-gpio-delays;
memory-region = <&coldfire_memory>;
aspeed,sram = <&sram>;
diff --git a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-lanyang.dts b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-lanyang.dts
index 65b2208f5a90..9f2ad551255d 100644
--- a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-lanyang.dts
+++ b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-lanyang.dts
@@ -63,7 +63,7 @@
};
fsi: gpio-fsi {
- compatible = "fsi-master-gpio", "fsi-master";
+ compatible = "fsi-master-gpio";
#address-cells = <2>;
#size-cells = <0>;
diff --git a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-mowgli.dts b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-mowgli.dts
index 31ff19ef87a0..6c8b966ffccc 100644
--- a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-mowgli.dts
+++ b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-mowgli.dts
@@ -165,7 +165,7 @@
};
fsi: gpio-fsi {
- compatible = "fsi-master-gpio", "fsi-master";
+ compatible = "fsi-master-gpio";
#address-cells = <2>;
#size-cells = <0>;
no-gpio-delays;
diff --git a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-nicole.dts b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-nicole.dts
index 1a7c61750d0d..ce6d30ddf07c 100644
--- a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-nicole.dts
+++ b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-nicole.dts
@@ -77,10 +77,9 @@
};
fsi: gpio-fsi {
- compatible = "aspeed,ast2500-cf-fsi-master", "fsi-master";
+ compatible = "aspeed,ast2500-cf-fsi-master";
#address-cells = <2>;
#size-cells = <0>;
- no-gpio-delays;
memory-region = <&coldfire_memory>;
aspeed,sram = <&sram>;
diff --git a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-palmetto.dts b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-palmetto.dts
index 123da82c04d5..a1d3e046d4a2 100644
--- a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-palmetto.dts
+++ b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-palmetto.dts
@@ -55,7 +55,7 @@
};
fsi: gpio-fsi {
- compatible = "aspeed,ast2400-cf-fsi-master", "fsi-master";
+ compatible = "aspeed,ast2400-cf-fsi-master";
#address-cells = <2>;
#size-cells = <0>;
diff --git a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-romulus.dts b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-romulus.dts
index e6b383f6e977..a0263d969e51 100644
--- a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-romulus.dts
+++ b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-romulus.dts
@@ -68,10 +68,9 @@
};
fsi: gpio-fsi {
- compatible = "aspeed,ast2500-cf-fsi-master", "fsi-master";
+ compatible = "aspeed,ast2500-cf-fsi-master";
#address-cells = <2>;
#size-cells = <0>;
- no-gpio-delays;
memory-region = <&coldfire_memory>;
aspeed,sram = <&sram>;
diff --git a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-witherspoon.dts b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-witherspoon.dts
index 8b1e82c8cdfe..89907b628b65 100644
--- a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-witherspoon.dts
+++ b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-witherspoon.dts
@@ -173,7 +173,7 @@
};
fsi: gpio-fsi {
- compatible = "fsi-master-gpio", "fsi-master";
+ compatible = "fsi-master-gpio";
#address-cells = <2>;
#size-cells = <0>;
no-gpio-delays;
diff --git a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-zaius.dts b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-zaius.dts
index 6ac7b0aa6e54..627c91f178e6 100644
--- a/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-zaius.dts
+++ b/arch/arm/boot/dts/aspeed/aspeed-bmc-opp-zaius.dts
@@ -96,7 +96,7 @@
};
fsi: gpio-fsi {
- compatible = "fsi-master-gpio", "fsi-master";
+ compatible = "fsi-master-gpio";
#address-cells = <2>;
#size-cells = <0>;
no-gpio-delays;
diff --git a/arch/arm/boot/dts/aspeed/aspeed-g6.dtsi b/arch/arm/boot/dts/aspeed/aspeed-g6.dtsi
index 8ed715bd53aa..acdb6ae74b27 100644
--- a/arch/arm/boot/dts/aspeed/aspeed-g6.dtsi
+++ b/arch/arm/boot/dts/aspeed/aspeed-g6.dtsi
@@ -847,7 +847,7 @@
fsim0: fsi@1e79b000 {
#interrupt-cells = <1>;
- compatible = "aspeed,ast2600-fsi-master", "fsi-master";
+ compatible = "aspeed,ast2600-fsi-master";
reg = <0x1e79b000 0x94>;
interrupts = <GIC_SPI 100 IRQ_TYPE_LEVEL_HIGH>;
pinctrl-names = "default";
@@ -859,7 +859,7 @@
fsim1: fsi@1e79b100 {
#interrupt-cells = <1>;
- compatible = "aspeed,ast2600-fsi-master", "fsi-master";
+ compatible = "aspeed,ast2600-fsi-master";
reg = <0x1e79b100 0x94>;
interrupts = <GIC_SPI 101 IRQ_TYPE_LEVEL_HIGH>;
pinctrl-names = "default";
diff --git a/arch/arm/boot/dts/aspeed/ibm-power10-dual.dtsi b/arch/arm/boot/dts/aspeed/ibm-power10-dual.dtsi
index 07ce3b2bc62a..06fac236773f 100644
--- a/arch/arm/boot/dts/aspeed/ibm-power10-dual.dtsi
+++ b/arch/arm/boot/dts/aspeed/ibm-power10-dual.dtsi
@@ -82,6 +82,7 @@
#size-cells = <0>;
cfam0_spi0: spi@0 {
+ compatible = "ibm,spi-fsi";
reg = <0x0>;
#address-cells = <1>;
#size-cells = <0>;
@@ -98,6 +99,7 @@
};
cfam0_spi1: spi@20 {
+ compatible = "ibm,spi-fsi";
reg = <0x20>;
#address-cells = <1>;
#size-cells = <0>;
@@ -114,8 +116,8 @@
};
cfam0_spi2: spi@40 {
+ compatible = "ibm,spi-fsi";
reg = <0x40>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
@@ -131,8 +133,8 @@
};
cfam0_spi3: spi@60 {
+ compatible = "ibm,spi-fsi";
reg = <0x60>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
@@ -249,6 +251,7 @@
#size-cells = <0>;
cfam1_spi0: spi@0 {
+ compatible = "ibm,spi-fsi";
reg = <0x0>;
#address-cells = <1>;
#size-cells = <0>;
@@ -265,6 +268,7 @@
};
cfam1_spi1: spi@20 {
+ compatible = "ibm,spi-fsi";
reg = <0x20>;
#address-cells = <1>;
#size-cells = <0>;
@@ -281,8 +285,8 @@
};
cfam1_spi2: spi@40 {
+ compatible = "ibm,spi-fsi";
reg = <0x40>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
@@ -298,8 +302,8 @@
};
cfam1_spi3: spi@60 {
+ compatible = "ibm,spi-fsi";
reg = <0x60>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
diff --git a/arch/arm/boot/dts/aspeed/ibm-power10-quad.dtsi b/arch/arm/boot/dts/aspeed/ibm-power10-quad.dtsi
index 57494c744b5d..9501f66d0030 100644
--- a/arch/arm/boot/dts/aspeed/ibm-power10-quad.dtsi
+++ b/arch/arm/boot/dts/aspeed/ibm-power10-quad.dtsi
@@ -733,6 +733,7 @@
#size-cells = <0>;
cfam2_spi0: spi@0 {
+ compatible = "ibm,spi-fsi";
reg = <0x0>;
#address-cells = <1>;
#size-cells = <0>;
@@ -749,6 +750,7 @@
};
cfam2_spi1: spi@20 {
+ compatible = "ibm,spi-fsi";
reg = <0x20>;
#address-cells = <1>;
#size-cells = <0>;
@@ -765,8 +767,8 @@
};
cfam2_spi2: spi@40 {
+ compatible = "ibm,spi-fsi";
reg = <0x40>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
@@ -782,8 +784,8 @@
};
cfam2_spi3: spi@60 {
+ compatible = "ibm,spi-fsi";
reg = <0x60>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
@@ -1106,6 +1108,7 @@
#size-cells = <0>;
cfam3_spi0: spi@0 {
+ compatible = "ibm,spi-fsi";
reg = <0x0>;
#address-cells = <1>;
#size-cells = <0>;
@@ -1122,6 +1125,7 @@
};
cfam3_spi1: spi@20 {
+ compatible = "ibm,spi-fsi";
reg = <0x20>;
#address-cells = <1>;
#size-cells = <0>;
@@ -1138,8 +1142,8 @@
};
cfam3_spi2: spi@40 {
+ compatible = "ibm,spi-fsi";
reg = <0x40>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
@@ -1155,8 +1159,8 @@
};
cfam3_spi3: spi@60 {
+ compatible = "ibm,spi-fsi";
reg = <0x60>;
- compatible = "ibm,fsi2spi";
#address-cells = <1>;
#size-cells = <0>;
diff --git a/arch/arm64/boot/dts/xilinx/Makefile b/arch/arm64/boot/dts/xilinx/Makefile
index 7f5a8801cad1..70fac0b276df 100644
--- a/arch/arm64/boot/dts/xilinx/Makefile
+++ b/arch/arm64/boot/dts/xilinx/Makefile
@@ -30,4 +30,28 @@ dtb-$(CONFIG_ARCH_ZYNQMP) += zynqmp-smk-k26-revA-sck-kv-g-revA.dtb
zynqmp-smk-k26-revA-sck-kv-g-revB-dtbs := zynqmp-smk-k26-revA.dtb zynqmp-sck-kv-g-revB.dtbo
dtb-$(CONFIG_ARCH_ZYNQMP) += zynqmp-smk-k26-revA-sck-kv-g-revB.dtb
+zynqmp-sm-k26-revA-sck-kr-g-revA-dtbs := zynqmp-sm-k26-revA.dtb zynqmp-sck-kr-g-revA.dtbo
+dtb-$(CONFIG_ARCH_ZYNQMP) += zynqmp-sm-k26-revA-sck-kr-g-revA.dtb
+zynqmp-sm-k26-revA-sck-kr-g-revB-dtbs := zynqmp-sm-k26-revA.dtb zynqmp-sck-kr-g-revB.dtbo
+dtb-$(CONFIG_ARCH_ZYNQMP) += zynqmp-sm-k26-revA-sck-kr-g-revB.dtb
+zynqmp-smk-k26-revA-sck-kr-g-revA-dtbs := zynqmp-smk-k26-revA.dtb zynqmp-sck-kr-g-revA.dtbo
+dtb-$(CONFIG_ARCH_ZYNQMP) += zynqmp-smk-k26-revA-sck-kr-g-revA.dtb
+zynqmp-smk-k26-revA-sck-kr-g-revB-dtbs := zynqmp-smk-k26-revA.dtb zynqmp-sck-kr-g-revB.dtbo
+dtb-$(CONFIG_ARCH_ZYNQMP) += zynqmp-smk-k26-revA-sck-kr-g-revB.dtb
+
+zynqmp-sm-k24-revA-sck-kd-g-revA-dtbs := zynqmp-sm-k24-revA.dtb zynqmp-sck-kd-g-revA.dtbo
+dtb-$(CONFIG_ARCH_ZYNQMP) += zynqmp-sm-k24-revA-sck-kd-g-revA.dtb
+zynqmp-smk-k24-revA-sck-kd-g-revA-dtbs := zynqmp-smk-k24-revA.dtb zynqmp-sck-kd-g-revA.dtbo
+dtb-$(CONFIG_ARCH_ZYNQMP) += zynqmp-smk-k24-revA-sck-kd-g-revA.dtb
+
+zynqmp-sm-k24-revA-sck-kv-g-revB-dtbs := zynqmp-sm-k24-revA.dtb zynqmp-sck-kv-g-revB.dtbo
+dtb-$(CONFIG_ARCH_ZYNQMP) += zynqmp-sm-k24-revA-sck-kv-g-revB.dtb
+zynqmp-smk-k24-revA-sck-kv-g-revB-dtbs := zynqmp-smk-k24-revA.dtb zynqmp-sck-kv-g-revB.dtbo
+dtb-$(CONFIG_ARCH_ZYNQMP) += zynqmp-smk-k24-revA-sck-kv-g-revB.dtb
+
+zynqmp-sm-k24-revA-sck-kr-g-revB-dtbs := zynqmp-sm-k24-revA.dtb zynqmp-sck-kr-g-revB.dtbo
+dtb-$(CONFIG_ARCH_ZYNQMP) += zynqmp-sm-k24-revA-sck-kr-g-revB.dtb
+zynqmp-smk-k24-revA-sck-kr-g-revB-dtbs := zynqmp-smk-k24-revA.dtb zynqmp-sck-kr-g-revB.dtbo
+dtb-$(CONFIG_ARCH_ZYNQMP) += zynqmp-smk-k24-revA-sck-kr-g-revB.dtb
+
dtb-$(CONFIG_ARCH_ZYNQMP) += versal-net-vn-x-b2197-01-revA.dtb
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-sck-kd-g-revA.dtso b/arch/arm64/boot/dts/xilinx/zynqmp-sck-kd-g-revA.dtso
new file mode 100644
index 000000000000..02be5e1e8686
--- /dev/null
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-sck-kd-g-revA.dtso
@@ -0,0 +1,390 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * dts file for KD240 revA Carrier Card
+ *
+ * Copyright (C) 2021 - 2022, Xilinx, Inc.
+ * Copyright (C) 2022 - 2023, Advanced Micro Devices, Inc.
+ *
+ * Michal Simek <michal.simek@amd.com>
+ */
+
+#include <dt-bindings/gpio/gpio.h>
+#include <dt-bindings/phy/phy.h>
+#include <dt-bindings/pinctrl/pinctrl-zynqmp.h>
+
+/dts-v1/;
+/plugin/;
+
+&{/} {
+ compatible = "xlnx,zynqmp-sk-kd240-rev1",
+ "xlnx,zynqmp-sk-kd240-revB",
+ "xlnx,zynqmp-sk-kd240-revA",
+ "xlnx,zynqmp-sk-kd240", "xlnx,zynqmp";
+ model = "ZynqMP KD240 revA/B/1";
+
+ aliases {
+ ethernet0 = "/axi/ethernet@ff0c0000"; /* &gem1 */
+ };
+
+ ina260-u3 {
+ compatible = "iio-hwmon";
+ io-channels = <&u3 0>, <&u3 1>, <&u3 2>;
+ };
+
+ clk_26: clock2 { /* u17 - USB */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <26000000>;
+ };
+
+ clk_25_0: clock4 { /* u92/u91 - GEM2 */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <25000000>;
+ };
+
+ clk_25_1: clock5 { /* u92/u91 - GEM3 */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <25000000>;
+ };
+};
+
+&can0 {
+ status = "okay";
+ pinctrl-names = "default";
+ pinctrl-0 = <&pinctrl_can0_default>;
+};
+
+&i2c1 { /* I2C_SCK C26/C27 - MIO from SOM */
+ #address-cells = <1>;
+ #size-cells = <0>;
+ pinctrl-names = "default", "gpio";
+ pinctrl-0 = <&pinctrl_i2c1_default>;
+ pinctrl-1 = <&pinctrl_i2c1_gpio>;
+ scl-gpios = <&gpio 24 (GPIO_ACTIVE_HIGH | GPIO_OPEN_DRAIN)>;
+ sda-gpios = <&gpio 25 (GPIO_ACTIVE_HIGH | GPIO_OPEN_DRAIN)>;
+
+ u3: ina260@40 { /* u3 */
+ compatible = "ti,ina260";
+ #io-channel-cells = <1>;
+ label = "ina260-u14";
+ reg = <0x40>;
+ };
+
+ slg7xl45106: gpio@11 { /* u13 - reset logic */
+ compatible = "dlg,slg7xl45106";
+ reg = <0x11>;
+ label = "resetchip";
+ gpio-controller;
+ #gpio-cells = <2>;
+ gpio-line-names = "USB0_PHY_RESET_B", "",
+ "SD_RESET_B", "USB0_HUB_RESET_B",
+ "", "PS_GEM0_RESET_B",
+ "", "";
+ };
+
+ hub: usb-hub@2d { /* u36 */
+ compatible = "microchip,usb5744";
+ reg = <0x2d>;
+ };
+};
+
+/* USB 3.0 */
+&psgtr {
+ status = "okay";
+ /* usb */
+ clocks = <&clk_26>;
+ clock-names = "ref2";
+};
+
+&usb0 { /* mio52 - mio63 */
+ status = "okay";
+ pinctrl-names = "default";
+ pinctrl-0 = <&pinctrl_usb0_default>;
+ phy-names = "usb3-phy";
+ phys = <&psgtr 2 PHY_TYPE_USB3 0 2>;
+ reset-gpios = <&slg7xl45106 0 GPIO_ACTIVE_LOW>;
+ assigned-clock-rates = <250000000>, <20000000>;
+};
+
+&dwc3_0 {
+ status = "okay";
+ dr_mode = "host";
+ snps,usb3_lpm_capable;
+ maximum-speed = "super-speed";
+ #address-cells = <1>;
+ #size-cells = <0>;
+
+ /* 2.0 hub on port 1 */
+ hub_2_0: hub@1 {
+ compatible = "usb424,2744";
+ reg = <1>;
+ peer-hub = <&hub_3_0>;
+ i2c-bus = <&hub>;
+ reset-gpios = <&slg7xl45106 3 GPIO_ACTIVE_LOW>;
+ };
+
+ /* 3.0 hub on port 2 */
+ hub_3_0: hub@2 {
+ compatible = "usb424,5744";
+ reg = <2>;
+ peer-hub = <&hub_2_0>;
+ i2c-bus = <&hub>;
+ reset-gpios = <&slg7xl45106 3 GPIO_ACTIVE_LOW>;
+ };
+};
+
+&gem1 { /* mdio mio50/51 */
+ status = "okay";
+ pinctrl-names = "default";
+ pinctrl-0 = <&pinctrl_gem1_default>;
+ assigned-clock-rates = <250000000>;
+
+ phy-handle = <&phy0>;
+ phy-mode = "rgmii-id";
+ mdio: mdio {
+ #address-cells = <1>;
+ #size-cells = <0>;
+ phy0: ethernet-phy@8 { /* Adin u31 */
+ #phy-cells = <1>;
+ compatible = "ethernet-phy-id0283.bc30";
+ reg = <8>;
+ adi,rx-internal-delay-ps = <2000>;
+ adi,tx-internal-delay-ps = <2000>;
+ adi,fifo-depth-bits = <8>;
+ reset-assert-us = <10>;
+ reset-deassert-us = <5000>;
+ reset-gpios = <&gpio 77 GPIO_ACTIVE_LOW>;
+ };
+ };
+};
+
+/* 2 more ethernet phys u32@2 and u34@3 */
+
+&pinctrl0 { /* required by spec */
+ status = "okay";
+
+ pinctrl_can0_default: can0-default {
+ mux {
+ function = "can0";
+ groups = "can0_16_grp";
+ };
+
+ conf {
+ groups = "can0_16_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ conf-rx {
+ pins = "MIO66";
+ bias-pull-up;
+ };
+
+ conf-tx {
+ pins = "MIO67";
+ bias-pull-up;
+ drive-strength = <4>;
+ };
+ };
+
+ pinctrl_uart0_default: uart0-default {
+ conf {
+ groups = "uart0_17_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ drive-strength = <12>;
+ };
+
+ conf-rx {
+ pins = "MIO70";
+ bias-high-impedance;
+ };
+
+ conf-tx {
+ pins = "MIO71";
+ bias-disable;
+ };
+
+ mux {
+ groups = "uart0_17_grp";
+ function = "uart0";
+ };
+ };
+
+ pinctrl_uart1_default: uart1-default {
+ conf {
+ groups = "uart1_9_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ drive-strength = <12>;
+ };
+
+ conf-rx {
+ pins = "MIO37";
+ bias-high-impedance;
+ };
+
+ conf-tx {
+ pins = "MIO36";
+ bias-disable;
+ output-enable;
+ };
+
+ mux {
+ groups = "uart1_9_grp";
+ function = "uart1";
+ };
+ };
+
+ pinctrl_i2c1_default: i2c1-default {
+ conf {
+ groups = "i2c1_6_grp";
+ bias-pull-up;
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ mux {
+ groups = "i2c1_6_grp";
+ function = "i2c1";
+ };
+ };
+
+ pinctrl_i2c1_gpio: i2c1-gpio-grp {
+ conf {
+ groups = "gpio0_24_grp", "gpio0_25_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ mux {
+ groups = "gpio0_24_grp", "gpio0_25_grp";
+ function = "gpio0";
+ };
+ };
+
+ pinctrl_gem1_default: gem1-default {
+ conf {
+ groups = "ethernet1_0_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ conf-rx {
+ pins = "MIO45", "MIO46", "MIO47", "MIO48";
+ bias-disable;
+ low-power-disable;
+ };
+
+ conf-bootstrap {
+ pins = "MIO44", "MIO49";
+ bias-disable;
+ output-enable;
+ low-power-disable;
+ };
+
+ conf-tx {
+ pins = "MIO38", "MIO39", "MIO40",
+ "MIO41", "MIO42", "MIO43";
+ bias-disable;
+ output-enable;
+ low-power-enable;
+ };
+
+ conf-mdio {
+ groups = "mdio1_0_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ bias-disable;
+ output-enable;
+ };
+
+ mux-mdio {
+ function = "mdio1";
+ groups = "mdio1_0_grp";
+ };
+
+ mux {
+ function = "ethernet1";
+ groups = "ethernet1_0_grp";
+ };
+ };
+
+ pinctrl_usb0_default: usb0-default {
+ conf {
+ groups = "usb0_0_grp";
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ conf-rx {
+ pins = "MIO52", "MIO53", "MIO55";
+ bias-high-impedance;
+ drive-strength = <12>;
+ slew-rate = <SLEW_RATE_FAST>;
+ };
+
+ conf-tx {
+ pins = "MIO54", "MIO56", "MIO57", "MIO58", "MIO59",
+ "MIO60", "MIO61", "MIO62", "MIO63";
+ bias-disable;
+ output-enable;
+ drive-strength = <4>;
+ slew-rate = <SLEW_RATE_SLOW>;
+ };
+
+ mux {
+ groups = "usb0_0_grp";
+ function = "usb0";
+ };
+ };
+
+ pinctrl_usb1_default: usb1-default {
+ conf {
+ groups = "usb1_0_grp";
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ conf-rx {
+ pins = "MIO64", "MIO65", "MIO67";
+ bias-high-impedance;
+ drive-strength = <12>;
+ slew-rate = <SLEW_RATE_FAST>;
+ };
+
+ conf-tx {
+ pins = "MIO66", "MIO68", "MIO69", "MIO70", "MIO71",
+ "MIO72", "MIO73", "MIO74", "MIO75";
+ bias-disable;
+ output-enable;
+ drive-strength = <4>;
+ slew-rate = <SLEW_RATE_SLOW>;
+ };
+
+ mux {
+ groups = "usb1_0_grp";
+ function = "usb1";
+ };
+ };
+};
+
+&uart0 {
+ status = "okay";
+ rts-gpios = <&gpio 72 GPIO_ACTIVE_HIGH>;
+ linux,rs485-enabled-at-boot-time;
+ rs485-rts-delay = <10 10>;
+ pinctrl-names = "default";
+ pinctrl-0 = <&pinctrl_uart0_default>;
+ assigned-clock-rates = <100000000>;
+};
+
+&uart1 {
+ status = "okay";
+ pinctrl-names = "default";
+ pinctrl-0 = <&pinctrl_uart1_default>;
+};
+
+&zynqmp_dpsub {
+ status = "disabled";
+};
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-sck-kr-g-revA.dtso b/arch/arm64/boot/dts/xilinx/zynqmp-sck-kr-g-revA.dtso
new file mode 100644
index 000000000000..fbacfa984d76
--- /dev/null
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-sck-kr-g-revA.dtso
@@ -0,0 +1,438 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * dts file for KR260 revA Carrier Card
+ *
+ * (C) Copyright 2021, Xilinx, Inc.
+ *
+ * Michal Simek <michal.simek@amd.com>
+ */
+
+#include <dt-bindings/gpio/gpio.h>
+#include <dt-bindings/net/ti-dp83867.h>
+#include <dt-bindings/phy/phy.h>
+#include <dt-bindings/pinctrl/pinctrl-zynqmp.h>
+
+/dts-v1/;
+/plugin/;
+
+&{/} {
+ compatible = "xlnx,zynqmp-sk-kr260-revA",
+ "xlnx,zynqmp-sk-kr260", "xlnx,zynqmp";
+ model = "ZynqMP KR260 revA";
+
+ aliases {
+ ethernet0 = "/axi/ethernet@ff0b0000"; /* &gem0 */
+ ethernet1 = "/axi/ethernet@ff0c0000"; /* &gem1 */
+ };
+
+ ina260-u14 {
+ compatible = "iio-hwmon";
+ io-channels = <&u14 0>, <&u14 1>, <&u14 2>;
+ };
+
+ clk_27: clock0 { /* u86 - DP */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <27000000>;
+ };
+
+ clk_125: si5332-0 { /* u17 - GEM0/1 */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <125000000>;
+ };
+
+ clk_74: si5332-5 { /* u17 - SLVC-EC */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <74250000>;
+ };
+
+ clk_26: si5332-2 { /* u17 - USB */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <26000000>;
+ };
+
+ clk_156: si5332-3 { /* u17 - SFP+ */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <156250000>;
+ };
+
+ clk_25_0: si5332-1 { /* u17 - GEM2 */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <25000000>;
+ };
+
+ clk_25_1: si5332-4 { /* u17 - GEM3 */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <25000000>;
+ };
+};
+
+&i2c1 { /* I2C_SCK C26/C27 - MIO from SOM */
+ #address-cells = <1>;
+ #size-cells = <0>;
+ pinctrl-names = "default", "gpio";
+ pinctrl-0 = <&pinctrl_i2c1_default>;
+ pinctrl-1 = <&pinctrl_i2c1_gpio>;
+ scl-gpios = <&gpio 24 (GPIO_ACTIVE_HIGH | GPIO_OPEN_DRAIN)>;
+ sda-gpios = <&gpio 25 (GPIO_ACTIVE_HIGH | GPIO_OPEN_DRAIN)>;
+
+ u14: ina260@40 { /* u14 */
+ compatible = "ti,ina260";
+ #io-channel-cells = <1>;
+ label = "ina260-u14";
+ reg = <0x40>;
+ };
+
+ slg7xl45106: gpio@11 { /* u19 - reset logic */
+ compatible = "dlg,slg7xl45106";
+ reg = <0x11>;
+ label = "resetchip";
+ gpio-controller;
+ #gpio-cells = <2>;
+ gpio-line-names = "USB0_PHY_RESET_B", "USB1_PHY_RESET_B",
+ "SD_RESET_B", "USB0_HUB_RESET_B",
+ "USB1_HUB_RESET_B", "PS_GEM0_RESET_B",
+ "PS_GEM1_RESET_B", "";
+ };
+
+ i2c-mux@74 { /* u18 */
+ compatible = "nxp,pca9546";
+ #address-cells = <1>;
+ #size-cells = <0>;
+ reg = <0x74>;
+ usbhub_i2c0: i2c@0 {
+ #address-cells = <1>;
+ #size-cells = <0>;
+ reg = <0>;
+ hub_1: usb-hub@2d {
+ compatible = "microchip,usb5744";
+ reg = <0x2d>;
+ };
+ };
+ usbhub_i2c1: i2c@1 {
+ #address-cells = <1>;
+ #size-cells = <0>;
+ reg = <1>;
+ hub_2: usb-hub@2d {
+ compatible = "microchip,usb5744";
+ reg = <0x2d>;
+ };
+ };
+ /* Bus 2/3 are not connected */
+ };
+
+ /* si5332@6a - u17 - clock-generator */
+};
+
+/* GEM SGMII/DP and USB 3.0 */
+&psgtr {
+ status = "okay";
+ /* gem0/1, dp, usb */
+ clocks = <&clk_125>, <&clk_27>, <&clk_26>;
+ clock-names = "ref0", "ref1", "ref2";
+};
+
+&zynqmp_dpsub {
+ status = "okay";
+ phy-names = "dp-phy0";
+ phys = <&psgtr 1 PHY_TYPE_DP 0 1>;
+ assigned-clock-rates = <27000000>, <25000000>, <300000000>;
+};
+
+&zynqmp_dpdma {
+ status = "okay";
+ assigned-clock-rates = <600000000>;
+};
+
+&usb0 { /* mio52 - mio63 */
+ status = "okay";
+ pinctrl-names = "default";
+ pinctrl-0 = <&pinctrl_usb0_default>;
+ phy-names = "usb3-phy";
+ phys = <&psgtr 2 PHY_TYPE_USB3 0 2>;
+ reset-gpios = <&slg7xl45106 0 GPIO_ACTIVE_LOW>;
+ assigned-clock-rates = <250000000>, <20000000>;
+};
+
+&dwc3_0 {
+ status = "okay";
+ dr_mode = "host";
+ snps,usb3_lpm_capable;
+ maximum-speed = "super-speed";
+ #address-cells = <1>;
+ #size-cells = <0>;
+
+ /* 2.0 hub on port 1 */
+ hub_2_0: hub@1 {
+ compatible = "usb424,2744";
+ reg = <1>;
+ peer-hub = <&hub_3_0>;
+ i2c-bus = <&hub_1>;
+ reset-gpios = <&slg7xl45106 3 GPIO_ACTIVE_LOW>;
+ };
+
+ /* 3.0 hub on port 2 */
+ hub_3_0: hub@2 {
+ compatible = "usb424,5744";
+ reg = <2>;
+ peer-hub = <&hub_2_0>;
+ i2c-bus = <&hub_1>;
+ reset-gpios = <&slg7xl45106 3 GPIO_ACTIVE_LOW>;
+ };
+};
+
+&usb1 { /* mio64 - mio75 */
+ status = "okay";
+ pinctrl-names = "default";
+ pinctrl-0 = <&pinctrl_usb1_default>;
+ phy-names = "usb3-phy";
+ phys = <&psgtr 3 PHY_TYPE_USB3 1 2>;
+ reset-gpios = <&slg7xl45106 1 GPIO_ACTIVE_LOW>;
+ assigned-clock-rates = <250000000>, <20000000>;
+};
+
+&dwc3_1 {
+ status = "okay";
+ dr_mode = "host";
+ snps,usb3_lpm_capable;
+ maximum-speed = "super-speed";
+ #address-cells = <1>;
+ #size-cells = <0>;
+
+ /* 2.0 hub on port 1 */
+ hub1_2_0: hub@1 {
+ compatible = "usb424,2744";
+ reg = <1>;
+ peer-hub = <&hub1_3_0>;
+ i2c-bus = <&hub_2>;
+ reset-gpios = <&slg7xl45106 4 GPIO_ACTIVE_LOW>;
+ };
+
+ /* 3.0 hub on port 2 */
+ hub1_3_0: hub@2 {
+ compatible = "usb424,5744";
+ reg = <2>;
+ peer-hub = <&hub1_2_0>;
+ i2c-bus = <&hub_2>;
+ reset-gpios = <&slg7xl45106 4 GPIO_ACTIVE_LOW>;
+ };
+};
+
+&gem0 { /* mdio mio50/51 */
+ status = "okay";
+ phys = <&psgtr 0 PHY_TYPE_SGMII 0 0>;
+ phy-handle = <&phy0>;
+ phy-mode = "sgmii";
+ assigned-clock-rates = <250000000>;
+};
+
+&gem1 { /* mdio mio50/51, gem mio38 - mio49 */
+ status = "okay";
+ pinctrl-names = "default";
+ pinctrl-0 = <&pinctrl_gem1_default>;
+ phy-handle = <&phy1>;
+ phy-mode = "rgmii-id";
+ assigned-clock-rates = <250000000>;
+
+ mdio: mdio {
+ #address-cells = <1>;
+ #size-cells = <0>;
+ phy0: ethernet-phy@4 { /* u81 */
+ #phy-cells = <1>;
+ compatible = "ethernet-phy-id2000.a231";
+ reg = <4>;
+ ti,rx-internal-delay = <DP83867_RGMIIDCTL_2_25_NS>;
+ ti,tx-internal-delay = <DP83867_RGMIIDCTL_2_75_NS>;
+ ti,fifo-depth = <DP83867_PHYCR_FIFO_DEPTH_4_B_NIB>;
+ ti,dp83867-rxctrl-strap-quirk;
+ reset-assert-us = <300>;
+ reset-deassert-us = <280>;
+ reset-gpios = <&slg7xl45106 5 GPIO_ACTIVE_LOW>;
+ };
+ phy1: ethernet-phy@8 { /* u36 */
+ #phy-cells = <1>;
+ compatible = "ethernet-phy-id2000.a231";
+ reg = <8>;
+ ti,rx-internal-delay = <DP83867_RGMIIDCTL_2_25_NS>;
+ ti,tx-internal-delay = <DP83867_RGMIIDCTL_2_75_NS>;
+ ti,fifo-depth = <DP83867_PHYCR_FIFO_DEPTH_4_B_NIB>;
+ ti,dp83867-rxctrl-strap-quirk;
+ reset-assert-us = <100>;
+ reset-deassert-us = <280>;
+ reset-gpios = <&slg7xl45106 6 GPIO_ACTIVE_LOW>;
+ };
+ };
+};
+
+/* gem2/gem3 via PL with phys u79@2 and u80@3 */
+
+&pinctrl0 {
+ status = "okay";
+
+ pinctrl_uart1_default: uart1-default {
+ conf {
+ groups = "uart1_9_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ drive-strength = <12>;
+ };
+
+ conf-rx {
+ pins = "MIO37";
+ bias-high-impedance;
+ };
+
+ conf-tx {
+ pins = "MIO36";
+ bias-disable;
+ output-enable;
+ };
+
+ mux {
+ groups = "uart1_9_grp";
+ function = "uart1";
+ };
+ };
+
+ pinctrl_i2c1_default: i2c1-default {
+ conf {
+ groups = "i2c1_6_grp";
+ bias-pull-up;
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ mux {
+ groups = "i2c1_6_grp";
+ function = "i2c1";
+ };
+ };
+
+ pinctrl_i2c1_gpio: i2c1-gpio-grp {
+ conf {
+ groups = "gpio0_24_grp", "gpio0_25_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ mux {
+ groups = "gpio0_24_grp", "gpio0_25_grp";
+ function = "gpio0";
+ };
+ };
+
+ pinctrl_gem1_default: gem1-default {
+ conf {
+ groups = "ethernet1_0_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ conf-rx {
+ pins = "MIO44", "MIO46", "MIO48";
+ bias-high-impedance;
+ low-power-disable;
+ };
+
+ conf-bootstrap {
+ pins = "MIO45", "MIO47", "MIO49";
+ bias-disable;
+ output-enable;
+ low-power-disable;
+ };
+
+ conf-tx {
+ pins = "MIO38", "MIO39", "MIO40",
+ "MIO41", "MIO42", "MIO43";
+ bias-disable;
+ output-enable;
+ low-power-enable;
+ };
+
+ conf-mdio {
+ groups = "mdio1_0_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ bias-disable;
+ output-enable;
+ };
+
+ mux-mdio {
+ function = "mdio1";
+ groups = "mdio1_0_grp";
+ };
+
+ mux {
+ function = "ethernet1";
+ groups = "ethernet1_0_grp";
+ };
+ };
+
+ pinctrl_usb0_default: usb0-default {
+ conf {
+ groups = "usb0_0_grp";
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ conf-rx {
+ pins = "MIO52", "MIO53", "MIO55";
+ bias-high-impedance;
+ drive-strength = <12>;
+ slew-rate = <SLEW_RATE_FAST>;
+ };
+
+ conf-tx {
+ pins = "MIO54", "MIO56", "MIO57", "MIO58", "MIO59",
+ "MIO60", "MIO61", "MIO62", "MIO63";
+ bias-disable;
+ output-enable;
+ drive-strength = <4>;
+ slew-rate = <SLEW_RATE_SLOW>;
+ };
+
+ mux {
+ groups = "usb0_0_grp";
+ function = "usb0";
+ };
+ };
+
+ pinctrl_usb1_default: usb1-default {
+ conf {
+ groups = "usb1_0_grp";
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ conf-rx {
+ pins = "MIO64", "MIO65", "MIO67";
+ bias-high-impedance;
+ drive-strength = <12>;
+ slew-rate = <SLEW_RATE_FAST>;
+ };
+
+ conf-tx {
+ pins = "MIO66", "MIO68", "MIO69", "MIO70", "MIO71",
+ "MIO72", "MIO73", "MIO74", "MIO75";
+ bias-disable;
+ output-enable;
+ drive-strength = <4>;
+ slew-rate = <SLEW_RATE_SLOW>;
+ };
+
+ mux {
+ groups = "usb1_0_grp";
+ function = "usb1";
+ };
+ };
+};
+
+&uart1 {
+ status = "okay";
+ pinctrl-names = "default";
+ pinctrl-0 = <&pinctrl_uart1_default>;
+};
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-sck-kr-g-revB.dtso b/arch/arm64/boot/dts/xilinx/zynqmp-sck-kr-g-revB.dtso
new file mode 100644
index 000000000000..b7cda216b179
--- /dev/null
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-sck-kr-g-revB.dtso
@@ -0,0 +1,451 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * dts file for KR260 revB Carrier Card (A03 revision)
+ *
+ * (C) Copyright 2021 - 2022, Xilinx, Inc.
+ *
+ * Michal Simek <michal.simek@amd.com>
+ */
+
+#include <dt-bindings/gpio/gpio.h>
+#include <dt-bindings/net/ti-dp83867.h>
+#include <dt-bindings/phy/phy.h>
+#include <dt-bindings/pinctrl/pinctrl-zynqmp.h>
+
+/dts-v1/;
+/plugin/;
+
+&{/} {
+ compatible = "xlnx,zynqmp-sk-kr260-revB",
+ "xlnx,zynqmp-sk-kr260", "xlnx,zynqmp";
+ model = "ZynqMP KR260 revB";
+
+ ina260-u14 {
+ compatible = "iio-hwmon";
+ io-channels = <&u14 0>, <&u14 1>, <&u14 2>;
+ };
+
+ clk_125: clock0 { /* u87 - GEM0/1 */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <125000000>;
+ };
+
+ clk_27: clock1 { /* u86 - DP */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <27000000>;
+ };
+
+ clk_26: clock2 { /* u89 - USB */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <26000000>;
+ };
+
+ clk_156: clock3 { /* u90 - SFP+ */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <156250000>;
+ };
+
+ clk_25_0: clock4 { /* u92/u91 - GEM2 */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <25000000>;
+ };
+
+ clk_25_1: clock5 { /* u92/u91 - GEM3 */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <25000000>;
+ };
+
+ clk_74: clock6 { /* u88 - SLVC-EC */
+ compatible = "fixed-clock";
+ #clock-cells = <0>;
+ clock-frequency = <74250000>;
+ };
+
+ dpcon {
+ compatible = "dp-connector";
+ label = "P11";
+ type = "full-size";
+
+ port {
+ dpcon_in: endpoint {
+ remote-endpoint = <&dpsub_dp_out>;
+ };
+ };
+ };
+};
+
+&i2c1 { /* I2C_SCK C26/C27 - MIO from SOM */
+ #address-cells = <1>;
+ #size-cells = <0>;
+ pinctrl-names = "default", "gpio";
+ pinctrl-0 = <&pinctrl_i2c1_default>;
+ pinctrl-1 = <&pinctrl_i2c1_gpio>;
+ scl-gpios = <&gpio 24 (GPIO_ACTIVE_HIGH | GPIO_OPEN_DRAIN)>;
+ sda-gpios = <&gpio 25 (GPIO_ACTIVE_HIGH | GPIO_OPEN_DRAIN)>;
+
+ u14: ina260@40 { /* u14 */
+ compatible = "ti,ina260";
+ #io-channel-cells = <1>;
+ label = "ina260-u14";
+ reg = <0x40>;
+ };
+
+ slg7xl45106: gpio@11 { /* u19 - reset logic */
+ compatible = "dlg,slg7xl45106";
+ reg = <0x11>;
+ label = "resetchip";
+ gpio-controller;
+ #gpio-cells = <2>;
+ gpio-line-names = "USB0_PHY_RESET_B", "USB1_PHY_RESET_B",
+ "SD_RESET_B", "USB0_HUB_RESET_B",
+ "USB1_HUB_RESET_B", "PS_GEM0_RESET_B",
+ "PS_GEM1_RESET_B", "";
+ };
+
+ i2c-mux@74 { /* u18 */
+ compatible = "nxp,pca9546";
+ #address-cells = <1>;
+ #size-cells = <0>;
+ reg = <0x74>;
+ usbhub_i2c0: i2c@0 {
+ #address-cells = <1>;
+ #size-cells = <0>;
+ reg = <0>;
+ hub_1: usb-hub@2d {
+ compatible = "microchip,usb5744";
+ reg = <0x2d>;
+ };
+ };
+ usbhub_i2c1: i2c@1 {
+ #address-cells = <1>;
+ #size-cells = <0>;
+ reg = <1>;
+ hub_2: usb-hub@2d {
+ compatible = "microchip,usb5744";
+ reg = <0x2d>;
+ };
+ };
+ /* Bus 2/3 are not connected */
+ };
+
+ /* si5332@6a - u17 - clock-generator */
+};
+
+/* GEM SGMII/DP and USB 3.0 */
+&psgtr {
+ status = "okay";
+ /* gem0/1, dp, usb */
+ clocks = <&clk_125>, <&clk_27>, <&clk_26>;
+ clock-names = "ref0", "ref1", "ref2";
+};
+
+&zynqmp_dpsub {
+ status = "okay";
+ phy-names = "dp-phy0";
+ phys = <&psgtr 1 PHY_TYPE_DP 0 1>;
+ assigned-clock-rates = <27000000>, <25000000>, <300000000>;
+};
+
+&out_dp {
+ dpsub_dp_out: endpoint {
+ remote-endpoint = <&dpcon_in>;
+ };
+};
+
+&zynqmp_dpdma {
+ status = "okay";
+ assigned-clock-rates = <600000000>;
+};
+
+&usb0 { /* mio52 - mio63 */
+ status = "okay";
+ pinctrl-names = "default";
+ pinctrl-0 = <&pinctrl_usb0_default>;
+ phy-names = "usb3-phy";
+ phys = <&psgtr 2 PHY_TYPE_USB3 0 2>;
+ reset-gpios = <&slg7xl45106 0 GPIO_ACTIVE_LOW>;
+ assigned-clock-rates = <250000000>, <20000000>;
+};
+
+&dwc3_0 {
+ status = "okay";
+ dr_mode = "host";
+ snps,usb3_lpm_capable;
+ maximum-speed = "super-speed";
+ #address-cells = <1>;
+ #size-cells = <0>;
+
+ /* 2.0 hub on port 1 */
+ hub_2_0: hub@1 {
+ compatible = "usb424,2744";
+ reg = <1>;
+ peer-hub = <&hub_3_0>;
+ i2c-bus = <&hub_1>;
+ reset-gpios = <&slg7xl45106 3 GPIO_ACTIVE_LOW>;
+ };
+
+ /* 3.0 hub on port 2 */
+ hub_3_0: hub@2 {
+ compatible = "usb424,5744";
+ reg = <2>;
+ peer-hub = <&hub_2_0>;
+ i2c-bus = <&hub_1>;
+ reset-gpios = <&slg7xl45106 3 GPIO_ACTIVE_LOW>;
+ };
+};
+
+&usb1 { /* mio64 - mio75 */
+ status = "okay";
+ pinctrl-names = "default";
+ pinctrl-0 = <&pinctrl_usb1_default>;
+ phy-names = "usb3-phy";
+ phys = <&psgtr 3 PHY_TYPE_USB3 1 2>;
+ reset-gpios = <&slg7xl45106 1 GPIO_ACTIVE_LOW>;
+ assigned-clock-rates = <250000000>, <20000000>;
+};
+
+&dwc3_1 {
+ status = "okay";
+ dr_mode = "host";
+ snps,usb3_lpm_capable;
+ maximum-speed = "super-speed";
+ #address-cells = <1>;
+ #size-cells = <0>;
+
+ /* 2.0 hub on port 1 */
+ hub1_2_0: hub@1 {
+ compatible = "usb424,2744";
+ reg = <1>;
+ peer-hub = <&hub1_3_0>;
+ i2c-bus = <&hub_2>;
+ reset-gpios = <&slg7xl45106 4 GPIO_ACTIVE_LOW>;
+ };
+
+ /* 3.0 hub on port 2 */
+ hub1_3_0: hub@2 {
+ compatible = "usb424,5744";
+ reg = <2>;
+ peer-hub = <&hub1_2_0>;
+ i2c-bus = <&hub_2>;
+ reset-gpios = <&slg7xl45106 4 GPIO_ACTIVE_LOW>;
+ };
+};
+
+&gem0 { /* mdio mio50/51 */
+ status = "okay";
+ phys = <&psgtr 0 PHY_TYPE_SGMII 0 0>;
+ phy-handle = <&phy0>;
+ phy-mode = "sgmii";
+ assigned-clock-rates = <250000000>;
+};
+
+&gem1 { /* mdio mio50/51, gem mio38 - mio49 */
+ status = "okay";
+ pinctrl-names = "default";
+ pinctrl-0 = <&pinctrl_gem1_default>;
+ phy-handle = <&phy1>;
+ phy-mode = "rgmii-id";
+ assigned-clock-rates = <250000000>;
+
+ mdio: mdio {
+ #address-cells = <1>;
+ #size-cells = <0>;
+ phy0: ethernet-phy@4 { /* u81 */
+ #phy-cells = <1>;
+ compatible = "ethernet-phy-id2000.a231";
+ reg = <4>;
+ ti,rx-internal-delay = <DP83867_RGMIIDCTL_2_25_NS>;
+ ti,tx-internal-delay = <DP83867_RGMIIDCTL_2_75_NS>;
+ ti,fifo-depth = <DP83867_PHYCR_FIFO_DEPTH_4_B_NIB>;
+ ti,dp83867-rxctrl-strap-quirk;
+ reset-assert-us = <300>;
+ reset-deassert-us = <280>;
+ reset-gpios = <&slg7xl45106 5 GPIO_ACTIVE_LOW>;
+ };
+ phy1: ethernet-phy@8 { /* u36 */
+ #phy-cells = <1>;
+ compatible = "ethernet-phy-id2000.a231";
+ reg = <8>;
+ ti,rx-internal-delay = <DP83867_RGMIIDCTL_2_25_NS>;
+ ti,tx-internal-delay = <DP83867_RGMIIDCTL_2_75_NS>;
+ ti,fifo-depth = <DP83867_PHYCR_FIFO_DEPTH_4_B_NIB>;
+ ti,dp83867-rxctrl-strap-quirk;
+ reset-assert-us = <100>;
+ reset-deassert-us = <280>;
+ reset-gpios = <&slg7xl45106 6 GPIO_ACTIVE_LOW>;
+ };
+ };
+};
+
+/* gem2/gem3 via PL with phys u79@2 and u80@3 */
+
+&pinctrl0 {
+ status = "okay";
+
+ pinctrl_uart1_default: uart1-default {
+ conf {
+ groups = "uart1_9_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ drive-strength = <12>;
+ };
+
+ conf-rx {
+ pins = "MIO37";
+ bias-high-impedance;
+ };
+
+ conf-tx {
+ pins = "MIO36";
+ bias-disable;
+ output-enable;
+ };
+
+ mux {
+ groups = "uart1_9_grp";
+ function = "uart1";
+ };
+ };
+
+ pinctrl_i2c1_default: i2c1-default {
+ conf {
+ groups = "i2c1_6_grp";
+ bias-pull-up;
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ mux {
+ groups = "i2c1_6_grp";
+ function = "i2c1";
+ };
+ };
+
+ pinctrl_i2c1_gpio: i2c1-gpio-grp {
+ conf {
+ groups = "gpio0_24_grp", "gpio0_25_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ mux {
+ groups = "gpio0_24_grp", "gpio0_25_grp";
+ function = "gpio0";
+ };
+ };
+
+ pinctrl_gem1_default: gem1-default {
+ conf {
+ groups = "ethernet1_0_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ conf-rx {
+ pins = "MIO44", "MIO46", "MIO48";
+ bias-high-impedance;
+ low-power-disable;
+ };
+
+ conf-bootstrap {
+ pins = "MIO45", "MIO47", "MIO49";
+ bias-disable;
+ output-enable;
+ low-power-disable;
+ };
+
+ conf-tx {
+ pins = "MIO38", "MIO39", "MIO40",
+ "MIO41", "MIO42", "MIO43";
+ bias-disable;
+ output-enable;
+ low-power-enable;
+ };
+
+ conf-mdio {
+ groups = "mdio1_0_grp";
+ slew-rate = <SLEW_RATE_SLOW>;
+ power-source = <IO_STANDARD_LVCMOS18>;
+ bias-disable;
+ output-enable;
+ };
+
+ mux-mdio {
+ function = "mdio1";
+ groups = "mdio1_0_grp";
+ };
+
+ mux {
+ function = "ethernet1";
+ groups = "ethernet1_0_grp";
+ };
+ };
+
+ pinctrl_usb0_default: usb0-default {
+ conf {
+ groups = "usb0_0_grp";
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ conf-rx {
+ pins = "MIO52", "MIO53", "MIO55";
+ bias-high-impedance;
+ drive-strength = <12>;
+ slew-rate = <SLEW_RATE_FAST>;
+ };
+
+ conf-tx {
+ pins = "MIO54", "MIO56", "MIO57", "MIO58", "MIO59",
+ "MIO60", "MIO61", "MIO62", "MIO63";
+ bias-disable;
+ output-enable;
+ drive-strength = <4>;
+ slew-rate = <SLEW_RATE_SLOW>;
+ };
+
+ mux {
+ groups = "usb0_0_grp";
+ function = "usb0";
+ };
+ };
+
+ pinctrl_usb1_default: usb1-default {
+ conf {
+ groups = "usb1_0_grp";
+ power-source = <IO_STANDARD_LVCMOS18>;
+ };
+
+ conf-rx {
+ pins = "MIO64", "MIO65", "MIO67";
+ bias-high-impedance;
+ drive-strength = <12>;
+ slew-rate = <SLEW_RATE_FAST>;
+ };
+
+ conf-tx {
+ pins = "MIO66", "MIO68", "MIO69", "MIO70", "MIO71",
+ "MIO72", "MIO73", "MIO74", "MIO75";
+ bias-disable;
+ output-enable;
+ drive-strength = <4>;
+ slew-rate = <SLEW_RATE_SLOW>;
+ };
+
+ mux {
+ groups = "usb1_0_grp";
+ function = "usb1";
+ };
+ };
+};
+
+&uart1 {
+ status = "okay";
+ pinctrl-names = "default";
+ pinctrl-0 = <&pinctrl_uart1_default>;
+};
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-sck-kv-g-revA.dtso b/arch/arm64/boot/dts/xilinx/zynqmp-sck-kv-g-revA.dtso
index 95d16904d765..a98a888d1385 100644
--- a/arch/arm64/boot/dts/xilinx/zynqmp-sck-kv-g-revA.dtso
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-sck-kv-g-revA.dtso
@@ -129,7 +129,6 @@
pinctrl-0 = <&pinctrl_usb0_default>;
phy-names = "usb3-phy";
phys = <&psgtr 2 PHY_TYPE_USB3 0 1>;
- /* missing usb5744 - u43 */
};
&dwc3_0 {
@@ -137,6 +136,24 @@
dr_mode = "host";
snps,usb3_lpm_capable;
maximum-speed = "super-speed";
+ #address-cells = <1>;
+ #size-cells = <0>;
+
+ /* 2.0 hub on port 1 */
+ hub_2_0: hub@1 {
+ compatible = "usb424,2744";
+ reg = <1>;
+ peer-hub = <&hub_3_0>;
+ reset-gpios = <&gpio 44 GPIO_ACTIVE_LOW>;
+ };
+
+ /* 3.0 hub on port 2 */
+ hub_3_0: hub@2 {
+ compatible = "usb424,5744";
+ reg = <2>;
+ peer-hub = <&hub_2_0>;
+ reset-gpios = <&gpio 44 GPIO_ACTIVE_LOW>;
+ };
};
&sdhci1 { /* on CC with tuned parameters */
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-sck-kv-g-revB.dtso b/arch/arm64/boot/dts/xilinx/zynqmp-sck-kv-g-revB.dtso
index a74d0ac7e07a..1d2b46d7949e 100644
--- a/arch/arm64/boot/dts/xilinx/zynqmp-sck-kv-g-revB.dtso
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-sck-kv-g-revB.dtso
@@ -92,7 +92,10 @@
label = "ina260-u14";
reg = <0x40>;
};
- /* u43 - 0x2d - USB hub */
+ hub: usb-hub@2d {
+ compatible = "microchip,usb5744";
+ reg = <0x2d>;
+ };
/* u27 - 0xe0 - STDP4320 DP/HDMI splitter */
};
@@ -109,13 +112,11 @@
phy-names = "dp-phy0", "dp-phy1";
phys = <&psgtr 1 PHY_TYPE_DP 0 0>, <&psgtr 0 PHY_TYPE_DP 1 0>;
assigned-clock-rates = <27000000>, <25000000>, <300000000>;
+};
- ports {
- port@5 {
- dpsub_dp_out: endpoint {
- remote-endpoint = <&dpcon_in>;
- };
- };
+&out_dp {
+ dpsub_dp_out: endpoint {
+ remote-endpoint = <&dpcon_in>;
};
};
@@ -138,6 +139,26 @@
dr_mode = "host";
snps,usb3_lpm_capable;
maximum-speed = "super-speed";
+ #address-cells = <1>;
+ #size-cells = <0>;
+
+ /* 2.0 hub on port 1 */
+ hub_2_0: hub@1 {
+ compatible = "usb424,2744";
+ reg = <1>;
+ peer-hub = <&hub_3_0>;
+ i2c-bus = <&hub>;
+ reset-gpios = <&gpio 44 GPIO_ACTIVE_LOW>;
+ };
+
+ /* 3.0 hub on port 2 */
+ hub_3_0: hub@2 {
+ compatible = "usb424,5744";
+ reg = <2>;
+ peer-hub = <&hub_2_0>;
+ i2c-bus = <&hub>;
+ reset-gpios = <&gpio 44 GPIO_ACTIVE_LOW>;
+ };
};
&sdhci1 { /* on CC with tuned parameters */
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-sm-k24-revA.dts b/arch/arm64/boot/dts/xilinx/zynqmp-sm-k24-revA.dts
new file mode 100644
index 000000000000..653bd9362264
--- /dev/null
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-sm-k24-revA.dts
@@ -0,0 +1,23 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * dts file for Xilinx ZynqMP SM-K24 RevA
+ *
+ * (C) Copyright 2020 - 2021, Xilinx, Inc.
+ * (C) Copyright 2022, Advanced Micro Devices, Inc.
+ *
+ * Michal Simek <michal.simek@amd.com>
+ */
+
+#include "zynqmp-sm-k26-revA.dts"
+
+/ {
+ model = "ZynqMP SM-K24 RevA/B/1";
+ compatible = "xlnx,zynqmp-sm-k24-rev1", "xlnx,zynqmp-sm-k24-revB",
+ "xlnx,zynqmp-sm-k24-revA", "xlnx,zynqmp-sm-k24",
+ "xlnx,zynqmp";
+
+ memory@0 {
+ device_type = "memory"; /* 2GB */
+ reg = <0 0 0 0x80000000>;
+ };
+};
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-sm-k26-revA.dts b/arch/arm64/boot/dts/xilinx/zynqmp-sm-k26-revA.dts
index bfa7ea6b9224..500af1d2232f 100644
--- a/arch/arm64/boot/dts/xilinx/zynqmp-sm-k26-revA.dts
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-sm-k26-revA.dts
@@ -90,10 +90,10 @@
};
};
- pwm-fan {
+ pwm_fan: pwm-fan {
compatible = "pwm-fan";
status = "okay";
- pwms = <&ttc0 2 40000 0>;
+ pwms = <&ttc0 2 40000 1>;
};
};
@@ -233,6 +233,9 @@
pinctrl-0 = <&pinctrl_sdhci0_default>;
non-removable;
disable-wp;
+ no-sd;
+ no-sdio;
+ cap-mmc-hw-reset;
bus-width = <8>;
xlnx,mio-bank = <0>;
assigned-clock-rates = <187498123>;
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-smk-k24-revA.dts b/arch/arm64/boot/dts/xilinx/zynqmp-smk-k24-revA.dts
new file mode 100644
index 000000000000..7308983b15a0
--- /dev/null
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-smk-k24-revA.dts
@@ -0,0 +1,21 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * dts file for Xilinx ZynqMP SMK-K24 RevA
+ *
+ * (C) Copyright 2020 - 2021, Xilinx, Inc.
+ * (C) Copyright 2022, Advanced Micro Devices, Inc.
+ *
+ * Michal Simek <michal.simek@amd.com>
+ */
+
+#include "zynqmp-sm-k24-revA.dts"
+
+/ {
+ model = "ZynqMP SMK-K24 RevA";
+ compatible = "xlnx,zynqmp-smk-k24-revA", "xlnx,zynqmp-smk-k24",
+ "xlnx,zynqmp";
+};
+
+&sdhci0 {
+ status = "disabled";
+};
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-zc1751-xm016-dc2.dts b/arch/arm64/boot/dts/xilinx/zynqmp-zc1751-xm016-dc2.dts
index 1850325e1d6c..2ad7423c2f05 100644
--- a/arch/arm64/boot/dts/xilinx/zynqmp-zc1751-xm016-dc2.dts
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-zc1751-xm016-dc2.dts
@@ -135,7 +135,6 @@
status = "okay";
pinctrl-names = "default";
pinctrl-0 = <&pinctrl_nand0_default>;
- arasan,has-mdma;
nand@0 {
reg = <0x0>;
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-zc1751-xm017-dc3.dts b/arch/arm64/boot/dts/xilinx/zynqmp-zc1751-xm017-dc3.dts
index f553b317e6b2..8fbc33562bc4 100644
--- a/arch/arm64/boot/dts/xilinx/zynqmp-zc1751-xm017-dc3.dts
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-zc1751-xm017-dc3.dts
@@ -129,7 +129,6 @@
/* MT29F64G08AECDBJ4-6 */
&nand0 {
status = "okay";
- arasan,has-mdma;
num-cs = <2>;
};
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-zcu100-revC.dts b/arch/arm64/boot/dts/xilinx/zynqmp-zcu100-revC.dts
index 62c2503a502a..4ec8a400494e 100644
--- a/arch/arm64/boot/dts/xilinx/zynqmp-zcu100-revC.dts
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-zcu100-revC.dts
@@ -134,6 +134,18 @@
#clock-cells = <0>;
clock-frequency = <27000000>;
};
+
+ dpcon {
+ compatible = "dp-connector";
+ label = "P11";
+ type = "full-size";
+
+ port {
+ dpcon_in: endpoint {
+ remote-endpoint = <&dpsub_dp_out>;
+ };
+ };
+ };
};
&dcc {
@@ -509,6 +521,9 @@
xlnx,mio-bank = <0>;
non-removable;
disable-wp;
+ no-sd;
+ no-sdio;
+ cap-mmc-hw-reset;
cap-power-off-card;
mmc-pwrseq = <&sdio_pwrseq>;
vqmmc-supply = <&wmmcsdio_fixed>;
@@ -604,3 +619,9 @@
phys = <&psgtr 1 PHY_TYPE_DP 0 1>,
<&psgtr 0 PHY_TYPE_DP 1 1>;
};
+
+&out_dp {
+ dpsub_dp_out: endpoint {
+ remote-endpoint = <&dpcon_in>;
+ };
+};
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-zcu102-revA.dts b/arch/arm64/boot/dts/xilinx/zynqmp-zcu102-revA.dts
index 7e26489a1539..e172a30e7b21 100644
--- a/arch/arm64/boot/dts/xilinx/zynqmp-zcu102-revA.dts
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-zcu102-revA.dts
@@ -151,6 +151,18 @@
#clock-cells = <0>;
clock-frequency = <114285000>;
};
+
+ dpcon {
+ compatible = "dp-connector";
+ label = "P11";
+ type = "full-size";
+
+ port {
+ dpcon_in: endpoint {
+ remote-endpoint = <&dpsub_dp_out>;
+ };
+ };
+ };
};
&can1 {
@@ -1045,3 +1057,9 @@
phy-names = "dp-phy0";
phys = <&psgtr 1 PHY_TYPE_DP 0 3>;
};
+
+&out_dp {
+ dpsub_dp_out: endpoint {
+ remote-endpoint = <&dpcon_in>;
+ };
+};
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-zcu104-revA.dts b/arch/arm64/boot/dts/xilinx/zynqmp-zcu104-revA.dts
index eb2090673ec1..fe8f151ed706 100644
--- a/arch/arm64/boot/dts/xilinx/zynqmp-zcu104-revA.dts
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-zcu104-revA.dts
@@ -60,6 +60,18 @@
#clock-cells = <0>;
clock-frequency = <27000000>;
};
+
+ dpcon {
+ compatible = "dp-connector";
+ label = "P11";
+ type = "full-size";
+
+ port {
+ dpcon_in: endpoint {
+ remote-endpoint = <&dpsub_dp_out>;
+ };
+ };
+ };
};
&can1 {
@@ -529,3 +541,9 @@
phys = <&psgtr 1 PHY_TYPE_DP 0 3>,
<&psgtr 0 PHY_TYPE_DP 1 3>;
};
+
+&out_dp {
+ dpsub_dp_out: endpoint {
+ remote-endpoint = <&dpcon_in>;
+ };
+};
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-zcu104-revC.dts b/arch/arm64/boot/dts/xilinx/zynqmp-zcu104-revC.dts
index 4694d0a841f1..3ee8ab224722 100644
--- a/arch/arm64/boot/dts/xilinx/zynqmp-zcu104-revC.dts
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-zcu104-revC.dts
@@ -65,6 +65,18 @@
#clock-cells = <0>;
clock-frequency = <27000000>;
};
+
+ dpcon {
+ compatible = "dp-connector";
+ label = "P11";
+ type = "full-size";
+
+ port {
+ dpcon_in: endpoint {
+ remote-endpoint = <&dpsub_dp_out>;
+ };
+ };
+ };
};
&can1 {
@@ -541,3 +553,9 @@
phys = <&psgtr 1 PHY_TYPE_DP 0 3>,
<&psgtr 0 PHY_TYPE_DP 1 3>;
};
+
+&out_dp {
+ dpsub_dp_out: endpoint {
+ remote-endpoint = <&dpcon_in>;
+ };
+};
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-zcu106-revA.dts b/arch/arm64/boot/dts/xilinx/zynqmp-zcu106-revA.dts
index 7beedd730f94..cd132abf6e00 100644
--- a/arch/arm64/boot/dts/xilinx/zynqmp-zcu106-revA.dts
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-zcu106-revA.dts
@@ -1042,12 +1042,10 @@
phy-names = "dp-phy0", "dp-phy1";
phys = <&psgtr 1 PHY_TYPE_DP 0 3>,
<&psgtr 0 PHY_TYPE_DP 1 3>;
+};
- ports {
- port@5 {
- dpsub_dp_out: endpoint {
- remote-endpoint = <&dpcon_in>;
- };
- };
+&out_dp {
+ dpsub_dp_out: endpoint {
+ remote-endpoint = <&dpcon_in>;
};
};
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp-zcu111-revA.dts b/arch/arm64/boot/dts/xilinx/zynqmp-zcu111-revA.dts
index b67ff7ecf3c3..428b5558fbba 100644
--- a/arch/arm64/boot/dts/xilinx/zynqmp-zcu111-revA.dts
+++ b/arch/arm64/boot/dts/xilinx/zynqmp-zcu111-revA.dts
@@ -129,6 +129,18 @@
#clock-cells = <0>;
clock-frequency = <48000000>;
};
+
+ dpcon {
+ compatible = "dp-connector";
+ label = "P11";
+ type = "full-size";
+
+ port {
+ dpcon_in: endpoint {
+ remote-endpoint = <&dpsub_dp_out>;
+ };
+ };
+ };
};
&dcc {
@@ -494,7 +506,7 @@
#address-cells = <1>;
#size-cells = <0>;
reg = <5>;
- sc18is603@2f { /* sc18is602 - u93 */
+ sc18is603: spi@2f { /* sc18is602 - u93 */
compatible = "nxp,sc18is603";
reg = <0x2f>;
/* 4 gpios for CS not handled by driver */
@@ -864,3 +876,9 @@
phys = <&psgtr 1 PHY_TYPE_DP 0 1>,
<&psgtr 0 PHY_TYPE_DP 1 1>;
};
+
+&out_dp {
+ dpsub_dp_out: endpoint {
+ remote-endpoint = <&dpcon_in>;
+ };
+};
diff --git a/arch/arm64/boot/dts/xilinx/zynqmp.dtsi b/arch/arm64/boot/dts/xilinx/zynqmp.dtsi
index e11d282462bd..5f26649c9e11 100644
--- a/arch/arm64/boot/dts/xilinx/zynqmp.dtsi
+++ b/arch/arm64/boot/dts/xilinx/zynqmp.dtsi
@@ -187,7 +187,7 @@
};
psci {
- compatible = "arm,psci-0.2";
+ compatible = "arm,psci-1.0", "arm,psci-0.2";
method = "smc";
};
@@ -1319,22 +1319,22 @@
#address-cells = <1>;
#size-cells = <0>;
- port@0 {
+ live_video: port@0 {
reg = <0>;
};
- port@1 {
+ live_gfx: port@1 {
reg = <1>;
};
- port@2 {
+ live_audio: port@2 {
reg = <2>;
};
- port@3 {
+ out_video: port@3 {
reg = <3>;
};
- port@4 {
+ out_audio: port@4 {
reg = <4>;
};
- port@5 {
+ out_dp: port@5 {
reg = <5>;
};
};
diff --git a/arch/loongarch/boot/dts/loongson-2k0500-ref.dts b/arch/loongarch/boot/dts/loongson-2k0500-ref.dts
index a34734a6c3ce..018ed904352a 100644
--- a/arch/loongarch/boot/dts/loongson-2k0500-ref.dts
+++ b/arch/loongarch/boot/dts/loongson-2k0500-ref.dts
@@ -41,6 +41,15 @@
};
};
+&apbdma3 {
+ status = "okay";
+};
+
+&mmc0 {
+ status = "okay";
+ bus-width = <4>;
+};
+
&gmac0 {
status = "okay";
diff --git a/arch/loongarch/boot/dts/loongson-2k0500.dtsi b/arch/loongarch/boot/dts/loongson-2k0500.dtsi
index 760c60eebb89..588ebc3bded4 100644
--- a/arch/loongarch/boot/dts/loongson-2k0500.dtsi
+++ b/arch/loongarch/boot/dts/loongson-2k0500.dtsi
@@ -104,7 +104,7 @@
status = "disabled";
};
- dma-controller@1fe10c20 {
+ apbdma2: dma-controller@1fe10c20 {
compatible = "loongson,ls2k0500-apbdma", "loongson,ls2k1000-apbdma";
reg = <0 0x1fe10c20 0 0x8>;
interrupt-parent = <&eiointc>;
@@ -114,7 +114,7 @@
status = "disabled";
};
- dma-controller@1fe10c30 {
+ apbdma3: dma-controller@1fe10c30 {
compatible = "loongson,ls2k0500-apbdma", "loongson,ls2k1000-apbdma";
reg = <0 0x1fe10c30 0 0x8>;
interrupt-parent = <&eiointc>;
@@ -437,6 +437,30 @@
status = "disabled";
};
+ mmc0: mmc@1ff64000 {
+ compatible = "loongson,ls2k0500-mmc";
+ reg = <0 0x1ff64000 0 0x2000>,
+ <0 0x1fe10100 0 0x4>;
+ interrupt-parent = <&eiointc>;
+ interrupts = <57>;
+ dmas = <&apbdma3 0>;
+ dma-names = "rx-tx";
+ clocks = <&clk LOONGSON2_APB_CLK>;
+ status = "disabled";
+ };
+
+ mmc@1ff66000 {
+ compatible = "loongson,ls2k0500-mmc";
+ reg = <0 0x1ff66000 0 0x2000>,
+ <0 0x1fe10100 0 0x4>;
+ interrupt-parent = <&eiointc>;
+ interrupts = <58>;
+ dmas = <&apbdma2 0>;
+ dma-names = "rx-tx";
+ clocks = <&clk LOONGSON2_APB_CLK>;
+ status = "disabled";
+ };
+
pmc: power-management@1ff6c000 {
compatible = "loongson,ls2k0500-pmc", "syscon";
reg = <0x0 0x1ff6c000 0x0 0x58>;
diff --git a/arch/loongarch/boot/dts/loongson-2k1000-ref.dts b/arch/loongarch/boot/dts/loongson-2k1000-ref.dts
index 78ea995abf1c..d9a452ada5d7 100644
--- a/arch/loongarch/boot/dts/loongson-2k1000-ref.dts
+++ b/arch/loongarch/boot/dts/loongson-2k1000-ref.dts
@@ -48,6 +48,19 @@
};
};
+&apbdma1 {
+ status = "okay";
+};
+
+&mmc {
+ status = "okay";
+
+ pinctrl-0 = <&sdio_pins_default>;
+ pinctrl-names = "default";
+ bus-width = <4>;
+ cd-gpios = <&gpio0 22 GPIO_ACTIVE_LOW>;
+};
+
&gmac0 {
status = "okay";
diff --git a/arch/loongarch/boot/dts/loongson-2k1000.dtsi b/arch/loongarch/boot/dts/loongson-2k1000.dtsi
index 1da3beb00f0e..d8e01e2534dd 100644
--- a/arch/loongarch/boot/dts/loongson-2k1000.dtsi
+++ b/arch/loongarch/boot/dts/loongson-2k1000.dtsi
@@ -187,14 +187,14 @@
<26 IRQ_TYPE_LEVEL_HIGH>,
<26 IRQ_TYPE_LEVEL_HIGH>,
<26 IRQ_TYPE_LEVEL_HIGH>,
- <>,
- <26 IRQ_TYPE_LEVEL_HIGH>,
+ <0 IRQ_TYPE_NONE>,
<26 IRQ_TYPE_LEVEL_HIGH>,
<26 IRQ_TYPE_LEVEL_HIGH>,
<26 IRQ_TYPE_LEVEL_HIGH>,
<26 IRQ_TYPE_LEVEL_HIGH>,
<26 IRQ_TYPE_LEVEL_HIGH>,
<26 IRQ_TYPE_LEVEL_HIGH>,
+ <26 IRQ_TYPE_NONE>,
<26 IRQ_TYPE_LEVEL_HIGH>,
<26 IRQ_TYPE_LEVEL_HIGH>,
<26 IRQ_TYPE_LEVEL_HIGH>,
@@ -209,13 +209,13 @@
<27 IRQ_TYPE_LEVEL_HIGH>,
<27 IRQ_TYPE_LEVEL_HIGH>,
<27 IRQ_TYPE_LEVEL_HIGH>,
- <>,
+ <0 IRQ_TYPE_NONE>,
<27 IRQ_TYPE_LEVEL_HIGH>,
<27 IRQ_TYPE_LEVEL_HIGH>,
<27 IRQ_TYPE_LEVEL_HIGH>,
<27 IRQ_TYPE_LEVEL_HIGH>,
- <>,
- <>,
+ <0 IRQ_TYPE_NONE>,
+ <0 IRQ_TYPE_NONE>,
<27 IRQ_TYPE_LEVEL_HIGH>,
<27 IRQ_TYPE_LEVEL_HIGH>,
<27 IRQ_TYPE_LEVEL_HIGH>,
@@ -256,7 +256,7 @@
status = "disabled";
};
- dma-controller@1fe00c10 {
+ apbdma1: dma-controller@1fe00c10 {
compatible = "loongson,ls2k1000-apbdma";
reg = <0x0 0x1fe00c10 0x0 0x8>;
interrupt-parent = <&liointc1>;
@@ -405,6 +405,18 @@
status = "disabled";
};
+ mmc: mmc@1fe2c000 {
+ compatible = "loongson,ls2k1000-mmc";
+ reg = <0 0x1fe2c000 0 0x68>,
+ <0 0x1fe00438 0 0x8>;
+ interrupt-parent = <&liointc0>;
+ interrupts = <31 IRQ_TYPE_LEVEL_HIGH>;
+ clocks = <&clk LOONGSON2_APB_CLK>;
+ dmas = <&apbdma1 0>;
+ dma-names = "rx-tx";
+ status = "disabled";
+ };
+
spi0: spi@1fff0220 {
compatible = "loongson,ls2k1000-spi";
reg = <0x0 0x1fff0220 0x0 0x10>;
diff --git a/arch/loongarch/boot/dts/loongson-2k2000-ref.dts b/arch/loongarch/boot/dts/loongson-2k2000-ref.dts
index ea9e6985d0e9..3c6b12220386 100644
--- a/arch/loongarch/boot/dts/loongson-2k2000-ref.dts
+++ b/arch/loongarch/boot/dts/loongson-2k2000-ref.dts
@@ -39,6 +39,16 @@
};
};
+&emmc {
+ status = "okay";
+
+ bus-width = <8>;
+ cap-mmc-highspeed;
+ mmc-hs200-1_8v;
+ no-sd;
+ no-sdio;
+};
+
&sata {
status = "okay";
};
diff --git a/arch/loongarch/boot/dts/loongson-2k2000.dtsi b/arch/loongarch/boot/dts/loongson-2k2000.dtsi
index 9e0411f2754c..00cc485b753b 100644
--- a/arch/loongarch/boot/dts/loongson-2k2000.dtsi
+++ b/arch/loongarch/boot/dts/loongson-2k2000.dtsi
@@ -259,6 +259,24 @@
status = "disabled";
};
+ emmc: mmc@79990000 {
+ compatible = "loongson,ls2k2000-mmc";
+ reg = <0x0 0x79990000 0x0 0x1000>;
+ interrupt-parent = <&pic>;
+ interrupts = <51 IRQ_TYPE_LEVEL_HIGH>;
+ clocks = <&clk LOONGSON2_EMMC_CLK>;
+ status = "disabled";
+ };
+
+ mmc@79991000 {
+ compatible = "loongson,ls2k2000-mmc";
+ reg = <0x0 0x79991000 0x0 0x1000>;
+ interrupt-parent = <&pic>;
+ interrupts = <50 IRQ_TYPE_LEVEL_HIGH>;
+ clocks = <&clk LOONGSON2_EMMC_CLK>;
+ status = "disabled";
+ };
+
pcie@1a000000 {
compatible = "loongson,ls2k-pci";
reg = <0x0 0x1a000000 0x0 0x02000000>,
diff --git a/arch/loongarch/include/asm/inst.h b/arch/loongarch/include/asm/inst.h
index 3089785ca97e..277d2140676b 100644
--- a/arch/loongarch/include/asm/inst.h
+++ b/arch/loongarch/include/asm/inst.h
@@ -497,6 +497,7 @@ void arch_simulate_insn(union loongarch_instruction insn, struct pt_regs *regs);
int larch_insn_read(void *addr, u32 *insnp);
int larch_insn_write(void *addr, u32 insn);
int larch_insn_patch_text(void *addr, u32 insn);
+int larch_insn_text_copy(void *dst, void *src, size_t len);
u32 larch_insn_gen_nop(void);
u32 larch_insn_gen_b(unsigned long pc, unsigned long dest);
@@ -510,6 +511,8 @@ u32 larch_insn_gen_move(enum loongarch_gpr rd, enum loongarch_gpr rj);
u32 larch_insn_gen_lu12iw(enum loongarch_gpr rd, int imm);
u32 larch_insn_gen_lu32id(enum loongarch_gpr rd, int imm);
u32 larch_insn_gen_lu52id(enum loongarch_gpr rd, enum loongarch_gpr rj, int imm);
+u32 larch_insn_gen_beq(enum loongarch_gpr rd, enum loongarch_gpr rj, int imm);
+u32 larch_insn_gen_bne(enum loongarch_gpr rd, enum loongarch_gpr rj, int imm);
u32 larch_insn_gen_jirl(enum loongarch_gpr rd, enum loongarch_gpr rj, int imm);
static inline bool signed_imm_check(long val, unsigned int bit)
diff --git a/arch/loongarch/include/asm/loongarch.h b/arch/loongarch/include/asm/loongarch.h
index a0994d226eff..09dfd7eb406e 100644
--- a/arch/loongarch/include/asm/loongarch.h
+++ b/arch/loongarch/include/asm/loongarch.h
@@ -451,6 +451,13 @@
#define LOONGARCH_CSR_KS6 0x36
#define LOONGARCH_CSR_KS7 0x37
#define LOONGARCH_CSR_KS8 0x38
+#define LOONGARCH_CSR_KS9 0x39
+#define LOONGARCH_CSR_KS10 0x3a
+#define LOONGARCH_CSR_KS11 0x3b
+#define LOONGARCH_CSR_KS12 0x3c
+#define LOONGARCH_CSR_KS13 0x3d
+#define LOONGARCH_CSR_KS14 0x3e
+#define LOONGARCH_CSR_KS15 0x3f
/* Exception allocated KS0, KS1 and KS2 statically */
#define EXCEPTION_KS0 LOONGARCH_CSR_KS0
diff --git a/arch/loongarch/kernel/env.c b/arch/loongarch/kernel/env.c
index 27144de5c5fe..c0a5dc9aeae2 100644
--- a/arch/loongarch/kernel/env.c
+++ b/arch/loongarch/kernel/env.c
@@ -39,16 +39,19 @@ void __init init_environ(void)
static int __init init_cpu_fullname(void)
{
- struct device_node *root;
int cpu, ret;
- char *model;
+ char *cpuname;
+ const char *model;
+ struct device_node *root;
/* Parsing cpuname from DTS model property */
root = of_find_node_by_path("/");
- ret = of_property_read_string(root, "model", (const char **)&model);
+ ret = of_property_read_string(root, "model", &model);
+ if (ret == 0) {
+ cpuname = kstrdup(model, GFP_KERNEL);
+ loongson_sysconf.cpuname = strsep(&cpuname, " ");
+ }
of_node_put(root);
- if (ret == 0)
- loongson_sysconf.cpuname = strsep(&model, " ");
if (loongson_sysconf.cpuname && !strncmp(loongson_sysconf.cpuname, "Loongson", 8)) {
for (cpu = 0; cpu < NR_CPUS; cpu++)
diff --git a/arch/loongarch/kernel/inst.c b/arch/loongarch/kernel/inst.c
index 14d7d700bcb9..e61c482068fe 100644
--- a/arch/loongarch/kernel/inst.c
+++ b/arch/loongarch/kernel/inst.c
@@ -4,6 +4,7 @@
*/
#include <linux/sizes.h>
#include <linux/uaccess.h>
+#include <linux/set_memory.h>
#include <asm/cacheflush.h>
#include <asm/inst.h>
@@ -218,6 +219,32 @@ int larch_insn_patch_text(void *addr, u32 insn)
return ret;
}
+int larch_insn_text_copy(void *dst, void *src, size_t len)
+{
+ int ret;
+ unsigned long flags;
+ unsigned long dst_start, dst_end, dst_len;
+
+ dst_start = round_down((unsigned long)dst, PAGE_SIZE);
+ dst_end = round_up((unsigned long)dst + len, PAGE_SIZE);
+ dst_len = dst_end - dst_start; /* page-aligned */
+
+ set_memory_rw(dst_start, dst_len / PAGE_SIZE);
+ raw_spin_lock_irqsave(&patch_lock, flags);
+
+ ret = copy_to_kernel_nofault(dst, src, len);
+ if (ret)
+ pr_err("%s: operation failed\n", __func__);
+
+ raw_spin_unlock_irqrestore(&patch_lock, flags);
+ set_memory_rox(dst_start, dst_len / PAGE_SIZE);
+
+ if (!ret)
+ flush_icache_range((unsigned long)dst, (unsigned long)dst + len);
+
+ return ret;
+}
+
u32 larch_insn_gen_nop(void)
{
return INSN_NOP;
@@ -323,6 +350,34 @@ u32 larch_insn_gen_lu52id(enum loongarch_gpr rd, enum loongarch_gpr rj, int imm)
return insn.word;
}
+u32 larch_insn_gen_beq(enum loongarch_gpr rd, enum loongarch_gpr rj, int imm)
+{
+ union loongarch_instruction insn;
+
+ if ((imm & 3) || imm < -SZ_128K || imm >= SZ_128K) {
+ pr_warn("The generated beq instruction is out of range.\n");
+ return INSN_BREAK;
+ }
+
+ emit_beq(&insn, rj, rd, imm >> 2);
+
+ return insn.word;
+}
+
+u32 larch_insn_gen_bne(enum loongarch_gpr rd, enum loongarch_gpr rj, int imm)
+{
+ union loongarch_instruction insn;
+
+ if ((imm & 3) || imm < -SZ_128K || imm >= SZ_128K) {
+ pr_warn("The generated bne instruction is out of range.\n");
+ return INSN_BREAK;
+ }
+
+ emit_bne(&insn, rj, rd, imm >> 2);
+
+ return insn.word;
+}
+
u32 larch_insn_gen_jirl(enum loongarch_gpr rd, enum loongarch_gpr rj, int imm)
{
union loongarch_instruction insn;
diff --git a/arch/loongarch/kernel/relocate_kernel.S b/arch/loongarch/kernel/relocate_kernel.S
index 84e6de2fd973..8b5140ac9ea1 100644
--- a/arch/loongarch/kernel/relocate_kernel.S
+++ b/arch/loongarch/kernel/relocate_kernel.S
@@ -109,4 +109,4 @@ SYM_CODE_END(kexec_smp_wait)
relocate_new_kernel_end:
.section ".data"
-SYM_DATA(relocate_new_kernel_size, .long relocate_new_kernel_end - relocate_new_kernel)
+SYM_DATA(relocate_new_kernel_size, .quad relocate_new_kernel_end - relocate_new_kernel)
diff --git a/arch/loongarch/kernel/setup.c b/arch/loongarch/kernel/setup.c
index 22b27cd447a1..075b79b2c1d3 100644
--- a/arch/loongarch/kernel/setup.c
+++ b/arch/loongarch/kernel/setup.c
@@ -191,6 +191,16 @@ static int __init early_parse_mem(char *p)
return -EINVAL;
}
+ start = 0;
+ size = memparse(p, &p);
+ if (*p == '@') /* Every mem=... should contain '@' */
+ start = memparse(p + 1, &p);
+ else { /* Only one mem=... is allowed if no '@' */
+ usermem = 1;
+ memblock_enforce_memory_limit(size);
+ return 0;
+ }
+
/*
* If a user specifies memory size, we
* blow away any automatically generated
@@ -201,14 +211,6 @@ static int __init early_parse_mem(char *p)
memblock_remove(memblock_start_of_DRAM(),
memblock_end_of_DRAM() - memblock_start_of_DRAM());
}
- start = 0;
- size = memparse(p, &p);
- if (*p == '@')
- start = memparse(p + 1, &p);
- else {
- pr_err("Invalid format!\n");
- return -EINVAL;
- }
if (!IS_ENABLED(CONFIG_NUMA))
memblock_add(start, size);
diff --git a/arch/loongarch/kernel/unwind_orc.c b/arch/loongarch/kernel/unwind_orc.c
index 0005be49b056..0d5fa64a2225 100644
--- a/arch/loongarch/kernel/unwind_orc.c
+++ b/arch/loongarch/kernel/unwind_orc.c
@@ -508,7 +508,7 @@ bool unwind_next_frame(struct unwind_state *state)
state->pc = bt_address(pc);
if (!state->pc) {
- pr_err("cannot find unwind pc at %pK\n", (void *)pc);
+ pr_err("cannot find unwind pc at %p\n", (void *)pc);
goto err;
}
diff --git a/arch/loongarch/net/bpf_jit.c b/arch/loongarch/net/bpf_jit.c
index fa1500d4aa3e..1ecc2c59459c 100644
--- a/arch/loongarch/net/bpf_jit.c
+++ b/arch/loongarch/net/bpf_jit.c
@@ -4,13 +4,20 @@
*
* Copyright (C) 2022 Loongson Technology Corporation Limited
*/
+#include <linux/memory.h>
#include "bpf_jit.h"
-#define REG_TCC LOONGARCH_GPR_A6
-#define TCC_SAVED LOONGARCH_GPR_S5
+#define LOONGARCH_MAX_REG_ARGS 8
+
+#define LOONGARCH_LONG_JUMP_NINSNS 5
+#define LOONGARCH_LONG_JUMP_NBYTES (LOONGARCH_LONG_JUMP_NINSNS * 4)
-#define SAVE_RA BIT(0)
-#define SAVE_TCC BIT(1)
+#define LOONGARCH_FENTRY_NINSNS 2
+#define LOONGARCH_FENTRY_NBYTES (LOONGARCH_FENTRY_NINSNS * 4)
+#define LOONGARCH_BPF_FENTRY_NBYTES (LOONGARCH_LONG_JUMP_NINSNS * 4)
+
+#define REG_TCC LOONGARCH_GPR_A6
+#define BPF_TAIL_CALL_CNT_PTR_STACK_OFF(stack) (round_up(stack, 16) - 80)
static const int regmap[] = {
/* return value from in-kernel function, and exit value for eBPF program */
@@ -32,32 +39,57 @@ static const int regmap[] = {
[BPF_REG_AX] = LOONGARCH_GPR_T0,
};
-static void mark_call(struct jit_ctx *ctx)
+static void prepare_bpf_tail_call_cnt(struct jit_ctx *ctx, int *store_offset)
{
- ctx->flags |= SAVE_RA;
-}
+ const struct bpf_prog *prog = ctx->prog;
+ const bool is_main_prog = !bpf_is_subprog(prog);
-static void mark_tail_call(struct jit_ctx *ctx)
-{
- ctx->flags |= SAVE_TCC;
-}
+ if (is_main_prog) {
+ /*
+ * LOONGARCH_GPR_T3 = MAX_TAIL_CALL_CNT
+ * if (REG_TCC > T3 )
+ * std REG_TCC -> LOONGARCH_GPR_SP + store_offset
+ * else
+ * std REG_TCC -> LOONGARCH_GPR_SP + store_offset
+ * REG_TCC = LOONGARCH_GPR_SP + store_offset
+ *
+ * std REG_TCC -> LOONGARCH_GPR_SP + store_offset
+ *
+ * The purpose of this code is to first push the TCC into stack,
+ * and then push the address of TCC into stack.
+ * In cases where bpf2bpf and tailcall are used in combination,
+ * the value in REG_TCC may be a count or an address,
+ * these two cases need to be judged and handled separately.
+ */
+ emit_insn(ctx, addid, LOONGARCH_GPR_T3, LOONGARCH_GPR_ZERO, MAX_TAIL_CALL_CNT);
+ *store_offset -= sizeof(long);
-static bool seen_call(struct jit_ctx *ctx)
-{
- return (ctx->flags & SAVE_RA);
-}
+ emit_cond_jmp(ctx, BPF_JGT, REG_TCC, LOONGARCH_GPR_T3, 4);
-static bool seen_tail_call(struct jit_ctx *ctx)
-{
- return (ctx->flags & SAVE_TCC);
-}
+ /*
+ * If REG_TCC < MAX_TAIL_CALL_CNT, the value in REG_TCC is a count,
+ * push tcc into stack
+ */
+ emit_insn(ctx, std, REG_TCC, LOONGARCH_GPR_SP, *store_offset);
-static u8 tail_call_reg(struct jit_ctx *ctx)
-{
- if (seen_call(ctx))
- return TCC_SAVED;
+ /* Push the address of TCC into the REG_TCC */
+ emit_insn(ctx, addid, REG_TCC, LOONGARCH_GPR_SP, *store_offset);
+
+ emit_uncond_jmp(ctx, 2);
+
+ /*
+ * If REG_TCC > MAX_TAIL_CALL_CNT, the value in REG_TCC is an address,
+ * push tcc_ptr into stack
+ */
+ emit_insn(ctx, std, REG_TCC, LOONGARCH_GPR_SP, *store_offset);
+ } else {
+ *store_offset -= sizeof(long);
+ emit_insn(ctx, std, REG_TCC, LOONGARCH_GPR_SP, *store_offset);
+ }
- return REG_TCC;
+ /* Push tcc_ptr into stack */
+ *store_offset -= sizeof(long);
+ emit_insn(ctx, std, REG_TCC, LOONGARCH_GPR_SP, *store_offset);
}
/*
@@ -80,6 +112,10 @@ static u8 tail_call_reg(struct jit_ctx *ctx)
* | $s4 |
* +-------------------------+
* | $s5 |
+ * +-------------------------+
+ * | tcc |
+ * +-------------------------+
+ * | tcc_ptr |
* +-------------------------+ <--BPF_REG_FP
* | prog->aux->stack_depth |
* | (optional) |
@@ -88,22 +124,32 @@ static u8 tail_call_reg(struct jit_ctx *ctx)
*/
static void build_prologue(struct jit_ctx *ctx)
{
- int stack_adjust = 0, store_offset, bpf_stack_adjust;
+ int i, stack_adjust = 0, store_offset, bpf_stack_adjust;
+ const struct bpf_prog *prog = ctx->prog;
+ const bool is_main_prog = !bpf_is_subprog(prog);
bpf_stack_adjust = round_up(ctx->prog->aux->stack_depth, 16);
- /* To store ra, fp, s0, s1, s2, s3, s4 and s5. */
+ /* To store ra, fp, s0, s1, s2, s3, s4, s5 */
stack_adjust += sizeof(long) * 8;
+ /* To store tcc and tcc_ptr */
+ stack_adjust += sizeof(long) * 2;
+
stack_adjust = round_up(stack_adjust, 16);
stack_adjust += bpf_stack_adjust;
+ /* Reserve space for the move_imm + jirl instruction */
+ for (i = 0; i < LOONGARCH_LONG_JUMP_NINSNS; i++)
+ emit_insn(ctx, nop);
+
/*
- * First instruction initializes the tail call count (TCC).
- * On tail call we skip this instruction, and the TCC is
- * passed in REG_TCC from the caller.
+ * First instruction initializes the tail call count (TCC)
+ * register to zero. On tail call we skip this instruction,
+ * and the TCC is passed in REG_TCC from the caller.
*/
- emit_insn(ctx, addid, REG_TCC, LOONGARCH_GPR_ZERO, MAX_TAIL_CALL_CNT);
+ if (is_main_prog)
+ emit_insn(ctx, addid, REG_TCC, LOONGARCH_GPR_ZERO, 0);
emit_insn(ctx, addid, LOONGARCH_GPR_SP, LOONGARCH_GPR_SP, -stack_adjust);
@@ -131,20 +177,13 @@ static void build_prologue(struct jit_ctx *ctx)
store_offset -= sizeof(long);
emit_insn(ctx, std, LOONGARCH_GPR_S5, LOONGARCH_GPR_SP, store_offset);
+ prepare_bpf_tail_call_cnt(ctx, &store_offset);
+
emit_insn(ctx, addid, LOONGARCH_GPR_FP, LOONGARCH_GPR_SP, stack_adjust);
if (bpf_stack_adjust)
emit_insn(ctx, addid, regmap[BPF_REG_FP], LOONGARCH_GPR_SP, bpf_stack_adjust);
- /*
- * Program contains calls and tail calls, so REG_TCC need
- * to be saved across calls.
- */
- if (seen_tail_call(ctx) && seen_call(ctx))
- move_reg(ctx, TCC_SAVED, REG_TCC);
- else
- emit_insn(ctx, nop);
-
ctx->stack_size = stack_adjust;
}
@@ -177,6 +216,16 @@ static void __build_epilogue(struct jit_ctx *ctx, bool is_tail_call)
load_offset -= sizeof(long);
emit_insn(ctx, ldd, LOONGARCH_GPR_S5, LOONGARCH_GPR_SP, load_offset);
+ /*
+ * When push into the stack, follow the order of tcc then tcc_ptr.
+ * When pop from the stack, first pop tcc_ptr then followed by tcc.
+ */
+ load_offset -= 2 * sizeof(long);
+ emit_insn(ctx, ldd, REG_TCC, LOONGARCH_GPR_SP, load_offset);
+
+ load_offset += sizeof(long);
+ emit_insn(ctx, ldd, REG_TCC, LOONGARCH_GPR_SP, load_offset);
+
emit_insn(ctx, addid, LOONGARCH_GPR_SP, LOONGARCH_GPR_SP, stack_adjust);
if (!is_tail_call) {
@@ -189,7 +238,7 @@ static void __build_epilogue(struct jit_ctx *ctx, bool is_tail_call)
* Call the next bpf prog and skip the first instruction
* of TCC initialization.
*/
- emit_insn(ctx, jirl, LOONGARCH_GPR_ZERO, LOONGARCH_GPR_T3, 1);
+ emit_insn(ctx, jirl, LOONGARCH_GPR_ZERO, LOONGARCH_GPR_T3, 6);
}
}
@@ -208,12 +257,10 @@ bool bpf_jit_supports_far_kfunc_call(void)
return true;
}
-/* initialized on the first pass of build_body() */
-static int out_offset = -1;
-static int emit_bpf_tail_call(struct jit_ctx *ctx)
+static int emit_bpf_tail_call(struct jit_ctx *ctx, int insn)
{
- int off;
- u8 tcc = tail_call_reg(ctx);
+ int off, tc_ninsn = 0;
+ int tcc_ptr_off = BPF_TAIL_CALL_CNT_PTR_STACK_OFF(ctx->stack_size);
u8 a1 = LOONGARCH_GPR_A1;
u8 a2 = LOONGARCH_GPR_A2;
u8 t1 = LOONGARCH_GPR_T1;
@@ -222,7 +269,7 @@ static int emit_bpf_tail_call(struct jit_ctx *ctx)
const int idx0 = ctx->idx;
#define cur_offset (ctx->idx - idx0)
-#define jmp_offset (out_offset - (cur_offset))
+#define jmp_offset (tc_ninsn - (cur_offset))
/*
* a0: &ctx
@@ -232,6 +279,7 @@ static int emit_bpf_tail_call(struct jit_ctx *ctx)
* if (index >= array->map.max_entries)
* goto out;
*/
+ tc_ninsn = insn ? ctx->offset[insn+1] - ctx->offset[insn] : ctx->offset[0];
off = offsetof(struct bpf_array, map.max_entries);
emit_insn(ctx, ldwu, t1, a1, off);
/* bgeu $a2, $t1, jmp_offset */
@@ -239,11 +287,15 @@ static int emit_bpf_tail_call(struct jit_ctx *ctx)
goto toofar;
/*
- * if (--TCC < 0)
- * goto out;
+ * if ((*tcc_ptr)++ >= MAX_TAIL_CALL_CNT)
+ * goto out;
*/
- emit_insn(ctx, addid, REG_TCC, tcc, -1);
- if (emit_tailcall_jmp(ctx, BPF_JSLT, REG_TCC, LOONGARCH_GPR_ZERO, jmp_offset) < 0)
+ emit_insn(ctx, ldd, REG_TCC, LOONGARCH_GPR_SP, tcc_ptr_off);
+ emit_insn(ctx, ldd, t3, REG_TCC, 0);
+ emit_insn(ctx, addid, t3, t3, 1);
+ emit_insn(ctx, std, t3, REG_TCC, 0);
+ emit_insn(ctx, addid, t2, LOONGARCH_GPR_ZERO, MAX_TAIL_CALL_CNT);
+ if (emit_tailcall_jmp(ctx, BPF_JSGT, t3, t2, jmp_offset) < 0)
goto toofar;
/*
@@ -263,15 +315,6 @@ static int emit_bpf_tail_call(struct jit_ctx *ctx)
emit_insn(ctx, ldd, t3, t2, off);
__build_epilogue(ctx, true);
- /* out: */
- if (out_offset == -1)
- out_offset = cur_offset;
- if (cur_offset != out_offset) {
- pr_err_once("tail_call out_offset = %d, expected %d!\n",
- cur_offset, out_offset);
- return -1;
- }
-
return 0;
toofar:
@@ -463,7 +506,7 @@ static int build_insn(const struct bpf_insn *insn, struct jit_ctx *ctx, bool ext
u64 func_addr;
bool func_addr_fixed, sign_extend;
int i = insn - ctx->prog->insnsi;
- int ret, jmp_offset;
+ int ret, jmp_offset, tcc_ptr_off;
const u8 code = insn->code;
const u8 cond = BPF_OP(code);
const u8 t1 = LOONGARCH_GPR_T1;
@@ -899,12 +942,16 @@ static int build_insn(const struct bpf_insn *insn, struct jit_ctx *ctx, bool ext
/* function call */
case BPF_JMP | BPF_CALL:
- mark_call(ctx);
ret = bpf_jit_get_func_addr(ctx->prog, insn, extra_pass,
&func_addr, &func_addr_fixed);
if (ret < 0)
return ret;
+ if (insn->src_reg == BPF_PSEUDO_CALL) {
+ tcc_ptr_off = BPF_TAIL_CALL_CNT_PTR_STACK_OFF(ctx->stack_size);
+ emit_insn(ctx, ldd, REG_TCC, LOONGARCH_GPR_SP, tcc_ptr_off);
+ }
+
move_addr(ctx, t1, func_addr);
emit_insn(ctx, jirl, LOONGARCH_GPR_RA, t1, 0);
@@ -915,8 +962,7 @@ static int build_insn(const struct bpf_insn *insn, struct jit_ctx *ctx, bool ext
/* tail call */
case BPF_JMP | BPF_TAIL_CALL:
- mark_tail_call(ctx);
- if (emit_bpf_tail_call(ctx) < 0)
+ if (emit_bpf_tail_call(ctx, i) < 0)
return -EINVAL;
break;
@@ -1180,12 +1226,526 @@ static int validate_code(struct jit_ctx *ctx)
return -1;
}
+ return 0;
+}
+
+static int validate_ctx(struct jit_ctx *ctx)
+{
+ if (validate_code(ctx))
+ return -1;
+
if (WARN_ON_ONCE(ctx->num_exentries != ctx->prog->aux->num_exentries))
return -1;
return 0;
}
+static int emit_jump_and_link(struct jit_ctx *ctx, u8 rd, u64 target)
+{
+ if (!target) {
+ pr_err("bpf_jit: jump target address is error\n");
+ return -EFAULT;
+ }
+
+ move_imm(ctx, LOONGARCH_GPR_T1, target, false);
+ emit_insn(ctx, jirl, rd, LOONGARCH_GPR_T1, 0);
+
+ return 0;
+}
+
+static int emit_jump_or_nops(void *target, void *ip, u32 *insns, bool is_call)
+{
+ struct jit_ctx ctx;
+
+ ctx.idx = 0;
+ ctx.image = (union loongarch_instruction *)insns;
+
+ if (!target) {
+ emit_insn((&ctx), nop);
+ emit_insn((&ctx), nop);
+ return 0;
+ }
+
+ return emit_jump_and_link(&ctx, is_call ? LOONGARCH_GPR_T0 : LOONGARCH_GPR_ZERO, (u64)target);
+}
+
+static int emit_call(struct jit_ctx *ctx, u64 addr)
+{
+ return emit_jump_and_link(ctx, LOONGARCH_GPR_RA, addr);
+}
+
+void *bpf_arch_text_copy(void *dst, void *src, size_t len)
+{
+ int ret;
+
+ mutex_lock(&text_mutex);
+ ret = larch_insn_text_copy(dst, src, len);
+ mutex_unlock(&text_mutex);
+
+ return ret ? ERR_PTR(-EINVAL) : dst;
+}
+
+int bpf_arch_text_poke(void *ip, enum bpf_text_poke_type poke_type,
+ void *old_addr, void *new_addr)
+{
+ int ret;
+ bool is_call = (poke_type == BPF_MOD_CALL);
+ u32 old_insns[LOONGARCH_LONG_JUMP_NINSNS] = {[0 ... 4] = INSN_NOP};
+ u32 new_insns[LOONGARCH_LONG_JUMP_NINSNS] = {[0 ... 4] = INSN_NOP};
+
+ if (!is_kernel_text((unsigned long)ip) &&
+ !is_bpf_text_address((unsigned long)ip))
+ return -ENOTSUPP;
+
+ ret = emit_jump_or_nops(old_addr, ip, old_insns, is_call);
+ if (ret)
+ return ret;
+
+ if (memcmp(ip, old_insns, LOONGARCH_LONG_JUMP_NBYTES))
+ return -EFAULT;
+
+ ret = emit_jump_or_nops(new_addr, ip, new_insns, is_call);
+ if (ret)
+ return ret;
+
+ mutex_lock(&text_mutex);
+ if (memcmp(ip, new_insns, LOONGARCH_LONG_JUMP_NBYTES))
+ ret = larch_insn_text_copy(ip, new_insns, LOONGARCH_LONG_JUMP_NBYTES);
+ mutex_unlock(&text_mutex);
+
+ return ret;
+}
+
+int bpf_arch_text_invalidate(void *dst, size_t len)
+{
+ int i;
+ int ret = 0;
+ u32 *inst;
+
+ inst = kvmalloc(len, GFP_KERNEL);
+ if (!inst)
+ return -ENOMEM;
+
+ for (i = 0; i < (len / sizeof(u32)); i++)
+ inst[i] = INSN_BREAK;
+
+ mutex_lock(&text_mutex);
+ if (larch_insn_text_copy(dst, inst, len))
+ ret = -EINVAL;
+ mutex_unlock(&text_mutex);
+
+ kvfree(inst);
+
+ return ret;
+}
+
+static void store_args(struct jit_ctx *ctx, int nargs, int args_off)
+{
+ int i;
+
+ for (i = 0; i < nargs; i++) {
+ emit_insn(ctx, std, LOONGARCH_GPR_A0 + i, LOONGARCH_GPR_FP, -args_off);
+ args_off -= 8;
+ }
+}
+
+static void restore_args(struct jit_ctx *ctx, int nargs, int args_off)
+{
+ int i;
+
+ for (i = 0; i < nargs; i++) {
+ emit_insn(ctx, ldd, LOONGARCH_GPR_A0 + i, LOONGARCH_GPR_FP, -args_off);
+ args_off -= 8;
+ }
+}
+
+static int invoke_bpf_prog(struct jit_ctx *ctx, struct bpf_tramp_link *l,
+ int args_off, int retval_off, int run_ctx_off, bool save_ret)
+{
+ int ret;
+ u32 *branch;
+ struct bpf_prog *p = l->link.prog;
+ int cookie_off = offsetof(struct bpf_tramp_run_ctx, bpf_cookie);
+
+ if (l->cookie) {
+ move_imm(ctx, LOONGARCH_GPR_T1, l->cookie, false);
+ emit_insn(ctx, std, LOONGARCH_GPR_T1, LOONGARCH_GPR_FP, -run_ctx_off + cookie_off);
+ } else {
+ emit_insn(ctx, std, LOONGARCH_GPR_ZERO, LOONGARCH_GPR_FP, -run_ctx_off + cookie_off);
+ }
+
+ /* arg1: prog */
+ move_imm(ctx, LOONGARCH_GPR_A0, (const s64)p, false);
+ /* arg2: &run_ctx */
+ emit_insn(ctx, addid, LOONGARCH_GPR_A1, LOONGARCH_GPR_FP, -run_ctx_off);
+ ret = emit_call(ctx, (const u64)bpf_trampoline_enter(p));
+ if (ret)
+ return ret;
+
+ /* store prog start time */
+ move_reg(ctx, LOONGARCH_GPR_S1, LOONGARCH_GPR_A0);
+
+ /* if (__bpf_prog_enter(prog) == 0)
+ * goto skip_exec_of_prog;
+ */
+ branch = (u32 *)ctx->image + ctx->idx;
+ /* nop reserved for conditional jump */
+ emit_insn(ctx, nop);
+
+ /* arg1: &args_off */
+ emit_insn(ctx, addid, LOONGARCH_GPR_A0, LOONGARCH_GPR_FP, -args_off);
+ if (!p->jited)
+ move_imm(ctx, LOONGARCH_GPR_A1, (const s64)p->insnsi, false);
+ ret = emit_call(ctx, (const u64)p->bpf_func);
+ if (ret)
+ return ret;
+
+ if (save_ret) {
+ emit_insn(ctx, std, LOONGARCH_GPR_A0, LOONGARCH_GPR_FP, -retval_off);
+ emit_insn(ctx, std, regmap[BPF_REG_0], LOONGARCH_GPR_FP, -(retval_off - 8));
+ }
+
+ /* update branch with beqz */
+ if (ctx->image) {
+ int offset = (void *)(&ctx->image[ctx->idx]) - (void *)branch;
+ *branch = larch_insn_gen_beq(LOONGARCH_GPR_A0, LOONGARCH_GPR_ZERO, offset);
+ }
+
+ /* arg1: prog */
+ move_imm(ctx, LOONGARCH_GPR_A0, (const s64)p, false);
+ /* arg2: prog start time */
+ move_reg(ctx, LOONGARCH_GPR_A1, LOONGARCH_GPR_S1);
+ /* arg3: &run_ctx */
+ emit_insn(ctx, addid, LOONGARCH_GPR_A2, LOONGARCH_GPR_FP, -run_ctx_off);
+ ret = emit_call(ctx, (const u64)bpf_trampoline_exit(p));
+
+ return ret;
+}
+
+static void invoke_bpf_mod_ret(struct jit_ctx *ctx, struct bpf_tramp_links *tl,
+ int args_off, int retval_off, int run_ctx_off, u32 **branches)
+{
+ int i;
+
+ emit_insn(ctx, std, LOONGARCH_GPR_ZERO, LOONGARCH_GPR_FP, -retval_off);
+ for (i = 0; i < tl->nr_links; i++) {
+ invoke_bpf_prog(ctx, tl->links[i], args_off, retval_off, run_ctx_off, true);
+ emit_insn(ctx, ldd, LOONGARCH_GPR_T1, LOONGARCH_GPR_FP, -retval_off);
+ branches[i] = (u32 *)ctx->image + ctx->idx;
+ emit_insn(ctx, nop);
+ }
+}
+
+void *arch_alloc_bpf_trampoline(unsigned int size)
+{
+ return bpf_prog_pack_alloc(size, jit_fill_hole);
+}
+
+void arch_free_bpf_trampoline(void *image, unsigned int size)
+{
+ bpf_prog_pack_free(image, size);
+}
+
+static int __arch_prepare_bpf_trampoline(struct jit_ctx *ctx, struct bpf_tramp_image *im,
+ const struct btf_func_model *m, struct bpf_tramp_links *tlinks,
+ void *func_addr, u32 flags)
+{
+ int i, ret, save_ret;
+ int stack_size = 0, nargs = 0;
+ int retval_off, args_off, nargs_off, ip_off, run_ctx_off, sreg_off, tcc_ptr_off;
+ bool is_struct_ops = flags & BPF_TRAMP_F_INDIRECT;
+ void *orig_call = func_addr;
+ struct bpf_tramp_links *fentry = &tlinks[BPF_TRAMP_FENTRY];
+ struct bpf_tramp_links *fexit = &tlinks[BPF_TRAMP_FEXIT];
+ struct bpf_tramp_links *fmod_ret = &tlinks[BPF_TRAMP_MODIFY_RETURN];
+ u32 **branches = NULL;
+
+ if (flags & (BPF_TRAMP_F_ORIG_STACK | BPF_TRAMP_F_SHARE_IPMODIFY))
+ return -ENOTSUPP;
+
+ /*
+ * FP + 8 [ RA to parent func ] return address to parent
+ * function
+ * FP + 0 [ FP of parent func ] frame pointer of parent
+ * function
+ * FP - 8 [ T0 to traced func ] return address of traced
+ * function
+ * FP - 16 [ FP of traced func ] frame pointer of traced
+ * function
+ *
+ * FP - retval_off [ return value ] BPF_TRAMP_F_CALL_ORIG or
+ * BPF_TRAMP_F_RET_FENTRY_RET
+ * [ argN ]
+ * [ ... ]
+ * FP - args_off [ arg1 ]
+ *
+ * FP - nargs_off [ regs count ]
+ *
+ * FP - ip_off [ traced func ] BPF_TRAMP_F_IP_ARG
+ *
+ * FP - run_ctx_off [ bpf_tramp_run_ctx ]
+ *
+ * FP - sreg_off [ callee saved reg ]
+ *
+ * FP - tcc_ptr_off [ tail_call_cnt_ptr ]
+ */
+
+ if (m->nr_args > LOONGARCH_MAX_REG_ARGS)
+ return -ENOTSUPP;
+
+ if (flags & (BPF_TRAMP_F_ORIG_STACK | BPF_TRAMP_F_SHARE_IPMODIFY))
+ return -ENOTSUPP;
+
+ stack_size = 0;
+
+ /* Room of trampoline frame to store return address and frame pointer */
+ stack_size += 16;
+
+ save_ret = flags & (BPF_TRAMP_F_CALL_ORIG | BPF_TRAMP_F_RET_FENTRY_RET);
+ if (save_ret) {
+ /* Save BPF R0 and A0 */
+ stack_size += 16;
+ retval_off = stack_size;
+ }
+
+ /* Room of trampoline frame to store args */
+ nargs = m->nr_args;
+ stack_size += nargs * 8;
+ args_off = stack_size;
+
+ /* Room of trampoline frame to store args number */
+ stack_size += 8;
+ nargs_off = stack_size;
+
+ /* Room of trampoline frame to store ip address */
+ if (flags & BPF_TRAMP_F_IP_ARG) {
+ stack_size += 8;
+ ip_off = stack_size;
+ }
+
+ /* Room of trampoline frame to store struct bpf_tramp_run_ctx */
+ stack_size += round_up(sizeof(struct bpf_tramp_run_ctx), 8);
+ run_ctx_off = stack_size;
+
+ stack_size += 8;
+ sreg_off = stack_size;
+
+ /* Room of trampoline frame to store tail_call_cnt_ptr */
+ if (flags & BPF_TRAMP_F_TAIL_CALL_CTX) {
+ stack_size += 8;
+ tcc_ptr_off = stack_size;
+ }
+
+ stack_size = round_up(stack_size, 16);
+
+ if (is_struct_ops) {
+ /*
+ * For the trampoline called directly, just handle
+ * the frame of trampoline.
+ */
+ emit_insn(ctx, addid, LOONGARCH_GPR_SP, LOONGARCH_GPR_SP, -stack_size);
+ emit_insn(ctx, std, LOONGARCH_GPR_RA, LOONGARCH_GPR_SP, stack_size - 8);
+ emit_insn(ctx, std, LOONGARCH_GPR_FP, LOONGARCH_GPR_SP, stack_size - 16);
+ emit_insn(ctx, addid, LOONGARCH_GPR_FP, LOONGARCH_GPR_SP, stack_size);
+ } else {
+ /*
+ * For the trampoline called from function entry,
+ * the frame of traced function and the frame of
+ * trampoline need to be considered.
+ */
+ /* RA and FP for parent function */
+ emit_insn(ctx, addid, LOONGARCH_GPR_SP, LOONGARCH_GPR_SP, -16);
+ emit_insn(ctx, std, LOONGARCH_GPR_RA, LOONGARCH_GPR_SP, 8);
+ emit_insn(ctx, std, LOONGARCH_GPR_FP, LOONGARCH_GPR_SP, 0);
+ emit_insn(ctx, addid, LOONGARCH_GPR_FP, LOONGARCH_GPR_SP, 16);
+
+ /* RA and FP for traced function */
+ emit_insn(ctx, addid, LOONGARCH_GPR_SP, LOONGARCH_GPR_SP, -stack_size);
+ emit_insn(ctx, std, LOONGARCH_GPR_T0, LOONGARCH_GPR_SP, stack_size - 8);
+ emit_insn(ctx, std, LOONGARCH_GPR_FP, LOONGARCH_GPR_SP, stack_size - 16);
+ emit_insn(ctx, addid, LOONGARCH_GPR_FP, LOONGARCH_GPR_SP, stack_size);
+ }
+
+ if (flags & BPF_TRAMP_F_TAIL_CALL_CTX)
+ emit_insn(ctx, std, REG_TCC, LOONGARCH_GPR_FP, -tcc_ptr_off);
+
+ /* callee saved register S1 to pass start time */
+ emit_insn(ctx, std, LOONGARCH_GPR_S1, LOONGARCH_GPR_FP, -sreg_off);
+
+ /* store ip address of the traced function */
+ if (flags & BPF_TRAMP_F_IP_ARG) {
+ move_imm(ctx, LOONGARCH_GPR_T1, (const s64)func_addr, false);
+ emit_insn(ctx, std, LOONGARCH_GPR_T1, LOONGARCH_GPR_FP, -ip_off);
+ }
+
+ /* store nargs number */
+ move_imm(ctx, LOONGARCH_GPR_T1, nargs, false);
+ emit_insn(ctx, std, LOONGARCH_GPR_T1, LOONGARCH_GPR_FP, -nargs_off);
+
+ store_args(ctx, nargs, args_off);
+
+ /* To traced function */
+ /* Ftrace jump skips 2 NOP instructions */
+ if (is_kernel_text((unsigned long)orig_call))
+ orig_call += LOONGARCH_FENTRY_NBYTES;
+ /* Direct jump skips 5 NOP instructions */
+ else if (is_bpf_text_address((unsigned long)orig_call))
+ orig_call += LOONGARCH_BPF_FENTRY_NBYTES;
+
+ if (flags & BPF_TRAMP_F_CALL_ORIG) {
+ move_imm(ctx, LOONGARCH_GPR_A0, (const s64)im, false);
+ ret = emit_call(ctx, (const u64)__bpf_tramp_enter);
+ if (ret)
+ return ret;
+ }
+
+ for (i = 0; i < fentry->nr_links; i++) {
+ ret = invoke_bpf_prog(ctx, fentry->links[i], args_off, retval_off,
+ run_ctx_off, flags & BPF_TRAMP_F_RET_FENTRY_RET);
+ if (ret)
+ return ret;
+ }
+ if (fmod_ret->nr_links) {
+ branches = kcalloc(fmod_ret->nr_links, sizeof(u32 *), GFP_KERNEL);
+ if (!branches)
+ return -ENOMEM;
+
+ invoke_bpf_mod_ret(ctx, fmod_ret, args_off, retval_off, run_ctx_off, branches);
+ }
+
+ if (flags & BPF_TRAMP_F_CALL_ORIG) {
+ restore_args(ctx, m->nr_args, args_off);
+
+ if (flags & BPF_TRAMP_F_TAIL_CALL_CTX)
+ emit_insn(ctx, ldd, REG_TCC, LOONGARCH_GPR_FP, -tcc_ptr_off);
+
+ ret = emit_call(ctx, (const u64)orig_call);
+ if (ret)
+ goto out;
+ emit_insn(ctx, std, LOONGARCH_GPR_A0, LOONGARCH_GPR_FP, -retval_off);
+ emit_insn(ctx, std, regmap[BPF_REG_0], LOONGARCH_GPR_FP, -(retval_off - 8));
+ im->ip_after_call = ctx->ro_image + ctx->idx;
+ /* Reserve space for the move_imm + jirl instruction */
+ for (i = 0; i < LOONGARCH_LONG_JUMP_NINSNS; i++)
+ emit_insn(ctx, nop);
+ }
+
+ for (i = 0; ctx->image && i < fmod_ret->nr_links; i++) {
+ int offset = (void *)(&ctx->image[ctx->idx]) - (void *)branches[i];
+ *branches[i] = larch_insn_gen_bne(LOONGARCH_GPR_T1, LOONGARCH_GPR_ZERO, offset);
+ }
+
+ for (i = 0; i < fexit->nr_links; i++) {
+ ret = invoke_bpf_prog(ctx, fexit->links[i], args_off, retval_off, run_ctx_off, false);
+ if (ret)
+ goto out;
+ }
+
+ if (flags & BPF_TRAMP_F_CALL_ORIG) {
+ im->ip_epilogue = ctx->ro_image + ctx->idx;
+ move_imm(ctx, LOONGARCH_GPR_A0, (const s64)im, false);
+ ret = emit_call(ctx, (const u64)__bpf_tramp_exit);
+ if (ret)
+ goto out;
+ }
+
+ if (flags & BPF_TRAMP_F_RESTORE_REGS)
+ restore_args(ctx, m->nr_args, args_off);
+
+ if (save_ret) {
+ emit_insn(ctx, ldd, LOONGARCH_GPR_A0, LOONGARCH_GPR_FP, -retval_off);
+ emit_insn(ctx, ldd, regmap[BPF_REG_0], LOONGARCH_GPR_FP, -(retval_off - 8));
+ }
+
+ emit_insn(ctx, ldd, LOONGARCH_GPR_S1, LOONGARCH_GPR_FP, -sreg_off);
+
+ if (flags & BPF_TRAMP_F_TAIL_CALL_CTX)
+ emit_insn(ctx, ldd, REG_TCC, LOONGARCH_GPR_FP, -tcc_ptr_off);
+
+ if (is_struct_ops) {
+ /* trampoline called directly */
+ emit_insn(ctx, ldd, LOONGARCH_GPR_RA, LOONGARCH_GPR_SP, stack_size - 8);
+ emit_insn(ctx, ldd, LOONGARCH_GPR_FP, LOONGARCH_GPR_SP, stack_size - 16);
+ emit_insn(ctx, addid, LOONGARCH_GPR_SP, LOONGARCH_GPR_SP, stack_size);
+
+ emit_insn(ctx, jirl, LOONGARCH_GPR_ZERO, LOONGARCH_GPR_RA, 0);
+ } else {
+ /* trampoline called from function entry */
+ emit_insn(ctx, ldd, LOONGARCH_GPR_T0, LOONGARCH_GPR_SP, stack_size - 8);
+ emit_insn(ctx, ldd, LOONGARCH_GPR_FP, LOONGARCH_GPR_SP, stack_size - 16);
+ emit_insn(ctx, addid, LOONGARCH_GPR_SP, LOONGARCH_GPR_SP, stack_size);
+
+ emit_insn(ctx, ldd, LOONGARCH_GPR_RA, LOONGARCH_GPR_SP, 8);
+ emit_insn(ctx, ldd, LOONGARCH_GPR_FP, LOONGARCH_GPR_SP, 0);
+ emit_insn(ctx, addid, LOONGARCH_GPR_SP, LOONGARCH_GPR_SP, 16);
+
+ if (flags & BPF_TRAMP_F_SKIP_FRAME)
+ /* return to parent function */
+ emit_insn(ctx, jirl, LOONGARCH_GPR_ZERO, LOONGARCH_GPR_RA, 0);
+ else
+ /* return to traced function */
+ emit_insn(ctx, jirl, LOONGARCH_GPR_ZERO, LOONGARCH_GPR_T0, 0);
+ }
+
+ ret = ctx->idx;
+out:
+ kfree(branches);
+
+ return ret;
+}
+
+int arch_prepare_bpf_trampoline(struct bpf_tramp_image *im, void *ro_image,
+ void *ro_image_end, const struct btf_func_model *m,
+ u32 flags, struct bpf_tramp_links *tlinks, void *func_addr)
+{
+ int ret, size;
+ void *image, *tmp;
+ struct jit_ctx ctx;
+
+ size = ro_image_end - ro_image;
+ image = kvmalloc(size, GFP_KERNEL);
+ if (!image)
+ return -ENOMEM;
+
+ ctx.image = (union loongarch_instruction *)image;
+ ctx.ro_image = (union loongarch_instruction *)ro_image;
+ ctx.idx = 0;
+
+ jit_fill_hole(image, (unsigned int)(ro_image_end - ro_image));
+ ret = __arch_prepare_bpf_trampoline(&ctx, im, m, tlinks, func_addr, flags);
+ if (ret > 0 && validate_code(&ctx) < 0) {
+ ret = -EINVAL;
+ goto out;
+ }
+
+ tmp = bpf_arch_text_copy(ro_image, image, size);
+ if (IS_ERR(tmp)) {
+ ret = PTR_ERR(tmp);
+ goto out;
+ }
+
+ bpf_flush_icache(ro_image, ro_image_end);
+out:
+ kvfree(image);
+ return ret < 0 ? ret : size;
+}
+
+int arch_bpf_trampoline_size(const struct btf_func_model *m, u32 flags,
+ struct bpf_tramp_links *tlinks, void *func_addr)
+{
+ int ret;
+ struct jit_ctx ctx;
+ struct bpf_tramp_image im;
+
+ ctx.image = NULL;
+ ctx.idx = 0;
+
+ ret = __arch_prepare_bpf_trampoline(&ctx, &im, m, tlinks, func_addr, flags);
+
+ /* Page align */
+ return ret < 0 ? ret : round_up(ret * LOONGARCH_INSN_SIZE, PAGE_SIZE);
+}
+
struct bpf_prog *bpf_int_jit_compile(struct bpf_prog *prog)
{
bool tmp_blinded = false, extra_pass = false;
@@ -1288,7 +1848,7 @@ skip_init_ctx:
build_epilogue(&ctx);
/* 3. Extra pass to validate JITed code */
- if (validate_code(&ctx)) {
+ if (validate_ctx(&ctx)) {
bpf_jit_binary_free(header);
prog = orig_prog;
goto out_offset;
@@ -1342,7 +1902,6 @@ out:
if (tmp_blinded)
bpf_jit_prog_release_other(prog, prog == orig_prog ? tmp : orig_prog);
- out_offset = -1;
return prog;
@@ -1354,6 +1913,16 @@ out_free:
goto out_offset;
}
+bool bpf_jit_bypass_spec_v1(void)
+{
+ return true;
+}
+
+bool bpf_jit_bypass_spec_v4(void)
+{
+ return true;
+}
+
/* Indicate the JIT backend supports mixing bpf2bpf and tailcalls. */
bool bpf_jit_supports_subprog_tailcalls(void)
{
diff --git a/arch/loongarch/net/bpf_jit.h b/arch/loongarch/net/bpf_jit.h
index f9c569f53949..5697158fd164 100644
--- a/arch/loongarch/net/bpf_jit.h
+++ b/arch/loongarch/net/bpf_jit.h
@@ -18,6 +18,7 @@ struct jit_ctx {
u32 *offset;
int num_exentries;
union loongarch_instruction *image;
+ union loongarch_instruction *ro_image;
u32 stack_size;
};
@@ -308,3 +309,8 @@ static inline int emit_tailcall_jmp(struct jit_ctx *ctx, u8 cond, enum loongarch
return -EINVAL;
}
+
+static inline void bpf_flush_icache(void *start, void *end)
+{
+ flush_icache_range((unsigned long)start, (unsigned long)end);
+}
diff --git a/arch/loongarch/vdso/Makefile b/arch/loongarch/vdso/Makefile
index ccd2c5e135c6..d8316f993482 100644
--- a/arch/loongarch/vdso/Makefile
+++ b/arch/loongarch/vdso/Makefile
@@ -36,7 +36,7 @@ endif
# VDSO linker flags.
ldflags-y := -Bsymbolic --no-undefined -soname=linux-vdso.so.1 \
- $(filter -E%,$(KBUILD_CFLAGS)) -nostdlib -shared --build-id -T
+ $(filter -E%,$(KBUILD_CFLAGS)) -shared --build-id -T
#
# Shared build commands.
diff --git a/arch/x86/include/asm/hw_irq.h b/arch/x86/include/asm/hw_irq.h
index 162ebd73a698..99f7bf95ca16 100644
--- a/arch/x86/include/asm/hw_irq.h
+++ b/arch/x86/include/asm/hw_irq.h
@@ -26,7 +26,7 @@
#include <asm/irq.h>
#include <asm/sections.h>
-#ifdef CONFIG_IRQ_DOMAIN_HIERARCHY
+#ifdef CONFIG_X86_LOCAL_APIC
struct irq_data;
struct pci_dev;
struct msi_desc;
@@ -103,10 +103,10 @@ static inline void irq_complete_move(struct irq_cfg *c) { }
#endif
extern void apic_ack_edge(struct irq_data *data);
-#else /* CONFIG_IRQ_DOMAIN_HIERARCHY */
+#else /* CONFIG_X86_LOCAL_APIC */
static inline void lock_vector_lock(void) {}
static inline void unlock_vector_lock(void) {}
-#endif /* CONFIG_IRQ_DOMAIN_HIERARCHY */
+#endif /* !CONFIG_X86_LOCAL_APIC */
/* Statistics */
extern atomic_t irq_err_count;
diff --git a/arch/x86/include/asm/intel-family.h b/arch/x86/include/asm/intel-family.h
index be10c188614f..e345dbdf933e 100644
--- a/arch/x86/include/asm/intel-family.h
+++ b/arch/x86/include/asm/intel-family.h
@@ -150,6 +150,11 @@
#define INTEL_PANTHERLAKE_L IFM(6, 0xCC) /* Cougar Cove / Crestmont */
+#define INTEL_WILDCATLAKE_L IFM(6, 0xD5)
+
+#define INTEL_NOVALAKE IFM(18, 0x01)
+#define INTEL_NOVALAKE_L IFM(18, 0x03)
+
/* "Small Core" Processors (Atom/E-Core) */
#define INTEL_ATOM_BONNELL IFM(6, 0x1C) /* Diamondville, Pineview */
diff --git a/arch/x86/kernel/irq.c b/arch/x86/kernel/irq.c
index 9ed29ff10e59..10721a125226 100644
--- a/arch/x86/kernel/irq.c
+++ b/arch/x86/kernel/irq.c
@@ -256,26 +256,59 @@ static __always_inline void handle_irq(struct irq_desc *desc,
__handle_irq(desc, regs);
}
-static __always_inline int call_irq_handler(int vector, struct pt_regs *regs)
+static struct irq_desc *reevaluate_vector(int vector)
{
- struct irq_desc *desc;
- int ret = 0;
+ struct irq_desc *desc = __this_cpu_read(vector_irq[vector]);
+
+ if (!IS_ERR_OR_NULL(desc))
+ return desc;
+
+ if (desc == VECTOR_UNUSED)
+ pr_emerg_ratelimited("No irq handler for %d.%u\n", smp_processor_id(), vector);
+ else
+ __this_cpu_write(vector_irq[vector], VECTOR_UNUSED);
+ return NULL;
+}
+
+static __always_inline bool call_irq_handler(int vector, struct pt_regs *regs)
+{
+ struct irq_desc *desc = __this_cpu_read(vector_irq[vector]);
- desc = __this_cpu_read(vector_irq[vector]);
if (likely(!IS_ERR_OR_NULL(desc))) {
handle_irq(desc, regs);
- } else {
- ret = -EINVAL;
- if (desc == VECTOR_UNUSED) {
- pr_emerg_ratelimited("%s: %d.%u No irq handler for vector\n",
- __func__, smp_processor_id(),
- vector);
- } else {
- __this_cpu_write(vector_irq[vector], VECTOR_UNUSED);
- }
+ return true;
}
- return ret;
+ /*
+ * Reevaluate with vector_lock held to prevent a race against
+ * request_irq() setting up the vector:
+ *
+ * CPU0 CPU1
+ * interrupt is raised in APIC IRR
+ * but not handled
+ * free_irq()
+ * per_cpu(vector_irq, CPU1)[vector] = VECTOR_SHUTDOWN;
+ *
+ * request_irq() common_interrupt()
+ * d = this_cpu_read(vector_irq[vector]);
+ *
+ * per_cpu(vector_irq, CPU1)[vector] = desc;
+ *
+ * if (d == VECTOR_SHUTDOWN)
+ * this_cpu_write(vector_irq[vector], VECTOR_UNUSED);
+ *
+ * This requires that the same vector on the same target CPU is
+ * handed out or that a spurious interrupt hits that CPU/vector.
+ */
+ lock_vector_lock();
+ desc = reevaluate_vector(vector);
+ unlock_vector_lock();
+
+ if (!desc)
+ return false;
+
+ handle_irq(desc, regs);
+ return true;
}
/*
@@ -289,7 +322,7 @@ DEFINE_IDTENTRY_IRQ(common_interrupt)
/* entry code tells RCU that we're not quiescent. Check it. */
RCU_LOCKDEP_WARN(!rcu_is_watching(), "IRQ failed to wake up RCU");
- if (unlikely(call_irq_handler(vector, regs)))
+ if (unlikely(!call_irq_handler(vector, regs)))
apic_eoi();
set_irq_regs(old_regs);
diff --git a/block/bfq-iosched.h b/block/bfq-iosched.h
index 687a3a7ba784..0b4704932d72 100644
--- a/block/bfq-iosched.h
+++ b/block/bfq-iosched.h
@@ -427,9 +427,6 @@ struct bfq_iocq_bfqq_data {
*/
bool saved_IO_bound;
- u64 saved_io_start_time;
- u64 saved_tot_idle_time;
-
/*
* Same purpose as the previous fields for the values of the
* field keeping the queue's belonging to a large burst
@@ -450,6 +447,9 @@ struct bfq_iocq_bfqq_data {
*/
unsigned int saved_weight;
+ u64 saved_io_start_time;
+ u64 saved_tot_idle_time;
+
/*
* Similar to previous fields: save wr information.
*/
@@ -457,13 +457,13 @@ struct bfq_iocq_bfqq_data {
unsigned long saved_last_wr_start_finish;
unsigned long saved_service_from_wr;
unsigned long saved_wr_start_at_switch_to_srt;
- unsigned int saved_wr_cur_max_time;
struct bfq_ttime saved_ttime;
+ unsigned int saved_wr_cur_max_time;
/* Save also injection state */
- u64 saved_last_serv_time_ns;
unsigned int saved_inject_limit;
unsigned long saved_decrease_time_jif;
+ u64 saved_last_serv_time_ns;
/* candidate queue for a stable merge (due to close creation time) */
struct bfq_queue *stable_merge_bfqq;
diff --git a/drivers/base/regmap/regmap-irq.c b/drivers/base/regmap/regmap-irq.c
index d1585f073776..6112d942499b 100644
--- a/drivers/base/regmap/regmap-irq.c
+++ b/drivers/base/regmap/regmap-irq.c
@@ -21,6 +21,7 @@
struct regmap_irq_chip_data {
struct mutex lock;
+ struct lock_class_key lock_key;
struct irq_chip irq_chip;
struct regmap *map;
@@ -801,7 +802,13 @@ int regmap_add_irq_chip_fwnode(struct fwnode_handle *fwnode,
goto err_alloc;
}
- mutex_init(&d->lock);
+ /*
+ * If one regmap-irq is the parent of another then we'll try
+ * to lock the child with the parent locked, use an explicit
+ * lock_key so lockdep can figure out what's going on.
+ */
+ lockdep_register_key(&d->lock_key);
+ mutex_init_with_key(&d->lock, &d->lock_key);
for (i = 0; i < chip->num_irqs; i++)
d->mask_buf_def[chip->irqs[i].reg_offset / map->reg_stride]
@@ -816,7 +823,7 @@ int regmap_add_irq_chip_fwnode(struct fwnode_handle *fwnode,
d->mask_buf[i],
chip->irq_drv_data);
if (ret)
- goto err_alloc;
+ goto err_mutex;
}
if (chip->mask_base && !chip->handle_mask_sync) {
@@ -827,7 +834,7 @@ int regmap_add_irq_chip_fwnode(struct fwnode_handle *fwnode,
if (ret) {
dev_err(map->dev, "Failed to set masks in 0x%x: %d\n",
reg, ret);
- goto err_alloc;
+ goto err_mutex;
}
}
@@ -838,7 +845,7 @@ int regmap_add_irq_chip_fwnode(struct fwnode_handle *fwnode,
if (ret) {
dev_err(map->dev, "Failed to set masks in 0x%x: %d\n",
reg, ret);
- goto err_alloc;
+ goto err_mutex;
}
}
@@ -855,7 +862,7 @@ int regmap_add_irq_chip_fwnode(struct fwnode_handle *fwnode,
if (ret != 0) {
dev_err(map->dev, "Failed to read IRQ status: %d\n",
ret);
- goto err_alloc;
+ goto err_mutex;
}
}
@@ -879,7 +886,7 @@ int regmap_add_irq_chip_fwnode(struct fwnode_handle *fwnode,
if (ret != 0) {
dev_err(map->dev, "Failed to ack 0x%x: %d\n",
reg, ret);
- goto err_alloc;
+ goto err_mutex;
}
}
}
@@ -901,7 +908,7 @@ int regmap_add_irq_chip_fwnode(struct fwnode_handle *fwnode,
if (ret != 0) {
dev_err(map->dev, "Failed to set masks in 0x%x: %d\n",
reg, ret);
- goto err_alloc;
+ goto err_mutex;
}
}
}
@@ -910,7 +917,7 @@ int regmap_add_irq_chip_fwnode(struct fwnode_handle *fwnode,
if (chip->status_is_level) {
ret = read_irq_data(d);
if (ret < 0)
- goto err_alloc;
+ goto err_mutex;
memcpy(d->prev_status_buf, d->status_buf,
array_size(d->chip->num_regs, sizeof(d->prev_status_buf[0])));
@@ -918,7 +925,7 @@ int regmap_add_irq_chip_fwnode(struct fwnode_handle *fwnode,
ret = regmap_irq_create_domain(fwnode, irq_base, chip, d);
if (ret)
- goto err_alloc;
+ goto err_mutex;
ret = request_threaded_irq(irq, NULL, regmap_irq_thread,
irq_flags | IRQF_ONESHOT,
@@ -935,6 +942,9 @@ int regmap_add_irq_chip_fwnode(struct fwnode_handle *fwnode,
err_domain:
/* Should really dispose of the domain but... */
+err_mutex:
+ mutex_destroy(&d->lock);
+ lockdep_unregister_key(&d->lock_key);
err_alloc:
kfree(d->type_buf);
kfree(d->type_buf_def);
@@ -1027,6 +1037,8 @@ void regmap_del_irq_chip(int irq, struct regmap_irq_chip_data *d)
kfree(d->config_buf[i]);
kfree(d->config_buf);
}
+ mutex_destroy(&d->lock);
+ lockdep_unregister_key(&d->lock_key);
kfree(d);
}
EXPORT_SYMBOL_GPL(regmap_del_irq_chip);
diff --git a/drivers/bluetooth/btintel_pcie.c b/drivers/bluetooth/btintel_pcie.c
index ce17c5ea67e8..22a2953adbd6 100644
--- a/drivers/bluetooth/btintel_pcie.c
+++ b/drivers/bluetooth/btintel_pcie.c
@@ -2416,6 +2416,13 @@ static void btintel_pcie_hw_error(struct hci_dev *hdev, u8 code)
btintel_pcie_reset(hdev);
}
+static bool btintel_pcie_wakeup(struct hci_dev *hdev)
+{
+ struct btintel_pcie_data *data = hci_get_drvdata(hdev);
+
+ return device_may_wakeup(&data->pdev->dev);
+}
+
static int btintel_pcie_setup_hdev(struct btintel_pcie_data *data)
{
int err;
@@ -2441,6 +2448,7 @@ static int btintel_pcie_setup_hdev(struct btintel_pcie_data *data)
hdev->set_diag = btintel_set_diag;
hdev->set_bdaddr = btintel_set_bdaddr;
hdev->reset = btintel_pcie_reset;
+ hdev->wakeup = btintel_pcie_wakeup;
err = hci_register_dev(hdev);
if (err < 0) {
diff --git a/drivers/bluetooth/btmtk.c b/drivers/bluetooth/btmtk.c
index 4390fd571dbd..a8c520dc09e1 100644
--- a/drivers/bluetooth/btmtk.c
+++ b/drivers/bluetooth/btmtk.c
@@ -642,12 +642,7 @@ static int btmtk_usb_hci_wmt_sync(struct hci_dev *hdev,
* WMT command.
*/
err = wait_on_bit_timeout(&data->flags, BTMTK_TX_WAIT_VND_EVT,
- TASK_INTERRUPTIBLE, HCI_INIT_TIMEOUT);
- if (err == -EINTR) {
- bt_dev_err(hdev, "Execution of wmt command interrupted");
- clear_bit(BTMTK_TX_WAIT_VND_EVT, &data->flags);
- goto err_free_wc;
- }
+ TASK_UNINTERRUPTIBLE, HCI_INIT_TIMEOUT);
if (err) {
bt_dev_err(hdev, "Execution of wmt command timed out");
diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c
index 8085fabadde8..3595a8bad6bd 100644
--- a/drivers/bluetooth/btusb.c
+++ b/drivers/bluetooth/btusb.c
@@ -522,6 +522,8 @@ static const struct usb_device_id quirks_table[] = {
/* Realtek 8851BU Bluetooth devices */
{ USB_DEVICE(0x3625, 0x010b), .driver_info = BTUSB_REALTEK |
BTUSB_WIDEBAND_SPEECH },
+ { USB_DEVICE(0x2001, 0x332a), .driver_info = BTUSB_REALTEK |
+ BTUSB_WIDEBAND_SPEECH },
/* Realtek 8852AE Bluetooth devices */
{ USB_DEVICE(0x0bda, 0x2852), .driver_info = BTUSB_REALTEK |
diff --git a/drivers/char/ipmi/ipmi_msghandler.c b/drivers/char/ipmi/ipmi_msghandler.c
index 064944ae9fdc..8e9050f99e9e 100644
--- a/drivers/char/ipmi/ipmi_msghandler.c
+++ b/drivers/char/ipmi/ipmi_msghandler.c
@@ -4607,10 +4607,10 @@ return_unspecified:
* The NetFN and Command in the response is not even
* marginally correct.
*/
- dev_warn(intf->si_dev,
- "BMC returned incorrect response, expected netfn %x cmd %x, got netfn %x cmd %x\n",
- (msg->data[0] >> 2) | 1, msg->data[1],
- msg->rsp[0] >> 2, msg->rsp[1]);
+ dev_warn_ratelimited(intf->si_dev,
+ "BMC returned incorrect response, expected netfn %x cmd %x, got netfn %x cmd %x\n",
+ (msg->data[0] >> 2) | 1, msg->data[1],
+ msg->rsp[0] >> 2, msg->rsp[1]);
goto return_unspecified;
}
diff --git a/drivers/dpll/zl3073x/Kconfig b/drivers/dpll/zl3073x/Kconfig
index 7db262ab8458..9915f7423dea 100644
--- a/drivers/dpll/zl3073x/Kconfig
+++ b/drivers/dpll/zl3073x/Kconfig
@@ -1,7 +1,7 @@
# SPDX-License-Identifier: GPL-2.0-only
config ZL3073X
- tristate "Microchip Azurite DPLL/PTP/SyncE devices"
+ tristate "Microchip Azurite DPLL/PTP/SyncE devices" if COMPILE_TEST
depends on NET
select DPLL
select NET_DEVLINK
@@ -16,9 +16,9 @@ config ZL3073X
config ZL3073X_I2C
tristate "I2C bus implementation for Microchip Azurite devices"
- depends on I2C && ZL3073X
+ depends on I2C
select REGMAP_I2C
- default m
+ select ZL3073X
help
This is I2C bus implementation for Microchip Azurite DPLL/PTP/SyncE
devices.
@@ -28,9 +28,9 @@ config ZL3073X_I2C
config ZL3073X_SPI
tristate "SPI bus implementation for Microchip Azurite devices"
- depends on SPI && ZL3073X
+ depends on SPI
select REGMAP_SPI
- default m
+ select ZL3073X
help
This is SPI bus implementation for Microchip Azurite DPLL/PTP/SyncE
devices.
diff --git a/drivers/gpio/gpio-mlxbf2.c b/drivers/gpio/gpio-mlxbf2.c
index 6f3dda6b635f..390f2e74a9d8 100644
--- a/drivers/gpio/gpio-mlxbf2.c
+++ b/drivers/gpio/gpio-mlxbf2.c
@@ -397,7 +397,7 @@ mlxbf2_gpio_probe(struct platform_device *pdev)
gc->ngpio = npins;
gc->owner = THIS_MODULE;
- irq = platform_get_irq(pdev, 0);
+ irq = platform_get_irq_optional(pdev, 0);
if (irq >= 0) {
girq = &gs->gc.irq;
gpio_irq_chip_set_chip(girq, &mlxbf2_gpio_irq_chip);
diff --git a/drivers/gpio/gpio-pxa.c b/drivers/gpio/gpio-pxa.c
index 13f7da2a9486..cbcdd416f8b9 100644
--- a/drivers/gpio/gpio-pxa.c
+++ b/drivers/gpio/gpio-pxa.c
@@ -499,8 +499,6 @@ static void pxa_mask_muxed_gpio(struct irq_data *d)
gfer = readl_relaxed(base + GFER_OFFSET) & ~GPIO_bit(gpio);
writel_relaxed(grer, base + GRER_OFFSET);
writel_relaxed(gfer, base + GFER_OFFSET);
-
- gpiochip_disable_irq(&pchip->chip, gpio);
}
static int pxa_gpio_set_wake(struct irq_data *d, unsigned int on)
@@ -520,21 +518,17 @@ static void pxa_unmask_muxed_gpio(struct irq_data *d)
unsigned int gpio = irqd_to_hwirq(d);
struct pxa_gpio_bank *c = gpio_to_pxabank(&pchip->chip, gpio);
- gpiochip_enable_irq(&pchip->chip, gpio);
-
c->irq_mask |= GPIO_bit(gpio);
update_edge_detect(c);
}
-static const struct irq_chip pxa_muxed_gpio_chip = {
+static struct irq_chip pxa_muxed_gpio_chip = {
.name = "GPIO",
.irq_ack = pxa_ack_muxed_gpio,
.irq_mask = pxa_mask_muxed_gpio,
.irq_unmask = pxa_unmask_muxed_gpio,
.irq_set_type = pxa_gpio_irq_type,
.irq_set_wake = pxa_gpio_set_wake,
- .flags = IRQCHIP_IMMUTABLE,
- GPIOCHIP_IRQ_RESOURCE_HELPERS,
};
static int pxa_gpio_nums(struct platform_device *pdev)
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_aca.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_aca.c
index cbc40cad581b..d1e431818212 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_aca.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_aca.c
@@ -130,6 +130,27 @@ static void aca_smu_bank_dump(struct amdgpu_device *adev, int idx, int total, st
RAS_EVENT_LOG(adev, event_id, HW_ERR "hardware error logged by the scrubber\n");
}
+static bool aca_bank_hwip_is_matched(struct aca_bank *bank, enum aca_hwip_type type)
+{
+
+ struct aca_hwip *hwip;
+ int hwid, mcatype;
+ u64 ipid;
+
+ if (!bank || type == ACA_HWIP_TYPE_UNKNOW)
+ return false;
+
+ hwip = &aca_hwid_mcatypes[type];
+ if (!hwip->hwid)
+ return false;
+
+ ipid = bank->regs[ACA_REG_IDX_IPID];
+ hwid = ACA_REG__IPID__HARDWAREID(ipid);
+ mcatype = ACA_REG__IPID__MCATYPE(ipid);
+
+ return hwip->hwid == hwid && hwip->mcatype == mcatype;
+}
+
static int aca_smu_get_valid_aca_banks(struct amdgpu_device *adev, enum aca_smu_type type,
int start, int count,
struct aca_banks *banks, struct ras_query_context *qctx)
@@ -168,6 +189,15 @@ static int aca_smu_get_valid_aca_banks(struct amdgpu_device *adev, enum aca_smu_
bank.smu_err_type = type;
+ /*
+ * Poison being consumed when injecting a UE while running background workloads,
+ * which are unexpected.
+ */
+ if (type == ACA_SMU_TYPE_UE &&
+ ACA_REG__STATUS__POISON(bank.regs[ACA_REG_IDX_STATUS]) &&
+ !aca_bank_hwip_is_matched(&bank, ACA_HWIP_TYPE_UMC))
+ continue;
+
aca_smu_bank_dump(adev, i, count, &bank, qctx);
ret = aca_banks_add_bank(banks, &bank);
@@ -178,27 +208,6 @@ static int aca_smu_get_valid_aca_banks(struct amdgpu_device *adev, enum aca_smu_
return 0;
}
-static bool aca_bank_hwip_is_matched(struct aca_bank *bank, enum aca_hwip_type type)
-{
-
- struct aca_hwip *hwip;
- int hwid, mcatype;
- u64 ipid;
-
- if (!bank || type == ACA_HWIP_TYPE_UNKNOW)
- return false;
-
- hwip = &aca_hwid_mcatypes[type];
- if (!hwip->hwid)
- return false;
-
- ipid = bank->regs[ACA_REG_IDX_IPID];
- hwid = ACA_REG__IPID__HARDWAREID(ipid);
- mcatype = ACA_REG__IPID__MCATYPE(ipid);
-
- return hwip->hwid == hwid && hwip->mcatype == mcatype;
-}
-
static bool aca_bank_is_valid(struct aca_handle *handle, struct aca_bank *bank, enum aca_smu_type type)
{
const struct aca_bank_ops *bank_ops = handle->bank_ops;
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c
index 260165bbe373..37d8a7034a7e 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c
@@ -494,7 +494,8 @@ static int vm_update_pds(struct amdgpu_vm *vm, struct amdgpu_sync *sync)
return amdgpu_sync_fence(sync, vm->last_update, GFP_KERNEL);
}
-static uint64_t get_pte_flags(struct amdgpu_device *adev, struct kgd_mem *mem)
+static uint64_t get_pte_flags(struct amdgpu_device *adev, struct amdgpu_vm *vm,
+ struct kgd_mem *mem)
{
uint32_t mapping_flags = AMDGPU_VM_PAGE_READABLE |
AMDGPU_VM_MTYPE_DEFAULT;
@@ -504,7 +505,7 @@ static uint64_t get_pte_flags(struct amdgpu_device *adev, struct kgd_mem *mem)
if (mem->alloc_flags & KFD_IOC_ALLOC_MEM_FLAGS_EXECUTABLE)
mapping_flags |= AMDGPU_VM_PAGE_EXECUTABLE;
- return amdgpu_gem_va_map_flags(adev, mapping_flags);
+ return mapping_flags;
}
/**
@@ -961,7 +962,7 @@ static int kfd_mem_attach(struct amdgpu_device *adev, struct kgd_mem *mem,
goto unwind;
}
attachment[i]->va = va;
- attachment[i]->pte_flags = get_pte_flags(adev, mem);
+ attachment[i]->pte_flags = get_pte_flags(adev, vm, mem);
attachment[i]->adev = adev;
list_add(&attachment[i]->list, &mem->attachments);
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_cper.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_cper.c
index 25252231a68a..6c266f18c598 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_cper.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_cper.c
@@ -206,6 +206,7 @@ int amdgpu_cper_entry_fill_bad_page_threshold_section(struct amdgpu_device *adev
{
struct cper_sec_desc *section_desc;
struct cper_sec_nonstd_err *section;
+ uint32_t socket_id;
section_desc = (struct cper_sec_desc *)((uint8_t *)hdr + SEC_DESC_OFFSET(idx));
section = (struct cper_sec_nonstd_err *)((uint8_t *)hdr +
@@ -224,6 +225,9 @@ int amdgpu_cper_entry_fill_bad_page_threshold_section(struct amdgpu_device *adev
section->ctx.reg_arr_size = sizeof(section->ctx.reg_dump);
/* Hardcoded Reg dump for bad page threshold CPER */
+ socket_id = (adev->smuio.funcs && adev->smuio.funcs->get_socket_id) ?
+ adev->smuio.funcs->get_socket_id(adev) :
+ 0;
section->ctx.reg_dump[CPER_ACA_REG_CTL_LO] = 0x1;
section->ctx.reg_dump[CPER_ACA_REG_CTL_HI] = 0x0;
section->ctx.reg_dump[CPER_ACA_REG_STATUS_LO] = 0x137;
@@ -234,8 +238,8 @@ int amdgpu_cper_entry_fill_bad_page_threshold_section(struct amdgpu_device *adev
section->ctx.reg_dump[CPER_ACA_REG_MISC0_HI] = 0x0;
section->ctx.reg_dump[CPER_ACA_REG_CONFIG_LO] = 0x2;
section->ctx.reg_dump[CPER_ACA_REG_CONFIG_HI] = 0x1ff;
- section->ctx.reg_dump[CPER_ACA_REG_IPID_LO] = 0x0;
- section->ctx.reg_dump[CPER_ACA_REG_IPID_HI] = 0x96;
+ section->ctx.reg_dump[CPER_ACA_REG_IPID_LO] = (socket_id / 4) & 0x01;
+ section->ctx.reg_dump[CPER_ACA_REG_IPID_HI] = 0x096 | (((socket_id % 4) & 0x3) << 12);
section->ctx.reg_dump[CPER_ACA_REG_SYND_LO] = 0x0;
section->ctx.reg_dump[CPER_ACA_REG_SYND_HI] = 0x0;
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_cs.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_cs.c
index a2adaacf6adb..27f8f316f6c2 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_cs.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_cs.c
@@ -396,7 +396,7 @@ static int amdgpu_cs_p2_ib(struct amdgpu_cs_parser *p,
chunk_ib->ib_bytes : 0,
AMDGPU_IB_POOL_DELAYED, ib);
if (r) {
- DRM_ERROR("Failed to get ib !\n");
+ drm_err(adev_to_drm(p->adev), "Failed to get ib !\n");
return r;
}
@@ -468,7 +468,7 @@ static int amdgpu_syncobj_lookup_and_add(struct amdgpu_cs_parser *p,
r = drm_syncobj_find_fence(p->filp, handle, point, flags, &fence);
if (r) {
- DRM_ERROR("syncobj %u failed to find fence @ %llu (%d)!\n",
+ drm_err(adev_to_drm(p->adev), "syncobj %u failed to find fence @ %llu (%d)!\n",
handle, point, r);
return r;
}
@@ -902,7 +902,7 @@ static int amdgpu_cs_parser_bos(struct amdgpu_cs_parser *p,
sizeof(struct page *),
GFP_KERNEL);
if (!e->user_pages) {
- DRM_ERROR("kvmalloc_array failure\n");
+ drm_err(adev_to_drm(p->adev), "kvmalloc_array failure\n");
r = -ENOMEM;
goto out_free_user_pages;
}
@@ -983,7 +983,7 @@ static int amdgpu_cs_parser_bos(struct amdgpu_cs_parser *p,
r = amdgpu_vm_validate(p->adev, &fpriv->vm, NULL,
amdgpu_cs_bo_validate, p);
if (r) {
- DRM_ERROR("amdgpu_vm_validate() failed.\n");
+ drm_err(adev_to_drm(p->adev), "amdgpu_vm_validate() failed.\n");
goto out_free_user_pages;
}
@@ -1061,13 +1061,13 @@ static int amdgpu_cs_patch_ibs(struct amdgpu_cs_parser *p,
va_start = ib->gpu_addr & AMDGPU_GMC_HOLE_MASK;
r = amdgpu_cs_find_mapping(p, va_start, &aobj, &m);
if (r) {
- DRM_ERROR("IB va_start is invalid\n");
+ drm_err(adev_to_drm(p->adev), "IB va_start is invalid\n");
return r;
}
if ((va_start + ib->length_dw * 4) >
(m->last + 1) * AMDGPU_GPU_PAGE_SIZE) {
- DRM_ERROR("IB va_start+ib_bytes is invalid\n");
+ drm_err(adev_to_drm(p->adev), "IB va_start+ib_bytes is invalid\n");
return -EINVAL;
}
@@ -1235,7 +1235,7 @@ static int amdgpu_cs_sync_rings(struct amdgpu_cs_parser *p)
r = amdgpu_ctx_wait_prev_fence(p->ctx, p->entities[p->gang_leader_idx]);
if (r) {
if (r != -ERESTARTSYS)
- DRM_ERROR("amdgpu_ctx_wait_prev_fence failed.\n");
+ drm_err(adev_to_drm(p->adev), "amdgpu_ctx_wait_prev_fence failed.\n");
return r;
}
@@ -1448,7 +1448,7 @@ int amdgpu_cs_ioctl(struct drm_device *dev, void *data, struct drm_file *filp)
r = amdgpu_cs_parser_init(&parser, adev, filp, data);
if (r) {
- DRM_ERROR_RATELIMITED("Failed to initialize parser %d!\n", r);
+ drm_err_ratelimited(dev, "Failed to initialize parser %d!\n", r);
return r;
}
@@ -1463,9 +1463,9 @@ int amdgpu_cs_ioctl(struct drm_device *dev, void *data, struct drm_file *filp)
r = amdgpu_cs_parser_bos(&parser, data);
if (r) {
if (r == -ENOMEM)
- DRM_ERROR("Not enough memory for command submission!\n");
+ drm_err(dev, "Not enough memory for command submission!\n");
else if (r != -ERESTARTSYS && r != -EAGAIN)
- DRM_DEBUG("Failed to process the buffer list %d!\n", r);
+ drm_dbg(dev, "Failed to process the buffer list %d!\n", r);
goto error_fini;
}
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
index 6f93473436be..3843e30fb3f3 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
@@ -3389,7 +3389,7 @@ static int amdgpu_device_enable_mgpu_fan_boost(void)
for (i = 0; i < mgpu_info.num_dgpu; i++) {
gpu_ins = &(mgpu_info.gpu_ins[i]);
adev = gpu_ins->adev;
- if (!(adev->flags & AMD_IS_APU) &&
+ if (!(adev->flags & AMD_IS_APU || amdgpu_sriov_multi_vf_mode(adev)) &&
!gpu_ins->mgpu_fan_enabled) {
ret = amdgpu_dpm_enable_mgpu_fan_boost(adev);
if (ret)
@@ -5701,7 +5701,7 @@ int amdgpu_device_link_reset(struct amdgpu_device *adev)
dev_info(adev->dev, "GPU link reset\n");
- if (!adev->pcie_reset_ctx.occurs_dpc)
+ if (!amdgpu_reset_in_dpc(adev))
ret = amdgpu_dpm_link_reset(adev);
if (ret)
@@ -6136,12 +6136,11 @@ static int amdgpu_device_health_check(struct list_head *device_list_handle)
return ret;
}
-static int amdgpu_device_recovery_prepare(struct amdgpu_device *adev,
+static void amdgpu_device_recovery_prepare(struct amdgpu_device *adev,
struct list_head *device_list,
struct amdgpu_hive_info *hive)
{
struct amdgpu_device *tmp_adev = NULL;
- int r;
/*
* Build list of devices to reset.
@@ -6153,7 +6152,7 @@ static int amdgpu_device_recovery_prepare(struct amdgpu_device *adev,
list_add_tail(&tmp_adev->reset_list, device_list);
if (adev->shutdown)
tmp_adev->shutdown = true;
- if (adev->pcie_reset_ctx.occurs_dpc)
+ if (amdgpu_reset_in_dpc(adev))
tmp_adev->pcie_reset_ctx.in_link_reset = true;
}
if (!list_is_first(&adev->reset_list, device_list))
@@ -6161,14 +6160,6 @@ static int amdgpu_device_recovery_prepare(struct amdgpu_device *adev,
} else {
list_add_tail(&adev->reset_list, device_list);
}
-
- if (!amdgpu_sriov_vf(adev) && (!adev->pcie_reset_ctx.occurs_dpc)) {
- r = amdgpu_device_health_check(device_list);
- if (r)
- return r;
- }
-
- return 0;
}
static void amdgpu_device_recovery_get_reset_lock(struct amdgpu_device *adev,
@@ -6237,9 +6228,8 @@ static void amdgpu_device_halt_activities(struct amdgpu_device *adev,
drm_client_dev_suspend(adev_to_drm(tmp_adev), false);
/* disable ras on ALL IPs */
- if (!need_emergency_restart &&
- (!adev->pcie_reset_ctx.occurs_dpc) &&
- amdgpu_device_ip_need_full_reset(tmp_adev))
+ if (!need_emergency_restart && !amdgpu_reset_in_dpc(adev) &&
+ amdgpu_device_ip_need_full_reset(tmp_adev))
amdgpu_ras_suspend(tmp_adev);
for (i = 0; i < AMDGPU_MAX_RINGS; ++i) {
@@ -6267,10 +6257,10 @@ static int amdgpu_device_asic_reset(struct amdgpu_device *adev,
retry: /* Rest of adevs pre asic reset from XGMI hive. */
list_for_each_entry(tmp_adev, device_list, reset_list) {
- if (adev->pcie_reset_ctx.occurs_dpc)
+ if (amdgpu_reset_in_dpc(adev))
tmp_adev->no_hw_access = true;
r = amdgpu_device_pre_asic_reset(tmp_adev, reset_context);
- if (adev->pcie_reset_ctx.occurs_dpc)
+ if (amdgpu_reset_in_dpc(adev))
tmp_adev->no_hw_access = false;
/*TODO Should we stop ?*/
if (r) {
@@ -6461,8 +6451,13 @@ int amdgpu_device_gpu_recover(struct amdgpu_device *adev,
reset_context->hive = hive;
INIT_LIST_HEAD(&device_list);
- if (amdgpu_device_recovery_prepare(adev, &device_list, hive))
- goto end_reset;
+ amdgpu_device_recovery_prepare(adev, &device_list, hive);
+
+ if (!amdgpu_sriov_vf(adev)) {
+ r = amdgpu_device_health_check(&device_list);
+ if (r)
+ goto end_reset;
+ }
/* We need to lock reset domain only once both for XGMI and single device */
amdgpu_device_recovery_get_reset_lock(adev, &device_list);
@@ -6907,7 +6902,7 @@ pci_ers_result_t amdgpu_pci_error_detected(struct pci_dev *pdev, pci_channel_sta
if (hive)
mutex_lock(&hive->hive_lock);
- adev->pcie_reset_ctx.occurs_dpc = true;
+ amdgpu_reset_set_dpc_status(adev, true);
memset(&reset_context, 0, sizeof(reset_context));
INIT_LIST_HEAD(&device_list);
@@ -6969,12 +6964,6 @@ pci_ers_result_t amdgpu_pci_slot_reset(struct pci_dev *pdev)
int r = 0, i;
u32 memsize;
- /* PCI error slot reset should be skipped During RAS recovery */
- if ((amdgpu_ip_version(adev, GC_HWIP, 0) == IP_VERSION(9, 4, 3) ||
- amdgpu_ip_version(adev, GC_HWIP, 0) == IP_VERSION(9, 4, 4)) &&
- amdgpu_ras_in_recovery(adev))
- return PCI_ERS_RESULT_RECOVERED;
-
dev_info(adev->dev, "PCI error: slot reset callback!!\n");
memset(&reset_context, 0, sizeof(reset_context));
@@ -7076,7 +7065,7 @@ void amdgpu_pci_resume(struct pci_dev *pdev)
amdgpu_device_sched_resume(&device_list, NULL, NULL);
amdgpu_device_gpu_resume(adev, &device_list, false);
amdgpu_device_recovery_put_reset_lock(adev, &device_list);
- adev->pcie_reset_ctx.occurs_dpc = false;
+ amdgpu_reset_set_dpc_status(adev, false);
if (hive) {
mutex_unlock(&hive->hive_lock);
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c
index efb54c23ba17..141ba1f100d4 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c
@@ -2597,6 +2597,7 @@ static int amdgpu_pmops_suspend(struct device *dev)
else if (amdgpu_acpi_is_s3_active(adev))
adev->in_s3 = true;
if (!adev->in_s0ix && !adev->in_s3) {
+#if IS_ENABLED(CONFIG_SUSPEND)
/* don't allow going deep first time followed by s2idle the next time */
if (adev->last_suspend_state != PM_SUSPEND_ON &&
adev->last_suspend_state != pm_suspend_target_state) {
@@ -2604,11 +2605,14 @@ static int amdgpu_pmops_suspend(struct device *dev)
pm_suspend_target_state);
return -EINVAL;
}
+#endif
return 0;
}
+#if IS_ENABLED(CONFIG_SUSPEND)
/* cache the state last used for suspend */
adev->last_suspend_state = pm_suspend_target_state;
+#endif
return amdgpu_device_suspend(drm_dev, true);
}
@@ -2964,15 +2968,15 @@ out:
}
static const struct dev_pm_ops amdgpu_pm_ops = {
- .prepare = amdgpu_pmops_prepare,
- .complete = amdgpu_pmops_complete,
- .suspend = amdgpu_pmops_suspend,
- .suspend_noirq = amdgpu_pmops_suspend_noirq,
- .resume = amdgpu_pmops_resume,
- .freeze = amdgpu_pmops_freeze,
- .thaw = amdgpu_pmops_thaw,
- .poweroff = amdgpu_pmops_poweroff,
- .restore = amdgpu_pmops_restore,
+ .prepare = pm_sleep_ptr(amdgpu_pmops_prepare),
+ .complete = pm_sleep_ptr(amdgpu_pmops_complete),
+ .suspend = pm_sleep_ptr(amdgpu_pmops_suspend),
+ .suspend_noirq = pm_sleep_ptr(amdgpu_pmops_suspend_noirq),
+ .resume = pm_sleep_ptr(amdgpu_pmops_resume),
+ .freeze = pm_sleep_ptr(amdgpu_pmops_freeze),
+ .thaw = pm_sleep_ptr(amdgpu_pmops_thaw),
+ .poweroff = pm_sleep_ptr(amdgpu_pmops_poweroff),
+ .restore = pm_sleep_ptr(amdgpu_pmops_restore),
.runtime_suspend = amdgpu_pmops_runtime_suspend,
.runtime_resume = amdgpu_pmops_runtime_resume,
.runtime_idle = amdgpu_pmops_runtime_idle,
@@ -3117,7 +3121,7 @@ static struct pci_driver amdgpu_kms_pci_driver = {
.probe = amdgpu_pci_probe,
.remove = amdgpu_pci_remove,
.shutdown = amdgpu_pci_shutdown,
- .driver.pm = &amdgpu_pm_ops,
+ .driver.pm = pm_ptr(&amdgpu_pm_ops),
.err_handler = &amdgpu_pci_err_handler,
.dev_groups = amdgpu_sysfs_groups,
};
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c
index 9e7506965cab..bcb74286a78a 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_fence.c
@@ -738,7 +738,7 @@ void amdgpu_fence_driver_force_completion(struct amdgpu_ring *ring)
}
-/**
+/*
* Kernel queue reset handling
*
* The driver can reset individual queues for most engines, but those queues
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_gem.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_gem.c
index 6626a6e64ff5..d5e685c5e28b 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_gem.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_gem.c
@@ -790,36 +790,6 @@ error:
return fence;
}
-/**
- * amdgpu_gem_va_map_flags - map GEM UAPI flags into hardware flags
- *
- * @adev: amdgpu_device pointer
- * @flags: GEM UAPI flags
- *
- * Returns the GEM UAPI flags mapped into hardware for the ASIC.
- */
-uint64_t amdgpu_gem_va_map_flags(struct amdgpu_device *adev, uint32_t flags)
-{
- uint64_t pte_flag = 0;
-
- if (flags & AMDGPU_VM_PAGE_EXECUTABLE)
- pte_flag |= AMDGPU_PTE_EXECUTABLE;
- if (flags & AMDGPU_VM_PAGE_READABLE)
- pte_flag |= AMDGPU_PTE_READABLE;
- if (flags & AMDGPU_VM_PAGE_WRITEABLE)
- pte_flag |= AMDGPU_PTE_WRITEABLE;
- if (flags & AMDGPU_VM_PAGE_PRT)
- pte_flag |= AMDGPU_PTE_PRT_FLAG(adev);
- if (flags & AMDGPU_VM_PAGE_NOALLOC)
- pte_flag |= AMDGPU_PTE_NOALLOC;
-
- if (adev->gmc.gmc_funcs->map_mtype)
- pte_flag |= amdgpu_gmc_map_mtype(adev,
- flags & AMDGPU_VM_MTYPE_MASK);
-
- return pte_flag;
-}
-
int amdgpu_gem_va_ioctl(struct drm_device *dev, void *data,
struct drm_file *filp)
{
@@ -840,7 +810,6 @@ int amdgpu_gem_va_ioctl(struct drm_device *dev, void *data,
struct dma_fence_chain *timeline_chain = NULL;
struct dma_fence *fence;
struct drm_exec exec;
- uint64_t va_flags;
uint64_t vm_size;
int r = 0;
@@ -944,10 +913,9 @@ int amdgpu_gem_va_ioctl(struct drm_device *dev, void *data,
switch (args->operation) {
case AMDGPU_VA_OP_MAP:
- va_flags = amdgpu_gem_va_map_flags(adev, args->flags);
r = amdgpu_vm_bo_map(adev, bo_va, args->va_address,
args->offset_in_bo, args->map_size,
- va_flags);
+ args->flags);
break;
case AMDGPU_VA_OP_UNMAP:
r = amdgpu_vm_bo_unmap(adev, bo_va, args->va_address);
@@ -959,10 +927,9 @@ int amdgpu_gem_va_ioctl(struct drm_device *dev, void *data,
args->map_size);
break;
case AMDGPU_VA_OP_REPLACE:
- va_flags = amdgpu_gem_va_map_flags(adev, args->flags);
r = amdgpu_vm_bo_replace_map(adev, bo_va, args->va_address,
args->offset_in_bo, args->map_size,
- va_flags);
+ args->flags);
break;
default:
break;
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_gem.h b/drivers/gpu/drm/amd/amdgpu/amdgpu_gem.h
index 3a8f57900a3a..b51e8f95ee86 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_gem.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_gem.h
@@ -63,7 +63,6 @@ int amdgpu_gem_mmap_ioctl(struct drm_device *dev, void *data,
struct drm_file *filp);
int amdgpu_gem_wait_idle_ioctl(struct drm_device *dev, void *data,
struct drm_file *filp);
-uint64_t amdgpu_gem_va_map_flags(struct amdgpu_device *adev, uint32_t flags);
int amdgpu_gem_va_ioctl(struct drm_device *dev, void *data,
struct drm_file *filp);
int amdgpu_gem_op_ioctl(struct drm_device *dev, void *data,
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_gmc.h b/drivers/gpu/drm/amd/amdgpu/amdgpu_gmc.h
index 397c6ccdb903..55097ca10738 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_gmc.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_gmc.h
@@ -154,15 +154,15 @@ struct amdgpu_gmc_funcs {
unsigned pasid);
/* enable/disable PRT support */
void (*set_prt)(struct amdgpu_device *adev, bool enable);
- /* map mtype to hardware flags */
- uint64_t (*map_mtype)(struct amdgpu_device *adev, uint32_t flags);
/* get the pde for a given mc addr */
void (*get_vm_pde)(struct amdgpu_device *adev, int level,
u64 *dst, u64 *flags);
- /* get the pte flags to use for a BO VA mapping */
+ /* get the pte flags to use for PTEs */
void (*get_vm_pte)(struct amdgpu_device *adev,
- struct amdgpu_bo_va_mapping *mapping,
- uint64_t *flags);
+ struct amdgpu_vm *vm,
+ struct amdgpu_bo *bo,
+ uint32_t vm_flags,
+ uint64_t *pte_flags);
/* override per-page pte flags */
void (*override_vm_pte_flags)(struct amdgpu_device *dev,
struct amdgpu_vm *vm,
@@ -356,9 +356,10 @@ struct amdgpu_gmc {
#define amdgpu_gmc_emit_flush_gpu_tlb(r, vmid, addr) (r)->adev->gmc.gmc_funcs->emit_flush_gpu_tlb((r), (vmid), (addr))
#define amdgpu_gmc_emit_pasid_mapping(r, vmid, pasid) (r)->adev->gmc.gmc_funcs->emit_pasid_mapping((r), (vmid), (pasid))
-#define amdgpu_gmc_map_mtype(adev, flags) (adev)->gmc.gmc_funcs->map_mtype((adev),(flags))
#define amdgpu_gmc_get_vm_pde(adev, level, dst, flags) (adev)->gmc.gmc_funcs->get_vm_pde((adev), (level), (dst), (flags))
-#define amdgpu_gmc_get_vm_pte(adev, mapping, flags) (adev)->gmc.gmc_funcs->get_vm_pte((adev), (mapping), (flags))
+#define amdgpu_gmc_get_vm_pte(adev, vm, bo, vm_flags, pte_flags) \
+ ((adev)->gmc.gmc_funcs->get_vm_pte((adev), (vm), (bo), (vm_flags), \
+ (pte_flags)))
#define amdgpu_gmc_override_vm_pte_flags(adev, vm, addr, pte_flags) \
(adev)->gmc.gmc_funcs->override_vm_pte_flags \
((adev), (vm), (addr), (pte_flags))
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_job.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_job.c
index e6061d45f142..9b1c55115921 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_job.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_job.c
@@ -365,13 +365,6 @@ amdgpu_job_prepare_job(struct drm_sched_job *sched_job,
dev_err(ring->adev->dev, "Error getting VM ID (%d)\n", r);
goto error;
}
- /*
- * The VM structure might be released after the VMID is
- * assigned, we had multiple problems with people trying to use
- * the VM pointer so better set it to NULL.
- */
- if (!fence)
- job->vm = NULL;
return fence;
}
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_nbio.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_nbio.c
index e56ba93a8df6..a974265837f0 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_nbio.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_nbio.c
@@ -55,7 +55,8 @@ u64 amdgpu_nbio_get_pcie_replay_count(struct amdgpu_device *adev)
bool amdgpu_nbio_is_replay_cnt_supported(struct amdgpu_device *adev)
{
- if (amdgpu_sriov_vf(adev) || !adev->asic_funcs->get_pcie_replay_count ||
+ if (amdgpu_sriov_vf(adev) || !adev->asic_funcs ||
+ !adev->asic_funcs->get_pcie_replay_count ||
(!adev->nbio.funcs || !adev->nbio.funcs->get_pcie_replay_count))
return false;
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_object.h b/drivers/gpu/drm/amd/amdgpu/amdgpu_object.h
index c316920f3450..87523fcd4386 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_object.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_object.h
@@ -69,7 +69,7 @@ struct amdgpu_bo_va_mapping {
uint64_t last;
uint64_t __subtree_last;
uint64_t offset;
- uint64_t flags;
+ uint32_t flags;
};
/* User space allocated BO in a VM */
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ras.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_ras.c
index eb3c28669789..25bade9a5e95 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ras.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ras.c
@@ -2622,7 +2622,7 @@ static int amdgpu_ras_badpages_read(struct amdgpu_device *adev,
goto out;
}
- *bps = kmalloc(sizeof(struct ras_badpage) * data->count, GFP_KERNEL);
+ *bps = kmalloc_array(data->count, sizeof(struct ras_badpage), GFP_KERNEL);
if (!*bps) {
ret = -ENOMEM;
goto out;
@@ -2786,7 +2786,7 @@ static int amdgpu_ras_realloc_eh_data_space(struct amdgpu_device *adev,
unsigned int old_space = data->count + data->space_left;
unsigned int new_space = old_space + pages;
unsigned int align_space = ALIGN(new_space, 512);
- void *bps = kmalloc(align_space * sizeof(*data->bps), GFP_KERNEL);
+ void *bps = kmalloc_array(align_space, sizeof(*data->bps), GFP_KERNEL);
if (!bps) {
return -ENOMEM;
@@ -3363,7 +3363,6 @@ static void amdgpu_ras_do_page_retirement(struct work_struct *work)
page_retirement_dwork.work);
struct amdgpu_device *adev = con->adev;
struct ras_err_data err_data;
- unsigned long err_cnt;
/* If gpu reset is ongoing, delay retiring the bad pages */
if (amdgpu_in_reset(adev) || amdgpu_ras_in_recovery(adev)) {
@@ -3375,13 +3374,9 @@ static void amdgpu_ras_do_page_retirement(struct work_struct *work)
amdgpu_ras_error_data_init(&err_data);
amdgpu_umc_handle_bad_pages(adev, &err_data);
- err_cnt = err_data.err_addr_cnt;
amdgpu_ras_error_data_fini(&err_data);
- if (err_cnt && amdgpu_ras_is_rma(adev))
- amdgpu_ras_reset_gpu(adev);
-
amdgpu_ras_schedule_retirement_dwork(con,
AMDGPU_RAS_RETIRE_PAGE_INTERVAL);
}
@@ -3435,6 +3430,9 @@ static int amdgpu_ras_poison_creation_handler(struct amdgpu_device *adev,
if (total_detect_count)
schedule_delayed_work(&ras->page_retirement_dwork, 0);
+ if (amdgpu_ras_is_rma(adev) && atomic_cmpxchg(&ras->rma_in_recovery, 0, 1) == 0)
+ amdgpu_ras_reset_gpu(adev);
+
return 0;
}
@@ -3470,6 +3468,12 @@ static int amdgpu_ras_poison_consumption_handler(struct amdgpu_device *adev,
reset_flags |= msg.reset;
}
+ /*
+ * Try to ensure poison creation handler is completed first
+ * to set rma if bad page exceed threshold.
+ */
+ flush_delayed_work(&con->page_retirement_dwork);
+
/* for RMA, amdgpu_ras_poison_creation_handler will trigger gpu reset */
if (reset_flags && !amdgpu_ras_is_rma(adev)) {
if (reset_flags & AMDGPU_RAS_GPU_RESET_MODE1_RESET)
@@ -3479,8 +3483,6 @@ static int amdgpu_ras_poison_consumption_handler(struct amdgpu_device *adev,
else
reset = reset_flags;
- flush_delayed_work(&con->page_retirement_dwork);
-
con->gpu_reset_flags |= reset;
amdgpu_ras_reset_gpu(adev);
@@ -3648,6 +3650,7 @@ int amdgpu_ras_recovery_init(struct amdgpu_device *adev, bool init_bp_info)
mutex_init(&con->recovery_lock);
INIT_WORK(&con->recovery_work, amdgpu_ras_do_recovery);
atomic_set(&con->in_recovery, 0);
+ atomic_set(&con->rma_in_recovery, 0);
con->eeprom_control.bad_channel_bitmap = 0;
max_eeprom_records_count = amdgpu_ras_eeprom_max_record_count(&con->eeprom_control);
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ras.h b/drivers/gpu/drm/amd/amdgpu/amdgpu_ras.h
index 434e23c84962..ff63020f9c6c 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ras.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ras.h
@@ -522,6 +522,7 @@ struct amdgpu_ras {
/* gpu recovery */
struct work_struct recovery_work;
atomic_t in_recovery;
+ atomic_t rma_in_recovery;
struct amdgpu_device *adev;
/* error handler data */
struct ras_err_handler_data *eh_data;
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_reset.h b/drivers/gpu/drm/amd/amdgpu/amdgpu_reset.h
index 4d9b9701139b..3a806953338f 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_reset.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_reset.h
@@ -160,4 +160,15 @@ int amdgpu_reset_do_xgmi_reset_on_init(
bool amdgpu_reset_in_recovery(struct amdgpu_device *adev);
+static inline void amdgpu_reset_set_dpc_status(struct amdgpu_device *adev,
+ bool status)
+{
+ adev->pcie_reset_ctx.occurs_dpc = status;
+}
+
+static inline bool amdgpu_reset_in_dpc(struct amdgpu_device *adev)
+{
+ return adev->pcie_reset_ctx.occurs_dpc;
+}
+
#endif
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_seq64.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_seq64.c
index d45ebfb642ca..a0b479d5fff1 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_seq64.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_seq64.c
@@ -67,9 +67,9 @@ static inline u64 amdgpu_seq64_get_va_base(struct amdgpu_device *adev)
int amdgpu_seq64_map(struct amdgpu_device *adev, struct amdgpu_vm *vm,
struct amdgpu_bo_va **bo_va)
{
- u64 seq64_addr, va_flags;
struct amdgpu_bo *bo;
struct drm_exec exec;
+ u64 seq64_addr;
int r;
bo = adev->seq64.sbo;
@@ -94,9 +94,9 @@ int amdgpu_seq64_map(struct amdgpu_device *adev, struct amdgpu_vm *vm,
seq64_addr = amdgpu_seq64_get_va_base(adev) & AMDGPU_GMC_HOLE_MASK;
- va_flags = amdgpu_gem_va_map_flags(adev, AMDGPU_VM_PAGE_READABLE | AMDGPU_VM_MTYPE_UC);
- r = amdgpu_vm_bo_map(adev, *bo_va, seq64_addr, 0, AMDGPU_VA_RESERVED_SEQ64_SIZE,
- va_flags);
+ r = amdgpu_vm_bo_map(adev, *bo_va, seq64_addr, 0,
+ AMDGPU_VA_RESERVED_SEQ64_SIZE,
+ AMDGPU_VM_PAGE_READABLE | AMDGPU_VM_MTYPE_UC);
if (r) {
DRM_ERROR("failed to do bo_map on userq sem, err=%d\n", r);
amdgpu_vm_bo_del(adev, *bo_va);
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
index f1f67521c29c..b497a6714138 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
@@ -92,6 +92,7 @@ MODULE_FIRMWARE(FIRMWARE_VCN5_0_0);
MODULE_FIRMWARE(FIRMWARE_VCN5_0_1);
static void amdgpu_vcn_idle_work_handler(struct work_struct *work);
+static void amdgpu_vcn_reg_dump_fini(struct amdgpu_device *adev);
int amdgpu_vcn_early_init(struct amdgpu_device *adev, int i)
{
@@ -285,6 +286,10 @@ int amdgpu_vcn_sw_fini(struct amdgpu_device *adev, int i)
amdgpu_ucode_release(&adev->vcn.inst[0].fw);
adev->vcn.inst[i].fw = NULL;
}
+
+ if (adev->vcn.reg_list)
+ amdgpu_vcn_reg_dump_fini(adev);
+
mutex_destroy(&adev->vcn.inst[i].vcn_pg_lock);
mutex_destroy(&adev->vcn.inst[i].vcn1_jpeg1_workaround);
@@ -1527,3 +1532,85 @@ int amdgpu_vcn_ring_reset(struct amdgpu_ring *ring,
return amdgpu_vcn_reset_engine(adev, ring->me);
}
+
+int amdgpu_vcn_reg_dump_init(struct amdgpu_device *adev,
+ const struct amdgpu_hwip_reg_entry *reg, u32 count)
+{
+ adev->vcn.ip_dump = kcalloc(adev->vcn.num_vcn_inst * count,
+ sizeof(uint32_t), GFP_KERNEL);
+ if (!adev->vcn.ip_dump)
+ return -ENOMEM;
+ adev->vcn.reg_list = reg;
+ adev->vcn.reg_count = count;
+
+ return 0;
+}
+
+static void amdgpu_vcn_reg_dump_fini(struct amdgpu_device *adev)
+{
+ kfree(adev->vcn.ip_dump);
+ adev->vcn.reg_list = NULL;
+ adev->vcn.reg_count = 0;
+}
+
+void amdgpu_vcn_dump_ip_state(struct amdgpu_ip_block *ip_block)
+{
+ struct amdgpu_device *adev = ip_block->adev;
+ int i, j;
+ bool is_powered;
+ u32 inst_off;
+
+ if (!adev->vcn.ip_dump)
+ return;
+
+ for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
+ if (adev->vcn.harvest_config & (1 << i))
+ continue;
+
+ inst_off = i * adev->vcn.reg_count;
+ /* mmUVD_POWER_STATUS is always readable and is the first in reg_list */
+ adev->vcn.ip_dump[inst_off] =
+ RREG32(SOC15_REG_ENTRY_OFFSET_INST(adev->vcn.reg_list[0], i));
+ is_powered = (adev->vcn.ip_dump[inst_off] &
+ UVD_POWER_STATUS__UVD_POWER_STATUS_TILES_OFF) !=
+ UVD_POWER_STATUS__UVD_POWER_STATUS_TILES_OFF;
+
+ if (is_powered)
+ for (j = 1; j < adev->vcn.reg_count; j++)
+ adev->vcn.ip_dump[inst_off + j] =
+ RREG32(SOC15_REG_ENTRY_OFFSET_INST(adev->vcn.reg_list[j], i));
+ }
+}
+
+void amdgpu_vcn_print_ip_state(struct amdgpu_ip_block *ip_block, struct drm_printer *p)
+{
+ struct amdgpu_device *adev = ip_block->adev;
+ int i, j;
+ bool is_powered;
+ u32 inst_off;
+
+ if (!adev->vcn.ip_dump)
+ return;
+
+ drm_printf(p, "num_instances:%d\n", adev->vcn.num_vcn_inst);
+ for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
+ if (adev->vcn.harvest_config & (1 << i)) {
+ drm_printf(p, "\nHarvested Instance:VCN%d Skipping dump\n", i);
+ continue;
+ }
+
+ inst_off = i * adev->vcn.reg_count;
+ is_powered = (adev->vcn.ip_dump[inst_off] &
+ UVD_POWER_STATUS__UVD_POWER_STATUS_TILES_OFF) !=
+ UVD_POWER_STATUS__UVD_POWER_STATUS_TILES_OFF;
+
+ if (is_powered) {
+ drm_printf(p, "\nActive Instance:VCN%d\n", i);
+ for (j = 0; j < adev->vcn.reg_count; j++)
+ drm_printf(p, "%-50s \t 0x%08x\n", adev->vcn.reg_list[j].reg_name,
+ adev->vcn.ip_dump[inst_off + j]);
+ } else {
+ drm_printf(p, "\nInactive Instance:VCN%d\n", i);
+ }
+ }
+}
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.h b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.h
index 0bc0a94d7cf0..b3fb1d0e43fc 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.h
@@ -237,6 +237,8 @@
#define AMDGPU_DRM_KEY_INJECT_WORKAROUND_VCNFW_ASD_HANDSHAKING 2
+struct amdgpu_hwip_reg_entry;
+
enum amdgpu_vcn_caps {
AMDGPU_VCN_RRMT_ENABLED,
};
@@ -362,6 +364,8 @@ struct amdgpu_vcn {
bool workload_profile_active;
struct mutex workload_profile_mutex;
+ u32 reg_count;
+ const struct amdgpu_hwip_reg_entry *reg_list;
};
struct amdgpu_fw_shared_rb_ptrs_struct {
@@ -557,4 +561,8 @@ int vcn_set_powergating_state(struct amdgpu_ip_block *ip_block,
int amdgpu_vcn_ring_reset(struct amdgpu_ring *ring,
unsigned int vmid,
struct amdgpu_fence *guilty_fence);
+int amdgpu_vcn_reg_dump_init(struct amdgpu_device *adev,
+ const struct amdgpu_hwip_reg_entry *reg, u32 count);
+void amdgpu_vcn_dump_ip_state(struct amdgpu_ip_block *ip_block);
+void amdgpu_vcn_print_ip_state(struct amdgpu_ip_block *ip_block, struct drm_printer *p);
#endif
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c
index 5cacf5717016..39b4250ede0f 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c
@@ -1332,13 +1332,14 @@ int amdgpu_vm_bo_update(struct amdgpu_device *adev, struct amdgpu_bo_va *bo_va,
/* normally,bo_va->flags only contians READABLE and WIRTEABLE bit go here
* but in case of something, we filter the flags in first place
*/
- if (!(mapping->flags & AMDGPU_PTE_READABLE))
+ if (!(mapping->flags & AMDGPU_VM_PAGE_READABLE))
update_flags &= ~AMDGPU_PTE_READABLE;
- if (!(mapping->flags & AMDGPU_PTE_WRITEABLE))
+ if (!(mapping->flags & AMDGPU_VM_PAGE_WRITEABLE))
update_flags &= ~AMDGPU_PTE_WRITEABLE;
/* Apply ASIC specific mapping flags */
- amdgpu_gmc_get_vm_pte(adev, mapping, &update_flags);
+ amdgpu_gmc_get_vm_pte(adev, vm, bo, mapping->flags,
+ &update_flags);
trace_amdgpu_vm_bo_update(mapping);
@@ -1479,7 +1480,7 @@ static void amdgpu_vm_free_mapping(struct amdgpu_device *adev,
struct amdgpu_bo_va_mapping *mapping,
struct dma_fence *fence)
{
- if (mapping->flags & AMDGPU_PTE_PRT_FLAG(adev))
+ if (mapping->flags & AMDGPU_VM_PAGE_PRT)
amdgpu_vm_add_prt_cb(adev, fence);
kfree(mapping);
}
@@ -1758,7 +1759,7 @@ static void amdgpu_vm_bo_insert_map(struct amdgpu_device *adev,
list_add(&mapping->list, &bo_va->invalids);
amdgpu_vm_it_insert(mapping, &vm->va);
- if (mapping->flags & AMDGPU_PTE_PRT_FLAG(adev))
+ if (mapping->flags & AMDGPU_VM_PAGE_PRT)
amdgpu_vm_prt_get(adev);
if (amdgpu_vm_is_bo_always_valid(vm, bo) && !bo_va->base.moved)
@@ -1818,7 +1819,7 @@ static int amdgpu_vm_verify_parameters(struct amdgpu_device *adev,
int amdgpu_vm_bo_map(struct amdgpu_device *adev,
struct amdgpu_bo_va *bo_va,
uint64_t saddr, uint64_t offset,
- uint64_t size, uint64_t flags)
+ uint64_t size, uint32_t flags)
{
struct amdgpu_bo_va_mapping *mapping, *tmp;
struct amdgpu_bo *bo = bo_va->base.bo;
@@ -1877,7 +1878,7 @@ int amdgpu_vm_bo_map(struct amdgpu_device *adev,
int amdgpu_vm_bo_replace_map(struct amdgpu_device *adev,
struct amdgpu_bo_va *bo_va,
uint64_t saddr, uint64_t offset,
- uint64_t size, uint64_t flags)
+ uint64_t size, uint32_t flags)
{
struct amdgpu_bo_va_mapping *mapping;
struct amdgpu_bo *bo = bo_va->base.bo;
@@ -2734,7 +2735,7 @@ void amdgpu_vm_fini(struct amdgpu_device *adev, struct amdgpu_vm *vm)
dma_fence_put(vm->last_tlb_flush);
list_for_each_entry_safe(mapping, tmp, &vm->freed, list) {
- if (mapping->flags & AMDGPU_PTE_PRT_FLAG(adev) && prt_fini_needed) {
+ if (mapping->flags & AMDGPU_VM_PAGE_PRT && prt_fini_needed) {
amdgpu_vm_prt_fini(adev, vm);
prt_fini_needed = false;
}
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.h b/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.h
index fd086efd8457..3b4fa3246675 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.h
@@ -538,11 +538,11 @@ struct amdgpu_bo_va *amdgpu_vm_bo_add(struct amdgpu_device *adev,
int amdgpu_vm_bo_map(struct amdgpu_device *adev,
struct amdgpu_bo_va *bo_va,
uint64_t addr, uint64_t offset,
- uint64_t size, uint64_t flags);
+ uint64_t size, uint32_t flags);
int amdgpu_vm_bo_replace_map(struct amdgpu_device *adev,
struct amdgpu_bo_va *bo_va,
uint64_t addr, uint64_t offset,
- uint64_t size, uint64_t flags);
+ uint64_t size, uint32_t flags);
int amdgpu_vm_bo_unmap(struct amdgpu_device *adev,
struct amdgpu_bo_va *bo_va,
uint64_t addr);
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_xcp.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_xcp.c
index c417f8689220..699acc1b46b5 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_xcp.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_xcp.c
@@ -406,6 +406,7 @@ void amdgpu_xcp_dev_unplug(struct amdgpu_device *adev)
p_ddev->primary->dev = adev->xcp_mgr->xcp[i].pdev;
p_ddev->driver = adev->xcp_mgr->xcp[i].driver;
p_ddev->vma_offset_manager = adev->xcp_mgr->xcp[i].vma_offset_manager;
+ amdgpu_xcp_drm_dev_free(p_ddev);
}
}
diff --git a/drivers/gpu/drm/amd/amdgpu/gmc_v10_0.c b/drivers/gpu/drm/amd/amdgpu/gmc_v10_0.c
index 7923f491cf73..7031dd8c3c5e 100644
--- a/drivers/gpu/drm/amd/amdgpu/gmc_v10_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gmc_v10_0.c
@@ -466,24 +466,6 @@ static void gmc_v10_0_emit_pasid_mapping(struct amdgpu_ring *ring, unsigned int
* 0 valid
*/
-static uint64_t gmc_v10_0_map_mtype(struct amdgpu_device *adev, uint32_t flags)
-{
- switch (flags) {
- case AMDGPU_VM_MTYPE_DEFAULT:
- return AMDGPU_PTE_MTYPE_NV10(0ULL, MTYPE_NC);
- case AMDGPU_VM_MTYPE_NC:
- return AMDGPU_PTE_MTYPE_NV10(0ULL, MTYPE_NC);
- case AMDGPU_VM_MTYPE_WC:
- return AMDGPU_PTE_MTYPE_NV10(0ULL, MTYPE_WC);
- case AMDGPU_VM_MTYPE_CC:
- return AMDGPU_PTE_MTYPE_NV10(0ULL, MTYPE_CC);
- case AMDGPU_VM_MTYPE_UC:
- return AMDGPU_PTE_MTYPE_NV10(0ULL, MTYPE_UC);
- default:
- return AMDGPU_PTE_MTYPE_NV10(0ULL, MTYPE_NC);
- }
-}
-
static void gmc_v10_0_get_vm_pde(struct amdgpu_device *adev, int level,
uint64_t *addr, uint64_t *flags)
{
@@ -508,21 +490,39 @@ static void gmc_v10_0_get_vm_pde(struct amdgpu_device *adev, int level,
}
static void gmc_v10_0_get_vm_pte(struct amdgpu_device *adev,
- struct amdgpu_bo_va_mapping *mapping,
+ struct amdgpu_vm *vm,
+ struct amdgpu_bo *bo,
+ uint32_t vm_flags,
uint64_t *flags)
{
- struct amdgpu_bo *bo = mapping->bo_va->base.bo;
-
- *flags &= ~AMDGPU_PTE_EXECUTABLE;
- *flags |= mapping->flags & AMDGPU_PTE_EXECUTABLE;
+ if (vm_flags & AMDGPU_VM_PAGE_EXECUTABLE)
+ *flags |= AMDGPU_PTE_EXECUTABLE;
+ else
+ *flags &= ~AMDGPU_PTE_EXECUTABLE;
- *flags &= ~AMDGPU_PTE_MTYPE_NV10_MASK;
- *flags |= (mapping->flags & AMDGPU_PTE_MTYPE_NV10_MASK);
+ switch (vm_flags & AMDGPU_VM_MTYPE_MASK) {
+ case AMDGPU_VM_MTYPE_DEFAULT:
+ case AMDGPU_VM_MTYPE_NC:
+ default:
+ *flags = AMDGPU_PTE_MTYPE_NV10(*flags, MTYPE_NC);
+ break;
+ case AMDGPU_VM_MTYPE_WC:
+ *flags = AMDGPU_PTE_MTYPE_NV10(*flags, MTYPE_WC);
+ break;
+ case AMDGPU_VM_MTYPE_CC:
+ *flags = AMDGPU_PTE_MTYPE_NV10(*flags, MTYPE_CC);
+ break;
+ case AMDGPU_VM_MTYPE_UC:
+ *flags = AMDGPU_PTE_MTYPE_NV10(*flags, MTYPE_UC);
+ break;
+ }
- *flags &= ~AMDGPU_PTE_NOALLOC;
- *flags |= (mapping->flags & AMDGPU_PTE_NOALLOC);
+ if (vm_flags & AMDGPU_VM_PAGE_NOALLOC)
+ *flags |= AMDGPU_PTE_NOALLOC;
+ else
+ *flags &= ~AMDGPU_PTE_NOALLOC;
- if (mapping->flags & AMDGPU_PTE_PRT) {
+ if (vm_flags & AMDGPU_VM_PAGE_PRT) {
*flags |= AMDGPU_PTE_PRT;
*flags |= AMDGPU_PTE_SNOOPED;
*flags |= AMDGPU_PTE_LOG;
@@ -563,7 +563,6 @@ static const struct amdgpu_gmc_funcs gmc_v10_0_gmc_funcs = {
.flush_gpu_tlb_pasid = gmc_v10_0_flush_gpu_tlb_pasid,
.emit_flush_gpu_tlb = gmc_v10_0_emit_flush_gpu_tlb,
.emit_pasid_mapping = gmc_v10_0_emit_pasid_mapping,
- .map_mtype = gmc_v10_0_map_mtype,
.get_vm_pde = gmc_v10_0_get_vm_pde,
.get_vm_pte = gmc_v10_0_get_vm_pte,
.get_vbios_fb_size = gmc_v10_0_get_vbios_fb_size,
diff --git a/drivers/gpu/drm/amd/amdgpu/gmc_v11_0.c b/drivers/gpu/drm/amd/amdgpu/gmc_v11_0.c
index f15d691e9a20..93d2b0bbe641 100644
--- a/drivers/gpu/drm/amd/amdgpu/gmc_v11_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gmc_v11_0.c
@@ -430,24 +430,6 @@ static void gmc_v11_0_emit_pasid_mapping(struct amdgpu_ring *ring, unsigned int
* 0 valid
*/
-static uint64_t gmc_v11_0_map_mtype(struct amdgpu_device *adev, uint32_t flags)
-{
- switch (flags) {
- case AMDGPU_VM_MTYPE_DEFAULT:
- return AMDGPU_PTE_MTYPE_NV10(0ULL, MTYPE_NC);
- case AMDGPU_VM_MTYPE_NC:
- return AMDGPU_PTE_MTYPE_NV10(0ULL, MTYPE_NC);
- case AMDGPU_VM_MTYPE_WC:
- return AMDGPU_PTE_MTYPE_NV10(0ULL, MTYPE_WC);
- case AMDGPU_VM_MTYPE_CC:
- return AMDGPU_PTE_MTYPE_NV10(0ULL, MTYPE_CC);
- case AMDGPU_VM_MTYPE_UC:
- return AMDGPU_PTE_MTYPE_NV10(0ULL, MTYPE_UC);
- default:
- return AMDGPU_PTE_MTYPE_NV10(0ULL, MTYPE_NC);
- }
-}
-
static void gmc_v11_0_get_vm_pde(struct amdgpu_device *adev, int level,
uint64_t *addr, uint64_t *flags)
{
@@ -472,21 +454,39 @@ static void gmc_v11_0_get_vm_pde(struct amdgpu_device *adev, int level,
}
static void gmc_v11_0_get_vm_pte(struct amdgpu_device *adev,
- struct amdgpu_bo_va_mapping *mapping,
+ struct amdgpu_vm *vm,
+ struct amdgpu_bo *bo,
+ uint32_t vm_flags,
uint64_t *flags)
{
- struct amdgpu_bo *bo = mapping->bo_va->base.bo;
-
- *flags &= ~AMDGPU_PTE_EXECUTABLE;
- *flags |= mapping->flags & AMDGPU_PTE_EXECUTABLE;
+ if (vm_flags & AMDGPU_VM_PAGE_EXECUTABLE)
+ *flags |= AMDGPU_PTE_EXECUTABLE;
+ else
+ *flags &= ~AMDGPU_PTE_EXECUTABLE;
- *flags &= ~AMDGPU_PTE_MTYPE_NV10_MASK;
- *flags |= (mapping->flags & AMDGPU_PTE_MTYPE_NV10_MASK);
+ switch (vm_flags & AMDGPU_VM_MTYPE_MASK) {
+ case AMDGPU_VM_MTYPE_DEFAULT:
+ case AMDGPU_VM_MTYPE_NC:
+ default:
+ *flags = AMDGPU_PTE_MTYPE_NV10(*flags, MTYPE_NC);
+ break;
+ case AMDGPU_VM_MTYPE_WC:
+ *flags = AMDGPU_PTE_MTYPE_NV10(*flags, MTYPE_WC);
+ break;
+ case AMDGPU_VM_MTYPE_CC:
+ *flags = AMDGPU_PTE_MTYPE_NV10(*flags, MTYPE_CC);
+ break;
+ case AMDGPU_VM_MTYPE_UC:
+ *flags = AMDGPU_PTE_MTYPE_NV10(*flags, MTYPE_UC);
+ break;
+ }
- *flags &= ~AMDGPU_PTE_NOALLOC;
- *flags |= (mapping->flags & AMDGPU_PTE_NOALLOC);
+ if (vm_flags & AMDGPU_VM_PAGE_NOALLOC)
+ *flags |= AMDGPU_PTE_NOALLOC;
+ else
+ *flags &= ~AMDGPU_PTE_NOALLOC;
- if (mapping->flags & AMDGPU_PTE_PRT) {
+ if (vm_flags & AMDGPU_VM_PAGE_PRT) {
*flags |= AMDGPU_PTE_PRT;
*flags |= AMDGPU_PTE_SNOOPED;
*flags |= AMDGPU_PTE_LOG;
@@ -527,7 +527,6 @@ static const struct amdgpu_gmc_funcs gmc_v11_0_gmc_funcs = {
.flush_gpu_tlb_pasid = gmc_v11_0_flush_gpu_tlb_pasid,
.emit_flush_gpu_tlb = gmc_v11_0_emit_flush_gpu_tlb,
.emit_pasid_mapping = gmc_v11_0_emit_pasid_mapping,
- .map_mtype = gmc_v11_0_map_mtype,
.get_vm_pde = gmc_v11_0_get_vm_pde,
.get_vm_pte = gmc_v11_0_get_vm_pte,
.get_vbios_fb_size = gmc_v11_0_get_vbios_fb_size,
diff --git a/drivers/gpu/drm/amd/amdgpu/gmc_v12_0.c b/drivers/gpu/drm/amd/amdgpu/gmc_v12_0.c
index de763105fdfd..a0a5367f9dc4 100644
--- a/drivers/gpu/drm/amd/amdgpu/gmc_v12_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gmc_v12_0.c
@@ -453,20 +453,6 @@ static void gmc_v12_0_emit_pasid_mapping(struct amdgpu_ring *ring, unsigned vmid
* 0 valid
*/
-static uint64_t gmc_v12_0_map_mtype(struct amdgpu_device *adev, uint32_t flags)
-{
- switch (flags) {
- case AMDGPU_VM_MTYPE_DEFAULT:
- return AMDGPU_PTE_MTYPE_GFX12(0ULL, MTYPE_NC);
- case AMDGPU_VM_MTYPE_NC:
- return AMDGPU_PTE_MTYPE_GFX12(0ULL, MTYPE_NC);
- case AMDGPU_VM_MTYPE_UC:
- return AMDGPU_PTE_MTYPE_GFX12(0ULL, MTYPE_UC);
- default:
- return AMDGPU_PTE_MTYPE_GFX12(0ULL, MTYPE_NC);
- }
-}
-
static void gmc_v12_0_get_vm_pde(struct amdgpu_device *adev, int level,
uint64_t *addr, uint64_t *flags)
{
@@ -490,19 +476,35 @@ static void gmc_v12_0_get_vm_pde(struct amdgpu_device *adev, int level,
}
static void gmc_v12_0_get_vm_pte(struct amdgpu_device *adev,
- struct amdgpu_bo_va_mapping *mapping,
+ struct amdgpu_vm *vm,
+ struct amdgpu_bo *bo,
+ uint32_t vm_flags,
uint64_t *flags)
{
- struct amdgpu_bo *bo = mapping->bo_va->base.bo;
+ if (vm_flags & AMDGPU_VM_PAGE_EXECUTABLE)
+ *flags |= AMDGPU_PTE_EXECUTABLE;
+ else
+ *flags &= ~AMDGPU_PTE_EXECUTABLE;
- *flags &= ~AMDGPU_PTE_EXECUTABLE;
- *flags |= mapping->flags & AMDGPU_PTE_EXECUTABLE;
+ switch (vm_flags & AMDGPU_VM_MTYPE_MASK) {
+ case AMDGPU_VM_MTYPE_DEFAULT:
+ *flags = AMDGPU_PTE_MTYPE_GFX12(*flags, MTYPE_NC);
+ break;
+ case AMDGPU_VM_MTYPE_NC:
+ default:
+ *flags = AMDGPU_PTE_MTYPE_GFX12(*flags, MTYPE_NC);
+ break;
+ case AMDGPU_VM_MTYPE_UC:
+ *flags = AMDGPU_PTE_MTYPE_GFX12(*flags, MTYPE_UC);
+ break;
+ }
- *flags &= ~AMDGPU_PTE_MTYPE_GFX12_MASK;
- *flags |= (mapping->flags & AMDGPU_PTE_MTYPE_GFX12_MASK);
+ if (vm_flags & AMDGPU_VM_PAGE_NOALLOC)
+ *flags |= AMDGPU_PTE_NOALLOC;
+ else
+ *flags &= ~AMDGPU_PTE_NOALLOC;
- if (mapping->flags & AMDGPU_PTE_PRT_GFX12) {
- *flags |= AMDGPU_PTE_PRT_GFX12;
+ if (vm_flags & AMDGPU_VM_PAGE_PRT) {
*flags |= AMDGPU_PTE_SNOOPED;
*flags |= AMDGPU_PTE_SYSTEM;
*flags |= AMDGPU_PTE_IS_PTE;
@@ -543,7 +545,6 @@ static const struct amdgpu_gmc_funcs gmc_v12_0_gmc_funcs = {
.flush_gpu_tlb_pasid = gmc_v12_0_flush_gpu_tlb_pasid,
.emit_flush_gpu_tlb = gmc_v12_0_emit_flush_gpu_tlb,
.emit_pasid_mapping = gmc_v12_0_emit_pasid_mapping,
- .map_mtype = gmc_v12_0_map_mtype,
.get_vm_pde = gmc_v12_0_get_vm_pde,
.get_vm_pte = gmc_v12_0_get_vm_pte,
.get_vbios_fb_size = gmc_v12_0_get_vbios_fb_size,
diff --git a/drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c b/drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c
index 8030fcd64210..f6ad7911f1e6 100644
--- a/drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c
@@ -382,7 +382,9 @@ static void gmc_v6_0_get_vm_pde(struct amdgpu_device *adev, int level,
}
static void gmc_v6_0_get_vm_pte(struct amdgpu_device *adev,
- struct amdgpu_bo_va_mapping *mapping,
+ struct amdgpu_vm *vm,
+ struct amdgpu_bo *bo,
+ uint32_t vm_flags,
uint64_t *flags)
{
*flags &= ~AMDGPU_PTE_EXECUTABLE;
diff --git a/drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c b/drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c
index a8d5795084fc..93d7ccb7d013 100644
--- a/drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c
@@ -504,7 +504,9 @@ static void gmc_v7_0_get_vm_pde(struct amdgpu_device *adev, int level,
}
static void gmc_v7_0_get_vm_pte(struct amdgpu_device *adev,
- struct amdgpu_bo_va_mapping *mapping,
+ struct amdgpu_vm *vm,
+ struct amdgpu_bo *bo,
+ uint32_t vm_flags,
uint64_t *flags)
{
*flags &= ~AMDGPU_PTE_EXECUTABLE;
diff --git a/drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c b/drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c
index b45fa0cea9d2..c5e2a2c41e06 100644
--- a/drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c
@@ -716,11 +716,15 @@ static void gmc_v8_0_get_vm_pde(struct amdgpu_device *adev, int level,
}
static void gmc_v8_0_get_vm_pte(struct amdgpu_device *adev,
- struct amdgpu_bo_va_mapping *mapping,
+ struct amdgpu_vm *vm,
+ struct amdgpu_bo *bo,
+ uint32_t vm_flags,
uint64_t *flags)
{
- *flags &= ~AMDGPU_PTE_EXECUTABLE;
- *flags |= mapping->flags & AMDGPU_PTE_EXECUTABLE;
+ if (vm_flags & AMDGPU_VM_PAGE_EXECUTABLE)
+ *flags |= AMDGPU_PTE_EXECUTABLE;
+ else
+ *flags &= ~AMDGPU_PTE_EXECUTABLE;
*flags &= ~AMDGPU_PTE_PRT;
}
diff --git a/drivers/gpu/drm/amd/amdgpu/gmc_v9_0.c b/drivers/gpu/drm/amd/amdgpu/gmc_v9_0.c
index c4d69cf4e06c..8404695eb13f 100644
--- a/drivers/gpu/drm/amd/amdgpu/gmc_v9_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gmc_v9_0.c
@@ -1073,27 +1073,6 @@ static void gmc_v9_0_emit_pasid_mapping(struct amdgpu_ring *ring, unsigned int v
* 0 valid
*/
-static uint64_t gmc_v9_0_map_mtype(struct amdgpu_device *adev, uint32_t flags)
-
-{
- switch (flags) {
- case AMDGPU_VM_MTYPE_DEFAULT:
- return AMDGPU_PTE_MTYPE_VG10(0ULL, MTYPE_NC);
- case AMDGPU_VM_MTYPE_NC:
- return AMDGPU_PTE_MTYPE_VG10(0ULL, MTYPE_NC);
- case AMDGPU_VM_MTYPE_WC:
- return AMDGPU_PTE_MTYPE_VG10(0ULL, MTYPE_WC);
- case AMDGPU_VM_MTYPE_RW:
- return AMDGPU_PTE_MTYPE_VG10(0ULL, MTYPE_RW);
- case AMDGPU_VM_MTYPE_CC:
- return AMDGPU_PTE_MTYPE_VG10(0ULL, MTYPE_CC);
- case AMDGPU_VM_MTYPE_UC:
- return AMDGPU_PTE_MTYPE_VG10(0ULL, MTYPE_UC);
- default:
- return AMDGPU_PTE_MTYPE_VG10(0ULL, MTYPE_NC);
- }
-}
-
static void gmc_v9_0_get_vm_pde(struct amdgpu_device *adev, int level,
uint64_t *addr, uint64_t *flags)
{
@@ -1123,6 +1102,7 @@ static void gmc_v9_0_get_vm_pde(struct amdgpu_device *adev, int level,
static void gmc_v9_0_get_coherence_flags(struct amdgpu_device *adev,
struct amdgpu_vm *vm,
struct amdgpu_bo *bo,
+ uint32_t vm_flags,
uint64_t *flags)
{
struct amdgpu_device *bo_adev = amdgpu_ttm_adev(bo->tbo.bdev);
@@ -1236,25 +1216,43 @@ static void gmc_v9_0_get_coherence_flags(struct amdgpu_device *adev,
}
static void gmc_v9_0_get_vm_pte(struct amdgpu_device *adev,
- struct amdgpu_bo_va_mapping *mapping,
+ struct amdgpu_vm *vm,
+ struct amdgpu_bo *bo,
+ uint32_t vm_flags,
uint64_t *flags)
{
- struct amdgpu_bo *bo = mapping->bo_va->base.bo;
-
- *flags &= ~AMDGPU_PTE_EXECUTABLE;
- *flags |= mapping->flags & AMDGPU_PTE_EXECUTABLE;
+ if (vm_flags & AMDGPU_VM_PAGE_EXECUTABLE)
+ *flags |= AMDGPU_PTE_EXECUTABLE;
+ else
+ *flags &= ~AMDGPU_PTE_EXECUTABLE;
- *flags &= ~AMDGPU_PTE_MTYPE_VG10_MASK;
- *flags |= mapping->flags & AMDGPU_PTE_MTYPE_VG10_MASK;
+ switch (vm_flags & AMDGPU_VM_MTYPE_MASK) {
+ case AMDGPU_VM_MTYPE_DEFAULT:
+ case AMDGPU_VM_MTYPE_NC:
+ default:
+ *flags = AMDGPU_PTE_MTYPE_VG10(*flags, MTYPE_NC);
+ break;
+ case AMDGPU_VM_MTYPE_WC:
+ *flags |= AMDGPU_PTE_MTYPE_VG10(*flags, MTYPE_WC);
+ break;
+ case AMDGPU_VM_MTYPE_RW:
+ *flags |= AMDGPU_PTE_MTYPE_VG10(*flags, MTYPE_RW);
+ break;
+ case AMDGPU_VM_MTYPE_CC:
+ *flags |= AMDGPU_PTE_MTYPE_VG10(*flags, MTYPE_CC);
+ break;
+ case AMDGPU_VM_MTYPE_UC:
+ *flags |= AMDGPU_PTE_MTYPE_VG10(*flags, MTYPE_UC);
+ break;
+ }
- if (mapping->flags & AMDGPU_PTE_PRT) {
+ if (vm_flags & AMDGPU_VM_PAGE_PRT) {
*flags |= AMDGPU_PTE_PRT;
*flags &= ~AMDGPU_PTE_VALID;
}
if ((*flags & AMDGPU_PTE_VALID) && bo)
- gmc_v9_0_get_coherence_flags(adev, mapping->bo_va->base.vm, bo,
- flags);
+ gmc_v9_0_get_coherence_flags(adev, vm, bo, vm_flags, flags);
}
static void gmc_v9_0_override_vm_pte_flags(struct amdgpu_device *adev,
@@ -1391,7 +1389,6 @@ static const struct amdgpu_gmc_funcs gmc_v9_0_gmc_funcs = {
.flush_gpu_tlb_pasid = gmc_v9_0_flush_gpu_tlb_pasid,
.emit_flush_gpu_tlb = gmc_v9_0_emit_flush_gpu_tlb,
.emit_pasid_mapping = gmc_v9_0_emit_pasid_mapping,
- .map_mtype = gmc_v9_0_map_mtype,
.get_vm_pde = gmc_v9_0_get_vm_pde,
.get_vm_pte = gmc_v9_0_get_vm_pte,
.override_vm_pte_flags = gmc_v9_0_override_vm_pte_flags,
diff --git a/drivers/gpu/drm/amd/amdgpu/jpeg_v4_0_3.c b/drivers/gpu/drm/amd/amdgpu/jpeg_v4_0_3.c
index b86288a69e7b..a78144773fab 100644
--- a/drivers/gpu/drm/amd/amdgpu/jpeg_v4_0_3.c
+++ b/drivers/gpu/drm/amd/amdgpu/jpeg_v4_0_3.c
@@ -444,7 +444,7 @@ static int jpeg_v4_0_3_hw_fini(struct amdgpu_ip_block *ip_block)
ret = jpeg_v4_0_3_set_powergating_state(ip_block, AMD_PG_STATE_GATE);
}
- if (amdgpu_ras_is_supported(adev, AMDGPU_RAS_BLOCK__JPEG))
+ if (amdgpu_ras_is_supported(adev, AMDGPU_RAS_BLOCK__JPEG) && !amdgpu_sriov_vf(adev))
amdgpu_irq_put(adev, &adev->jpeg.inst->ras_poison_irq, 0);
return ret;
diff --git a/drivers/gpu/drm/amd/amdgpu/jpeg_v5_0_1.c b/drivers/gpu/drm/amd/amdgpu/jpeg_v5_0_1.c
index 54523dc1f702..a2d781898767 100644
--- a/drivers/gpu/drm/amd/amdgpu/jpeg_v5_0_1.c
+++ b/drivers/gpu/drm/amd/amdgpu/jpeg_v5_0_1.c
@@ -196,6 +196,14 @@ static int jpeg_v5_0_1_sw_init(struct amdgpu_ip_block *ip_block)
}
}
+ if (amdgpu_ras_is_supported(adev, AMDGPU_RAS_BLOCK__JPEG)) {
+ r = amdgpu_jpeg_ras_sw_init(adev);
+ if (r) {
+ dev_err(adev->dev, "Failed to initialize jpeg ras block!\n");
+ return r;
+ }
+ }
+
r = amdgpu_jpeg_reg_dump_init(adev, jpeg_reg_list_5_0_1, ARRAY_SIZE(jpeg_reg_list_5_0_1));
if (r)
return r;
@@ -1016,8 +1024,9 @@ static int jpeg_v5_0_1_aca_bank_parser(struct aca_handle *handle, struct aca_ban
/* reference to smu driver if header file */
static int jpeg_v5_0_1_err_codes[] = {
- 16, 17, 18, 19, 20, 21, 22, 23, /* JPEG[0-7][S|D] */
- 24, 25, 26, 27, 28, 29, 30, 31
+ 16, 17, 18, 19, 20, 21, 22, 23, /* JPEG[0-9][S|D] */
+ 24, 25, 26, 27, 28, 29, 30, 31,
+ 48, 49, 50, 51,
};
static bool jpeg_v5_0_1_aca_bank_is_valid(struct aca_handle *handle, struct aca_bank *bank,
@@ -1058,6 +1067,11 @@ static int jpeg_v5_0_1_ras_late_init(struct amdgpu_device *adev, struct ras_comm
if (r)
return r;
+ r = amdgpu_ras_bind_aca(adev, AMDGPU_RAS_BLOCK__JPEG,
+ &jpeg_v5_0_1_aca_info, NULL);
+ if (r)
+ goto late_fini;
+
if (amdgpu_ras_is_supported(adev, ras_block->block) &&
adev->jpeg.inst->ras_poison_irq.funcs) {
r = amdgpu_irq_get(adev, &adev->jpeg.inst->ras_poison_irq, 0);
@@ -1065,11 +1079,6 @@ static int jpeg_v5_0_1_ras_late_init(struct amdgpu_device *adev, struct ras_comm
goto late_fini;
}
- r = amdgpu_ras_bind_aca(adev, AMDGPU_RAS_BLOCK__JPEG,
- &jpeg_v5_0_1_aca_info, NULL);
- if (r)
- goto late_fini;
-
return 0;
late_fini:
diff --git a/drivers/gpu/drm/amd/amdgpu/mmhub_v3_0_1.c b/drivers/gpu/drm/amd/amdgpu/mmhub_v3_0_1.c
index 134c4ec10887..910337dc28d1 100644
--- a/drivers/gpu/drm/amd/amdgpu/mmhub_v3_0_1.c
+++ b/drivers/gpu/drm/amd/amdgpu/mmhub_v3_0_1.c
@@ -36,40 +36,47 @@
static const char *mmhub_client_ids_v3_0_1[][2] = {
[0][0] = "VMC",
+ [1][0] = "ISPXT",
+ [2][0] = "ISPIXT",
[4][0] = "DCEDMC",
[5][0] = "DCEVGA",
[6][0] = "MP0",
[7][0] = "MP1",
- [8][0] = "MPIO",
- [16][0] = "HDP",
- [17][0] = "LSDMA",
- [18][0] = "JPEG",
- [19][0] = "VCNU0",
- [21][0] = "VSCH",
- [22][0] = "VCNU1",
- [23][0] = "VCN1",
- [32+20][0] = "VCN0",
- [2][1] = "DBGUNBIO",
+ [8][0] = "MPM",
+ [12][0] = "ISPTNR",
+ [14][0] = "ISPCRD0",
+ [15][0] = "ISPCRD1",
+ [16][0] = "ISPCRD2",
+ [22][0] = "HDP",
+ [23][0] = "LSDMA",
+ [24][0] = "JPEG",
+ [27][0] = "VSCH",
+ [28][0] = "VCNU",
+ [29][0] = "VCN",
+ [1][1] = "ISPXT",
+ [2][1] = "ISPIXT",
[3][1] = "DCEDWB",
[4][1] = "DCEDMC",
[5][1] = "DCEVGA",
[6][1] = "MP0",
[7][1] = "MP1",
- [8][1] = "MPIO",
- [10][1] = "DBGU0",
- [11][1] = "DBGU1",
- [12][1] = "DBGU2",
- [13][1] = "DBGU3",
- [14][1] = "XDP",
- [15][1] = "OSSSYS",
- [16][1] = "HDP",
- [17][1] = "LSDMA",
- [18][1] = "JPEG",
- [19][1] = "VCNU0",
- [20][1] = "VCN0",
- [21][1] = "VSCH",
- [22][1] = "VCNU1",
- [23][1] = "VCN1",
+ [8][1] = "MPM",
+ [10][1] = "ISPMWR0",
+ [11][1] = "ISPMWR1",
+ [12][1] = "ISPTNR",
+ [13][1] = "ISPSWR",
+ [14][1] = "ISPCWR0",
+ [15][1] = "ISPCWR1",
+ [16][1] = "ISPCWR2",
+ [17][1] = "ISPCWR3",
+ [18][1] = "XDP",
+ [21][1] = "OSSSYS",
+ [22][1] = "HDP",
+ [23][1] = "LSDMA",
+ [24][1] = "JPEG",
+ [27][1] = "VSCH",
+ [28][1] = "VCNU",
+ [29][1] = "VCN",
};
static uint32_t mmhub_v3_0_1_get_invalidate_req(unsigned int vmid,
diff --git a/drivers/gpu/drm/amd/amdgpu/mmhub_v3_3.c b/drivers/gpu/drm/amd/amdgpu/mmhub_v3_3.c
index bc3d6c2fc87a..f6fc9778bc30 100644
--- a/drivers/gpu/drm/amd/amdgpu/mmhub_v3_3.c
+++ b/drivers/gpu/drm/amd/amdgpu/mmhub_v3_3.c
@@ -40,30 +40,129 @@
static const char *mmhub_client_ids_v3_3[][2] = {
[0][0] = "VMC",
+ [1][0] = "ISPXT",
+ [2][0] = "ISPIXT",
[4][0] = "DCEDMC",
[6][0] = "MP0",
[7][0] = "MP1",
[8][0] = "MPM",
+ [9][0] = "ISPPDPRD",
+ [10][0] = "ISPCSTATRD",
+ [11][0] = "ISPBYRPRD",
+ [12][0] = "ISPRGBPRD",
+ [13][0] = "ISPMCFPRD",
+ [14][0] = "ISPMCFPRD1",
+ [15][0] = "ISPYUVPRD",
+ [16][0] = "ISPMCSCRD",
+ [17][0] = "ISPGDCRD",
+ [18][0] = "ISPLMERD",
+ [22][0] = "ISPXT1",
+ [23][0] = "ISPIXT1",
[24][0] = "HDP",
[25][0] = "LSDMA",
[26][0] = "JPEG",
[27][0] = "VPE",
+ [28][0] = "VSCH",
[29][0] = "VCNU",
[30][0] = "VCN",
+ [1][1] = "ISPXT",
+ [2][1] = "ISPIXT",
[3][1] = "DCEDWB",
[4][1] = "DCEDMC",
+ [5][1] = "ISPCSISWR",
[6][1] = "MP0",
[7][1] = "MP1",
[8][1] = "MPM",
+ [9][1] = "ISPPDPWR",
+ [10][1] = "ISPCSTATWR",
+ [11][1] = "ISPBYRPWR",
+ [12][1] = "ISPRGBPWR",
+ [13][1] = "ISPMCFPWR",
+ [14][1] = "ISPMWR0",
+ [15][1] = "ISPYUVPWR",
+ [16][1] = "ISPMCSCWR",
+ [17][1] = "ISPGDCWR",
+ [18][1] = "ISPLMEWR",
+ [20][1] = "ISPMWR2",
[21][1] = "OSSSYS",
+ [22][1] = "ISPXT1",
+ [23][1] = "ISPIXT1",
[24][1] = "HDP",
[25][1] = "LSDMA",
[26][1] = "JPEG",
[27][1] = "VPE",
+ [28][1] = "VSCH",
[29][1] = "VCNU",
[30][1] = "VCN",
};
+static const char *mmhub_client_ids_v3_3_1[][2] = {
+ [0][0] = "VMC",
+ [4][0] = "DCEDMC",
+ [6][0] = "MP0",
+ [7][0] = "MP1",
+ [8][0] = "MPM",
+ [24][0] = "HDP",
+ [25][0] = "LSDMA",
+ [26][0] = "JPEG0",
+ [27][0] = "VPE0",
+ [28][0] = "VSCH",
+ [29][0] = "VCNU0",
+ [30][0] = "VCN0",
+ [32+1][0] = "ISPXT",
+ [32+2][0] = "ISPIXT",
+ [32+9][0] = "ISPPDPRD",
+ [32+10][0] = "ISPCSTATRD",
+ [32+11][0] = "ISPBYRPRD",
+ [32+12][0] = "ISPRGBPRD",
+ [32+13][0] = "ISPMCFPRD",
+ [32+14][0] = "ISPMCFPRD1",
+ [32+15][0] = "ISPYUVPRD",
+ [32+16][0] = "ISPMCSCRD",
+ [32+17][0] = "ISPGDCRD",
+ [32+18][0] = "ISPLMERD",
+ [32+22][0] = "ISPXT1",
+ [32+23][0] = "ISPIXT1",
+ [32+26][0] = "JPEG1",
+ [32+27][0] = "VPE1",
+ [32+29][0] = "VCNU1",
+ [32+30][0] = "VCN1",
+ [3][1] = "DCEDWB",
+ [4][1] = "DCEDMC",
+ [6][1] = "MP0",
+ [7][1] = "MP1",
+ [8][1] = "MPM",
+ [21][1] = "OSSSYS",
+ [24][1] = "HDP",
+ [25][1] = "LSDMA",
+ [26][1] = "JPEG0",
+ [27][1] = "VPE0",
+ [28][1] = "VSCH",
+ [29][1] = "VCNU0",
+ [30][1] = "VCN0",
+ [32+1][1] = "ISPXT",
+ [32+2][1] = "ISPIXT",
+ [32+5][1] = "ISPCSISWR",
+ [32+9][1] = "ISPPDPWR",
+ [32+10][1] = "ISPCSTATWR",
+ [32+11][1] = "ISPBYRPWR",
+ [32+12][1] = "ISPRGBPWR",
+ [32+13][1] = "ISPMCFPWR",
+ [32+14][1] = "ISPMWR0",
+ [32+15][1] = "ISPYUVPWR",
+ [32+16][1] = "ISPMCSCWR",
+ [32+17][1] = "ISPGDCWR",
+ [32+18][1] = "ISPLMEWR",
+ [32+19][1] = "ISPMWR1",
+ [32+20][1] = "ISPMWR2",
+ [32+22][1] = "ISPXT1",
+ [32+23][1] = "ISPIXT1",
+ [32+26][1] = "JPEG1",
+ [32+27][1] = "VPE1",
+ [32+29][1] = "VCNU1",
+ [32+30][1] = "VCN1",
+};
+
static uint32_t mmhub_v3_3_get_invalidate_req(unsigned int vmid,
uint32_t flush_type)
{
@@ -102,12 +201,16 @@ mmhub_v3_3_print_l2_protection_fault_status(struct amdgpu_device *adev,
switch (amdgpu_ip_version(adev, MMHUB_HWIP, 0)) {
case IP_VERSION(3, 3, 0):
- case IP_VERSION(3, 3, 1):
case IP_VERSION(3, 3, 2):
mmhub_cid = cid < ARRAY_SIZE(mmhub_client_ids_v3_3) ?
mmhub_client_ids_v3_3[cid][rw] :
cid == 0x140 ? "UMSCH" : NULL;
break;
+ case IP_VERSION(3, 3, 1):
+ mmhub_cid = cid < ARRAY_SIZE(mmhub_client_ids_v3_3_1) ?
+ mmhub_client_ids_v3_3_1[cid][rw] :
+ cid == 0x140 ? "UMSCH" : NULL;
+ break;
default:
mmhub_cid = NULL;
break;
diff --git a/drivers/gpu/drm/amd/amdgpu/sdma_v7_0.c b/drivers/gpu/drm/amd/amdgpu/sdma_v7_0.c
index b8b06d4c5882..326ecc8d37d2 100644
--- a/drivers/gpu/drm/amd/amdgpu/sdma_v7_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/sdma_v7_0.c
@@ -1353,7 +1353,7 @@ static int sdma_v7_0_sw_init(struct amdgpu_ip_block *ip_block)
switch (amdgpu_ip_version(adev, SDMA0_HWIP, 0)) {
case IP_VERSION(7, 0, 0):
case IP_VERSION(7, 0, 1):
- if ((adev->sdma.instance[0].fw_version >= 7836028) && !adev->sdma.disable_uq)
+ if ((adev->sdma.instance[0].fw_version >= 7966358) && !adev->sdma.disable_uq)
adev->userq_funcs[AMDGPU_HW_IP_DMA] = &userq_mes_funcs;
break;
default:
diff --git a/drivers/gpu/drm/amd/amdgpu/vcn_v2_0.c b/drivers/gpu/drm/amd/amdgpu/vcn_v2_0.c
index d1481e6d57ec..b115137ab2d6 100644
--- a/drivers/gpu/drm/amd/amdgpu/vcn_v2_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/vcn_v2_0.c
@@ -136,8 +136,6 @@ static int vcn_v2_0_sw_init(struct amdgpu_ip_block *ip_block)
{
struct amdgpu_ring *ring;
int i, r;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_2_0);
- uint32_t *ptr;
struct amdgpu_device *adev = ip_block->adev;
volatile struct amdgpu_fw_shared *fw_shared;
@@ -232,14 +230,9 @@ static int vcn_v2_0_sw_init(struct amdgpu_ip_block *ip_block)
if (amdgpu_vcnfw_log)
amdgpu_vcn_fwlog_init(adev->vcn.inst);
- /* Allocate memory for VCN IP Dump buffer */
- ptr = kcalloc(adev->vcn.num_vcn_inst * reg_count, sizeof(uint32_t), GFP_KERNEL);
- if (!ptr) {
- DRM_ERROR("Failed to allocate memory for VCN IP Dump\n");
- adev->vcn.ip_dump = NULL;
- } else {
- adev->vcn.ip_dump = ptr;
- }
+ r = amdgpu_vcn_reg_dump_init(adev, vcn_reg_list_2_0, ARRAY_SIZE(vcn_reg_list_2_0));
+ if (r)
+ return r;
r = amdgpu_vcn_sysfs_reset_mask_init(adev);
if (r)
@@ -276,8 +269,6 @@ static int vcn_v2_0_sw_fini(struct amdgpu_ip_block *ip_block)
r = amdgpu_vcn_sw_fini(adev, 0);
- kfree(adev->vcn.ip_dump);
-
return r;
}
@@ -2101,66 +2092,6 @@ static int vcn_v2_0_start_sriov(struct amdgpu_device *adev)
return vcn_v2_0_start_mmsch(adev, &adev->virt.mm_table);
}
-static void vcn_v2_0_print_ip_state(struct amdgpu_ip_block *ip_block, struct drm_printer *p)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_2_0);
- uint32_t inst_off, is_powered;
-
- if (!adev->vcn.ip_dump)
- return;
-
- drm_printf(p, "num_instances:%d\n", adev->vcn.num_vcn_inst);
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i)) {
- drm_printf(p, "\nHarvested Instance:VCN%d Skipping dump\n", i);
- continue;
- }
-
- inst_off = i * reg_count;
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered) {
- drm_printf(p, "\nActive Instance:VCN%d\n", i);
- for (j = 0; j < reg_count; j++)
- drm_printf(p, "%-50s \t 0x%08x\n", vcn_reg_list_2_0[j].reg_name,
- adev->vcn.ip_dump[inst_off + j]);
- } else {
- drm_printf(p, "\nInactive Instance:VCN%d\n", i);
- }
- }
-}
-
-static void vcn_v2_0_dump_ip_state(struct amdgpu_ip_block *ip_block)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- bool is_powered;
- uint32_t inst_off;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_2_0);
-
- if (!adev->vcn.ip_dump)
- return;
-
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i))
- continue;
-
- inst_off = i * reg_count;
- /* mmUVD_POWER_STATUS is always readable and is first element of the array */
- adev->vcn.ip_dump[inst_off] = RREG32_SOC15(VCN, i, mmUVD_POWER_STATUS);
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered)
- for (j = 1; j < reg_count; j++)
- adev->vcn.ip_dump[inst_off + j] =
- RREG32(SOC15_REG_ENTRY_OFFSET_INST(vcn_reg_list_2_0[j], i));
- }
-}
-
static const struct amd_ip_funcs vcn_v2_0_ip_funcs = {
.name = "vcn_v2_0",
.early_init = vcn_v2_0_early_init,
@@ -2174,8 +2105,8 @@ static const struct amd_ip_funcs vcn_v2_0_ip_funcs = {
.wait_for_idle = vcn_v2_0_wait_for_idle,
.set_clockgating_state = vcn_v2_0_set_clockgating_state,
.set_powergating_state = vcn_set_powergating_state,
- .dump_ip_state = vcn_v2_0_dump_ip_state,
- .print_ip_state = vcn_v2_0_print_ip_state,
+ .dump_ip_state = amdgpu_vcn_dump_ip_state,
+ .print_ip_state = amdgpu_vcn_print_ip_state,
};
static const struct amdgpu_ring_funcs vcn_v2_0_dec_ring_vm_funcs = {
diff --git a/drivers/gpu/drm/amd/amdgpu/vcn_v2_5.c b/drivers/gpu/drm/amd/amdgpu/vcn_v2_5.c
index d7b2668ab0d9..3a7c137a83ef 100644
--- a/drivers/gpu/drm/amd/amdgpu/vcn_v2_5.c
+++ b/drivers/gpu/drm/amd/amdgpu/vcn_v2_5.c
@@ -297,8 +297,6 @@ static int vcn_v2_5_sw_init(struct amdgpu_ip_block *ip_block)
{
struct amdgpu_ring *ring;
int i, j, r;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_2_5);
- uint32_t *ptr;
struct amdgpu_device *adev = ip_block->adev;
for (j = 0; j < adev->vcn.num_vcn_inst; j++) {
@@ -423,14 +421,9 @@ static int vcn_v2_5_sw_init(struct amdgpu_ip_block *ip_block)
if (r)
return r;
- /* Allocate memory for VCN IP Dump buffer */
- ptr = kcalloc(adev->vcn.num_vcn_inst * reg_count, sizeof(uint32_t), GFP_KERNEL);
- if (!ptr) {
- DRM_ERROR("Failed to allocate memory for VCN IP Dump\n");
- adev->vcn.ip_dump = NULL;
- } else {
- adev->vcn.ip_dump = ptr;
- }
+ r = amdgpu_vcn_reg_dump_init(adev, vcn_reg_list_2_5, ARRAY_SIZE(vcn_reg_list_2_5));
+ if (r)
+ return r;
r = amdgpu_vcn_sysfs_reset_mask_init(adev);
if (r)
@@ -477,8 +470,6 @@ static int vcn_v2_5_sw_fini(struct amdgpu_ip_block *ip_block)
return r;
}
- kfree(adev->vcn.ip_dump);
-
return 0;
}
@@ -2133,66 +2124,6 @@ static void vcn_v2_5_set_irq_funcs(struct amdgpu_device *adev)
}
}
-static void vcn_v2_5_print_ip_state(struct amdgpu_ip_block *ip_block, struct drm_printer *p)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_2_5);
- uint32_t inst_off, is_powered;
-
- if (!adev->vcn.ip_dump)
- return;
-
- drm_printf(p, "num_instances:%d\n", adev->vcn.num_vcn_inst);
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i)) {
- drm_printf(p, "\nHarvested Instance:VCN%d Skipping dump\n", i);
- continue;
- }
-
- inst_off = i * reg_count;
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered) {
- drm_printf(p, "\nActive Instance:VCN%d\n", i);
- for (j = 0; j < reg_count; j++)
- drm_printf(p, "%-50s \t 0x%08x\n", vcn_reg_list_2_5[j].reg_name,
- adev->vcn.ip_dump[inst_off + j]);
- } else {
- drm_printf(p, "\nInactive Instance:VCN%d\n", i);
- }
- }
-}
-
-static void vcn_v2_5_dump_ip_state(struct amdgpu_ip_block *ip_block)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- bool is_powered;
- uint32_t inst_off;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_2_5);
-
- if (!adev->vcn.ip_dump)
- return;
-
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i))
- continue;
-
- inst_off = i * reg_count;
- /* mmUVD_POWER_STATUS is always readable and is first element of the array */
- adev->vcn.ip_dump[inst_off] = RREG32_SOC15(VCN, i, mmUVD_POWER_STATUS);
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered)
- for (j = 1; j < reg_count; j++)
- adev->vcn.ip_dump[inst_off + j] =
- RREG32(SOC15_REG_ENTRY_OFFSET_INST(vcn_reg_list_2_5[j], i));
- }
-}
-
static const struct amd_ip_funcs vcn_v2_5_ip_funcs = {
.name = "vcn_v2_5",
.early_init = vcn_v2_5_early_init,
@@ -2206,8 +2137,8 @@ static const struct amd_ip_funcs vcn_v2_5_ip_funcs = {
.wait_for_idle = vcn_v2_5_wait_for_idle,
.set_clockgating_state = vcn_v2_5_set_clockgating_state,
.set_powergating_state = vcn_set_powergating_state,
- .dump_ip_state = vcn_v2_5_dump_ip_state,
- .print_ip_state = vcn_v2_5_print_ip_state,
+ .dump_ip_state = amdgpu_vcn_dump_ip_state,
+ .print_ip_state = amdgpu_vcn_print_ip_state,
};
static const struct amd_ip_funcs vcn_v2_6_ip_funcs = {
@@ -2223,8 +2154,8 @@ static const struct amd_ip_funcs vcn_v2_6_ip_funcs = {
.wait_for_idle = vcn_v2_5_wait_for_idle,
.set_clockgating_state = vcn_v2_5_set_clockgating_state,
.set_powergating_state = vcn_set_powergating_state,
- .dump_ip_state = vcn_v2_5_dump_ip_state,
- .print_ip_state = vcn_v2_5_print_ip_state,
+ .dump_ip_state = amdgpu_vcn_dump_ip_state,
+ .print_ip_state = amdgpu_vcn_print_ip_state,
};
const struct amdgpu_ip_block_version vcn_v2_5_ip_block =
diff --git a/drivers/gpu/drm/amd/amdgpu/vcn_v3_0.c b/drivers/gpu/drm/amd/amdgpu/vcn_v3_0.c
index a89662c97c9e..ff2a85619f23 100644
--- a/drivers/gpu/drm/amd/amdgpu/vcn_v3_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/vcn_v3_0.c
@@ -175,8 +175,6 @@ static int vcn_v3_0_sw_init(struct amdgpu_ip_block *ip_block)
struct amdgpu_ring *ring;
int i, j, r;
int vcn_doorbell_index = 0;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_3_0);
- uint32_t *ptr;
struct amdgpu_device *adev = ip_block->adev;
/*
@@ -304,14 +302,9 @@ static int vcn_v3_0_sw_init(struct amdgpu_ip_block *ip_block)
return r;
}
- /* Allocate memory for VCN IP Dump buffer */
- ptr = kcalloc(adev->vcn.num_vcn_inst * reg_count, sizeof(uint32_t), GFP_KERNEL);
- if (ptr == NULL) {
- DRM_ERROR("Failed to allocate memory for VCN IP Dump\n");
- adev->vcn.ip_dump = NULL;
- } else {
- adev->vcn.ip_dump = ptr;
- }
+ r = amdgpu_vcn_reg_dump_init(adev, vcn_reg_list_3_0, ARRAY_SIZE(vcn_reg_list_3_0));
+ if (r)
+ return r;
r = amdgpu_vcn_sysfs_reset_mask_init(adev);
if (r)
@@ -2348,67 +2341,6 @@ static void vcn_v3_0_set_irq_funcs(struct amdgpu_device *adev)
}
}
-static void vcn_v3_0_print_ip_state(struct amdgpu_ip_block *ip_block, struct drm_printer *p)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_3_0);
- uint32_t inst_off;
- bool is_powered;
-
- if (!adev->vcn.ip_dump)
- return;
-
- drm_printf(p, "num_instances:%d\n", adev->vcn.num_vcn_inst);
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i)) {
- drm_printf(p, "\nHarvested Instance:VCN%d Skipping dump\n", i);
- continue;
- }
-
- inst_off = i * reg_count;
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered) {
- drm_printf(p, "\nActive Instance:VCN%d\n", i);
- for (j = 0; j < reg_count; j++)
- drm_printf(p, "%-50s \t 0x%08x\n", vcn_reg_list_3_0[j].reg_name,
- adev->vcn.ip_dump[inst_off + j]);
- } else {
- drm_printf(p, "\nInactive Instance:VCN%d\n", i);
- }
- }
-}
-
-static void vcn_v3_0_dump_ip_state(struct amdgpu_ip_block *ip_block)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- bool is_powered;
- uint32_t inst_off;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_3_0);
-
- if (!adev->vcn.ip_dump)
- return;
-
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i))
- continue;
-
- inst_off = i * reg_count;
- /* mmUVD_POWER_STATUS is always readable and is first element of the array */
- adev->vcn.ip_dump[inst_off] = RREG32_SOC15(VCN, i, mmUVD_POWER_STATUS);
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered)
- for (j = 1; j < reg_count; j++)
- adev->vcn.ip_dump[inst_off + j] =
- RREG32(SOC15_REG_ENTRY_OFFSET_INST(vcn_reg_list_3_0[j], i));
- }
-}
-
static const struct amd_ip_funcs vcn_v3_0_ip_funcs = {
.name = "vcn_v3_0",
.early_init = vcn_v3_0_early_init,
@@ -2422,8 +2354,8 @@ static const struct amd_ip_funcs vcn_v3_0_ip_funcs = {
.wait_for_idle = vcn_v3_0_wait_for_idle,
.set_clockgating_state = vcn_v3_0_set_clockgating_state,
.set_powergating_state = vcn_set_powergating_state,
- .dump_ip_state = vcn_v3_0_dump_ip_state,
- .print_ip_state = vcn_v3_0_print_ip_state,
+ .dump_ip_state = amdgpu_vcn_dump_ip_state,
+ .print_ip_state = amdgpu_vcn_print_ip_state,
};
const struct amdgpu_ip_block_version vcn_v3_0_ip_block = {
diff --git a/drivers/gpu/drm/amd/amdgpu/vcn_v4_0.c b/drivers/gpu/drm/amd/amdgpu/vcn_v4_0.c
index e9f9cb169034..1785786a72f8 100644
--- a/drivers/gpu/drm/amd/amdgpu/vcn_v4_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/vcn_v4_0.c
@@ -183,8 +183,6 @@ static int vcn_v4_0_sw_init(struct amdgpu_ip_block *ip_block)
struct amdgpu_ring *ring;
struct amdgpu_device *adev = ip_block->adev;
int i, r;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_4_0);
- uint32_t *ptr;
for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
if (adev->vcn.harvest_config & (1 << i))
@@ -255,14 +253,9 @@ static int vcn_v4_0_sw_init(struct amdgpu_ip_block *ip_block)
if (r)
return r;
- /* Allocate memory for VCN IP Dump buffer */
- ptr = kcalloc(adev->vcn.num_vcn_inst * reg_count, sizeof(uint32_t), GFP_KERNEL);
- if (!ptr) {
- DRM_ERROR("Failed to allocate memory for VCN IP Dump\n");
- adev->vcn.ip_dump = NULL;
- } else {
- adev->vcn.ip_dump = ptr;
- }
+ r = amdgpu_vcn_reg_dump_init(adev, vcn_reg_list_4_0, ARRAY_SIZE(vcn_reg_list_4_0));
+ if (r)
+ return r;
r = amdgpu_vcn_sysfs_reset_mask_init(adev);
if (r)
@@ -315,8 +308,6 @@ static int vcn_v4_0_sw_fini(struct amdgpu_ip_block *ip_block)
return r;
}
- kfree(adev->vcn.ip_dump);
-
return 0;
}
@@ -2252,67 +2243,6 @@ static void vcn_v4_0_set_irq_funcs(struct amdgpu_device *adev)
}
}
-static void vcn_v4_0_print_ip_state(struct amdgpu_ip_block *ip_block, struct drm_printer *p)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_4_0);
- uint32_t inst_off, is_powered;
-
- if (!adev->vcn.ip_dump)
- return;
-
- drm_printf(p, "num_instances:%d\n", adev->vcn.num_vcn_inst);
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i)) {
- drm_printf(p, "\nHarvested Instance:VCN%d Skipping dump\n", i);
- continue;
- }
-
- inst_off = i * reg_count;
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered) {
- drm_printf(p, "\nActive Instance:VCN%d\n", i);
- for (j = 0; j < reg_count; j++)
- drm_printf(p, "%-50s \t 0x%08x\n", vcn_reg_list_4_0[j].reg_name,
- adev->vcn.ip_dump[inst_off + j]);
- } else {
- drm_printf(p, "\nInactive Instance:VCN%d\n", i);
- }
- }
-}
-
-static void vcn_v4_0_dump_ip_state(struct amdgpu_ip_block *ip_block)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- bool is_powered;
- uint32_t inst_off;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_4_0);
-
- if (!adev->vcn.ip_dump)
- return;
-
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i))
- continue;
-
- inst_off = i * reg_count;
- /* mmUVD_POWER_STATUS is always readable and is first element of the array */
- adev->vcn.ip_dump[inst_off] = RREG32_SOC15(VCN, i, regUVD_POWER_STATUS);
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered)
- for (j = 1; j < reg_count; j++)
- adev->vcn.ip_dump[inst_off + j] =
- RREG32(SOC15_REG_ENTRY_OFFSET_INST(vcn_reg_list_4_0[j],
- i));
- }
-}
-
static const struct amd_ip_funcs vcn_v4_0_ip_funcs = {
.name = "vcn_v4_0",
.early_init = vcn_v4_0_early_init,
@@ -2326,8 +2256,8 @@ static const struct amd_ip_funcs vcn_v4_0_ip_funcs = {
.wait_for_idle = vcn_v4_0_wait_for_idle,
.set_clockgating_state = vcn_v4_0_set_clockgating_state,
.set_powergating_state = vcn_set_powergating_state,
- .dump_ip_state = vcn_v4_0_dump_ip_state,
- .print_ip_state = vcn_v4_0_print_ip_state,
+ .dump_ip_state = amdgpu_vcn_dump_ip_state,
+ .print_ip_state = amdgpu_vcn_print_ip_state,
};
const struct amdgpu_ip_block_version vcn_v4_0_ip_block = {
diff --git a/drivers/gpu/drm/amd/amdgpu/vcn_v4_0_3.c b/drivers/gpu/drm/amd/amdgpu/vcn_v4_0_3.c
index b904afc358ae..c6450ed65c12 100644
--- a/drivers/gpu/drm/amd/amdgpu/vcn_v4_0_3.c
+++ b/drivers/gpu/drm/amd/amdgpu/vcn_v4_0_3.c
@@ -160,8 +160,6 @@ static int vcn_v4_0_3_sw_init(struct amdgpu_ip_block *ip_block)
struct amdgpu_device *adev = ip_block->adev;
struct amdgpu_ring *ring;
int i, r, vcn_inst;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_4_0_3);
- uint32_t *ptr;
/* VCN DEC TRAP */
r = amdgpu_irq_add_id(adev, SOC15_IH_CLIENTID_VCN,
@@ -231,14 +229,9 @@ static int vcn_v4_0_3_sw_init(struct amdgpu_ip_block *ip_block)
}
}
- /* Allocate memory for VCN IP Dump buffer */
- ptr = kcalloc(adev->vcn.num_vcn_inst * reg_count, sizeof(uint32_t), GFP_KERNEL);
- if (!ptr) {
- DRM_ERROR("Failed to allocate memory for VCN IP Dump\n");
- adev->vcn.ip_dump = NULL;
- } else {
- adev->vcn.ip_dump = ptr;
- }
+ r = amdgpu_vcn_reg_dump_init(adev, vcn_reg_list_4_0_3, ARRAY_SIZE(vcn_reg_list_4_0_3));
+ if (r)
+ return r;
r = amdgpu_vcn_sysfs_reset_mask_init(adev);
if (r)
@@ -391,7 +384,7 @@ static int vcn_v4_0_3_hw_fini(struct amdgpu_ip_block *ip_block)
vinst->set_pg_state(vinst, AMD_PG_STATE_GATE);
}
- if (amdgpu_ras_is_supported(adev, AMDGPU_RAS_BLOCK__VCN))
+ if (amdgpu_ras_is_supported(adev, AMDGPU_RAS_BLOCK__VCN) && !amdgpu_sriov_vf(adev))
amdgpu_irq_put(adev, &adev->vcn.inst->ras_poison_irq, 0);
return 0;
@@ -1877,68 +1870,6 @@ static void vcn_v4_0_3_set_irq_funcs(struct amdgpu_device *adev)
adev->vcn.inst->ras_poison_irq.funcs = &vcn_v4_0_3_ras_irq_funcs;
}
-static void vcn_v4_0_3_print_ip_state(struct amdgpu_ip_block *ip_block, struct drm_printer *p)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_4_0_3);
- uint32_t inst_off, is_powered;
-
- if (!adev->vcn.ip_dump)
- return;
-
- drm_printf(p, "num_instances:%d\n", adev->vcn.num_vcn_inst);
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i)) {
- drm_printf(p, "\nHarvested Instance:VCN%d Skipping dump\n", i);
- continue;
- }
-
- inst_off = i * reg_count;
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered) {
- drm_printf(p, "\nActive Instance:VCN%d\n", i);
- for (j = 0; j < reg_count; j++)
- drm_printf(p, "%-50s \t 0x%08x\n", vcn_reg_list_4_0_3[j].reg_name,
- adev->vcn.ip_dump[inst_off + j]);
- } else {
- drm_printf(p, "\nInactive Instance:VCN%d\n", i);
- }
- }
-}
-
-static void vcn_v4_0_3_dump_ip_state(struct amdgpu_ip_block *ip_block)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- bool is_powered;
- uint32_t inst_off, inst_id;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_4_0_3);
-
- if (!adev->vcn.ip_dump)
- return;
-
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i))
- continue;
-
- inst_id = GET_INST(VCN, i);
- inst_off = i * reg_count;
- /* mmUVD_POWER_STATUS is always readable and is first element of the array */
- adev->vcn.ip_dump[inst_off] = RREG32_SOC15(VCN, inst_id, regUVD_POWER_STATUS);
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered)
- for (j = 1; j < reg_count; j++)
- adev->vcn.ip_dump[inst_off + j] =
- RREG32(SOC15_REG_ENTRY_OFFSET_INST(vcn_reg_list_4_0_3[j],
- inst_id));
- }
-}
-
static const struct amd_ip_funcs vcn_v4_0_3_ip_funcs = {
.name = "vcn_v4_0_3",
.early_init = vcn_v4_0_3_early_init,
@@ -1952,8 +1883,8 @@ static const struct amd_ip_funcs vcn_v4_0_3_ip_funcs = {
.wait_for_idle = vcn_v4_0_3_wait_for_idle,
.set_clockgating_state = vcn_v4_0_3_set_clockgating_state,
.set_powergating_state = vcn_set_powergating_state,
- .dump_ip_state = vcn_v4_0_3_dump_ip_state,
- .print_ip_state = vcn_v4_0_3_print_ip_state,
+ .dump_ip_state = amdgpu_vcn_dump_ip_state,
+ .print_ip_state = amdgpu_vcn_print_ip_state,
};
const struct amdgpu_ip_block_version vcn_v4_0_3_ip_block = {
diff --git a/drivers/gpu/drm/amd/amdgpu/vcn_v4_0_5.c b/drivers/gpu/drm/amd/amdgpu/vcn_v4_0_5.c
index ed57e6431d4b..f785467370d9 100644
--- a/drivers/gpu/drm/amd/amdgpu/vcn_v4_0_5.c
+++ b/drivers/gpu/drm/amd/amdgpu/vcn_v4_0_5.c
@@ -147,9 +147,6 @@ static int vcn_v4_0_5_sw_init(struct amdgpu_ip_block *ip_block)
struct amdgpu_ring *ring;
struct amdgpu_device *adev = ip_block->adev;
int i, r;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_4_0_5);
- uint32_t *ptr;
-
for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
volatile struct amdgpu_vcn4_fw_shared *fw_shared;
@@ -233,15 +230,9 @@ static int vcn_v4_0_5_sw_init(struct amdgpu_ip_block *ip_block)
return r;
}
- /* Allocate memory for VCN IP Dump buffer */
- ptr = kcalloc(adev->vcn.num_vcn_inst * reg_count, sizeof(uint32_t), GFP_KERNEL);
- if (!ptr) {
- DRM_ERROR("Failed to allocate memory for VCN IP Dump\n");
- adev->vcn.ip_dump = NULL;
- } else {
- adev->vcn.ip_dump = ptr;
- }
- return 0;
+ r = amdgpu_vcn_reg_dump_init(adev, vcn_reg_list_4_0_5, ARRAY_SIZE(vcn_reg_list_4_0_5));
+
+ return r;
}
/**
@@ -1710,67 +1701,6 @@ static void vcn_v4_0_5_set_irq_funcs(struct amdgpu_device *adev)
}
}
-static void vcn_v4_0_5_print_ip_state(struct amdgpu_ip_block *ip_block, struct drm_printer *p)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_4_0_5);
- uint32_t inst_off, is_powered;
-
- if (!adev->vcn.ip_dump)
- return;
-
- drm_printf(p, "num_instances:%d\n", adev->vcn.num_vcn_inst);
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i)) {
- drm_printf(p, "\nHarvested Instance:VCN%d Skipping dump\n", i);
- continue;
- }
-
- inst_off = i * reg_count;
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered) {
- drm_printf(p, "\nActive Instance:VCN%d\n", i);
- for (j = 0; j < reg_count; j++)
- drm_printf(p, "%-50s \t 0x%08x\n", vcn_reg_list_4_0_5[j].reg_name,
- adev->vcn.ip_dump[inst_off + j]);
- } else {
- drm_printf(p, "\nInactive Instance:VCN%d\n", i);
- }
- }
-}
-
-static void vcn_v4_0_5_dump_ip_state(struct amdgpu_ip_block *ip_block)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- bool is_powered;
- uint32_t inst_off;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_4_0_5);
-
- if (!adev->vcn.ip_dump)
- return;
-
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i))
- continue;
-
- inst_off = i * reg_count;
- /* mmUVD_POWER_STATUS is always readable and is first element of the array */
- adev->vcn.ip_dump[inst_off] = RREG32_SOC15(VCN, i, regUVD_POWER_STATUS);
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered)
- for (j = 1; j < reg_count; j++)
- adev->vcn.ip_dump[inst_off + j] =
- RREG32(SOC15_REG_ENTRY_OFFSET_INST(vcn_reg_list_4_0_5[j],
- i));
- }
-}
-
static const struct amd_ip_funcs vcn_v4_0_5_ip_funcs = {
.name = "vcn_v4_0_5",
.early_init = vcn_v4_0_5_early_init,
@@ -1784,8 +1714,8 @@ static const struct amd_ip_funcs vcn_v4_0_5_ip_funcs = {
.wait_for_idle = vcn_v4_0_5_wait_for_idle,
.set_clockgating_state = vcn_v4_0_5_set_clockgating_state,
.set_powergating_state = vcn_set_powergating_state,
- .dump_ip_state = vcn_v4_0_5_dump_ip_state,
- .print_ip_state = vcn_v4_0_5_print_ip_state,
+ .dump_ip_state = amdgpu_vcn_dump_ip_state,
+ .print_ip_state = amdgpu_vcn_print_ip_state,
};
const struct amdgpu_ip_block_version vcn_v4_0_5_ip_block = {
diff --git a/drivers/gpu/drm/amd/amdgpu/vcn_v5_0_0.c b/drivers/gpu/drm/amd/amdgpu/vcn_v5_0_0.c
index f8bb90fe764b..455f829b8bb9 100644
--- a/drivers/gpu/drm/amd/amdgpu/vcn_v5_0_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/vcn_v5_0_0.c
@@ -115,21 +115,6 @@ static int vcn_v5_0_0_early_init(struct amdgpu_ip_block *ip_block)
return 0;
}
-void vcn_v5_0_0_alloc_ip_dump(struct amdgpu_device *adev)
-{
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_5_0);
- uint32_t *ptr;
-
- /* Allocate memory for VCN IP Dump buffer */
- ptr = kcalloc(adev->vcn.num_vcn_inst * reg_count, sizeof(uint32_t), GFP_KERNEL);
- if (!ptr) {
- DRM_ERROR("Failed to allocate memory for VCN IP Dump\n");
- adev->vcn.ip_dump = NULL;
- } else {
- adev->vcn.ip_dump = ptr;
- }
-}
-
/**
* vcn_v5_0_0_sw_init - sw init for VCN block
*
@@ -201,7 +186,9 @@ static int vcn_v5_0_0_sw_init(struct amdgpu_ip_block *ip_block)
if (!amdgpu_sriov_vf(adev))
adev->vcn.supported_reset |= AMDGPU_RESET_TYPE_PER_QUEUE;
- vcn_v5_0_0_alloc_ip_dump(adev);
+ r = amdgpu_vcn_reg_dump_init(adev, vcn_reg_list_5_0, ARRAY_SIZE(vcn_reg_list_5_0));
+ if (r)
+ return r;
r = amdgpu_vcn_sysfs_reset_mask_init(adev);
if (r)
@@ -251,8 +238,6 @@ static int vcn_v5_0_0_sw_fini(struct amdgpu_ip_block *ip_block)
return r;
}
- kfree(adev->vcn.ip_dump);
-
return 0;
}
@@ -769,9 +754,10 @@ static int vcn_v5_0_0_start_dpg_mode(struct amdgpu_vcn_inst *vinst,
if (indirect) {
ret = amdgpu_vcn_psp_update_sram(adev, inst_idx, 0);
- dev_err(adev->dev, "%s: vcn sram load failed %d\n", __func__, ret);
- if (ret)
+ if (ret) {
+ dev_err(adev->dev, "%s: vcn sram load failed %d\n", __func__, ret);
return ret;
+ }
}
ring = &adev->vcn.inst[inst_idx].ring_enc[0];
@@ -1433,67 +1419,6 @@ static void vcn_v5_0_0_set_irq_funcs(struct amdgpu_device *adev)
}
}
-void vcn_v5_0_0_print_ip_state(struct amdgpu_ip_block *ip_block,
- struct drm_printer *p)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_5_0);
- uint32_t inst_off, is_powered;
-
- if (!adev->vcn.ip_dump)
- return;
-
- drm_printf(p, "num_instances:%d\n", adev->vcn.num_vcn_inst);
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i)) {
- drm_printf(p, "\nHarvested Instance:VCN%d Skipping dump\n", i);
- continue;
- }
-
- inst_off = i * reg_count;
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered) {
- drm_printf(p, "\nActive Instance:VCN%d\n", i);
- for (j = 0; j < reg_count; j++)
- drm_printf(p, "%-50s \t 0x%08x\n", vcn_reg_list_5_0[j].reg_name,
- adev->vcn.ip_dump[inst_off + j]);
- } else {
- drm_printf(p, "\nInactive Instance:VCN%d\n", i);
- }
- }
-}
-
-void vcn_v5_0_0_dump_ip_state(struct amdgpu_ip_block *ip_block)
-{
- struct amdgpu_device *adev = ip_block->adev;
- int i, j;
- bool is_powered;
- uint32_t inst_off;
- uint32_t reg_count = ARRAY_SIZE(vcn_reg_list_5_0);
-
- if (!adev->vcn.ip_dump)
- return;
-
- for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
- if (adev->vcn.harvest_config & (1 << i))
- continue;
-
- inst_off = i * reg_count;
- /* mmUVD_POWER_STATUS is always readable and is first element of the array */
- adev->vcn.ip_dump[inst_off] = RREG32_SOC15(VCN, i, regUVD_POWER_STATUS);
- is_powered = (adev->vcn.ip_dump[inst_off] &
- UVD_POWER_STATUS__UVD_POWER_STATUS_MASK) != 1;
-
- if (is_powered)
- for (j = 1; j < reg_count; j++)
- adev->vcn.ip_dump[inst_off + j] =
- RREG32(SOC15_REG_ENTRY_OFFSET_INST(vcn_reg_list_5_0[j], i));
- }
-}
-
static const struct amd_ip_funcs vcn_v5_0_0_ip_funcs = {
.name = "vcn_v5_0_0",
.early_init = vcn_v5_0_0_early_init,
@@ -1507,8 +1432,8 @@ static const struct amd_ip_funcs vcn_v5_0_0_ip_funcs = {
.wait_for_idle = vcn_v5_0_0_wait_for_idle,
.set_clockgating_state = vcn_v5_0_0_set_clockgating_state,
.set_powergating_state = vcn_set_powergating_state,
- .dump_ip_state = vcn_v5_0_0_dump_ip_state,
- .print_ip_state = vcn_v5_0_0_print_ip_state,
+ .dump_ip_state = amdgpu_vcn_dump_ip_state,
+ .print_ip_state = amdgpu_vcn_print_ip_state,
};
const struct amdgpu_ip_block_version vcn_v5_0_0_ip_block = {
diff --git a/drivers/gpu/drm/amd/amdgpu/vcn_v5_0_0.h b/drivers/gpu/drm/amd/amdgpu/vcn_v5_0_0.h
index b8927652bc50..51bbccd4360f 100644
--- a/drivers/gpu/drm/amd/amdgpu/vcn_v5_0_0.h
+++ b/drivers/gpu/drm/amd/amdgpu/vcn_v5_0_0.h
@@ -32,11 +32,6 @@
#define VCN_VID_IP_ADDRESS 0x0
#define VCN_AON_IP_ADDRESS 0x30000
-void vcn_v5_0_0_alloc_ip_dump(struct amdgpu_device *adev);
-void vcn_v5_0_0_print_ip_state(struct amdgpu_ip_block *ip_block,
- struct drm_printer *p);
-void vcn_v5_0_0_dump_ip_state(struct amdgpu_ip_block *ip_block);
-
extern const struct amdgpu_ip_block_version vcn_v5_0_0_ip_block;
#endif /* __VCN_V5_0_0_H__ */
diff --git a/drivers/gpu/drm/amd/amdgpu/vcn_v5_0_1.c b/drivers/gpu/drm/amd/amdgpu/vcn_v5_0_1.c
index d8bbb9376731..7cb21e2b4eb0 100644
--- a/drivers/gpu/drm/amd/amdgpu/vcn_v5_0_1.c
+++ b/drivers/gpu/drm/amd/amdgpu/vcn_v5_0_1.c
@@ -40,6 +40,40 @@
#include <drm/drm_drv.h>
+static const struct amdgpu_hwip_reg_entry vcn_reg_list_5_0_1[] = {
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_POWER_STATUS),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_STATUS),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_CONTEXT_ID),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_CONTEXT_ID2),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_GPCOM_VCPU_DATA0),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_GPCOM_VCPU_DATA1),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_GPCOM_VCPU_CMD),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_BASE_HI),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_BASE_LO),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_BASE_HI2),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_BASE_LO2),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_BASE_HI3),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_BASE_LO3),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_BASE_HI4),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_BASE_LO4),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_RPTR),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_WPTR),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_RPTR2),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_WPTR2),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_RPTR3),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_WPTR3),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_RPTR4),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_WPTR4),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_SIZE),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_SIZE2),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_SIZE3),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_RB_SIZE4),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_DPG_LMA_CTL),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_DPG_LMA_DATA),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_DPG_LMA_MASK),
+ SOC15_REG_ENTRY_STR(VCN, 0, regUVD_DPG_PAUSE)
+};
+
static int vcn_v5_0_1_start_sriov(struct amdgpu_device *adev);
static void vcn_v5_0_1_set_unified_ring_funcs(struct amdgpu_device *adev);
static void vcn_v5_0_1_set_irq_funcs(struct amdgpu_device *adev);
@@ -163,7 +197,17 @@ static int vcn_v5_0_1_sw_init(struct amdgpu_ip_block *ip_block)
return r;
}
- vcn_v5_0_0_alloc_ip_dump(adev);
+ if (amdgpu_ras_is_supported(adev, AMDGPU_RAS_BLOCK__VCN)) {
+ r = amdgpu_vcn_ras_sw_init(adev);
+ if (r) {
+ dev_err(adev->dev, "Failed to initialize vcn ras block!\n");
+ return r;
+ }
+ }
+
+ r = amdgpu_vcn_reg_dump_init(adev, vcn_reg_list_5_0_1, ARRAY_SIZE(vcn_reg_list_5_0_1));
+ if (r)
+ return r;
return amdgpu_vcn_sysfs_reset_mask_init(adev);
}
@@ -209,8 +253,6 @@ static int vcn_v5_0_1_sw_fini(struct amdgpu_ip_block *ip_block)
amdgpu_vcn_sysfs_reset_mask_fini(adev);
- kfree(adev->vcn.ip_dump);
-
return 0;
}
@@ -1480,8 +1522,8 @@ static const struct amd_ip_funcs vcn_v5_0_1_ip_funcs = {
.post_soft_reset = NULL,
.set_clockgating_state = vcn_v5_0_1_set_clockgating_state,
.set_powergating_state = vcn_set_powergating_state,
- .dump_ip_state = vcn_v5_0_0_dump_ip_state,
- .print_ip_state = vcn_v5_0_0_print_ip_state,
+ .dump_ip_state = amdgpu_vcn_dump_ip_state,
+ .print_ip_state = amdgpu_vcn_print_ip_state,
};
const struct amdgpu_ip_block_version vcn_v5_0_1_ip_block = {
@@ -1562,7 +1604,7 @@ static int vcn_v5_0_1_aca_bank_parser(struct aca_handle *handle, struct aca_bank
/* reference to smu driver if header file */
static int vcn_v5_0_1_err_codes[] = {
- 14, 15, /* VCN */
+ 14, 15, 47, /* VCN [D|V|S] */
};
static bool vcn_v5_0_1_aca_bank_is_valid(struct aca_handle *handle, struct aca_bank *bank,
@@ -1608,6 +1650,13 @@ static int vcn_v5_0_1_ras_late_init(struct amdgpu_device *adev, struct ras_commo
if (r)
goto late_fini;
+ if (amdgpu_ras_is_supported(adev, ras_block->block) &&
+ adev->vcn.inst->ras_poison_irq.funcs) {
+ r = amdgpu_irq_get(adev, &adev->vcn.inst->ras_poison_irq, 0);
+ if (r)
+ goto late_fini;
+ }
+
return 0;
late_fini:
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager.c b/drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager.c
index 2d91027e2a74..6c5c7c1bf5ed 100644
--- a/drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager.c
+++ b/drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager.c
@@ -2725,7 +2725,7 @@ static void get_queue_checkpoint_info(struct device_queue_manager *dqm,
dqm_lock(dqm);
mqd_mgr = dqm->mqd_mgrs[mqd_type];
- *mqd_size = mqd_mgr->mqd_size;
+ *mqd_size = mqd_mgr->mqd_size * NUM_XCC(mqd_mgr->dev->xcc_mask);
*ctl_stack_size = 0;
if (q->properties.type == KFD_QUEUE_TYPE_COMPUTE && mqd_mgr->get_checkpoint_info)
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_mqd_manager_v9.c b/drivers/gpu/drm/amd/amdkfd/kfd_mqd_manager_v9.c
index 97933d2a3803..f2dee320fada 100644
--- a/drivers/gpu/drm/amd/amdkfd/kfd_mqd_manager_v9.c
+++ b/drivers/gpu/drm/amd/amdkfd/kfd_mqd_manager_v9.c
@@ -373,7 +373,7 @@ static void get_checkpoint_info(struct mqd_manager *mm, void *mqd, u32 *ctl_stac
{
struct v9_mqd *m = get_mqd(mqd);
- *ctl_stack_size = m->cp_hqd_cntl_stack_size;
+ *ctl_stack_size = m->cp_hqd_cntl_stack_size * NUM_XCC(mm->dev->xcc_mask);
}
static void checkpoint_mqd(struct mqd_manager *mm, void *mqd, void *mqd_dst, void *ctl_stack_dst)
@@ -388,6 +388,24 @@ static void checkpoint_mqd(struct mqd_manager *mm, void *mqd, void *mqd_dst, voi
memcpy(ctl_stack_dst, ctl_stack, m->cp_hqd_cntl_stack_size);
}
+static void checkpoint_mqd_v9_4_3(struct mqd_manager *mm,
+ void *mqd,
+ void *mqd_dst,
+ void *ctl_stack_dst)
+{
+ struct v9_mqd *m;
+ int xcc;
+ uint64_t size = get_mqd(mqd)->cp_mqd_stride_size;
+
+ for (xcc = 0; xcc < NUM_XCC(mm->dev->xcc_mask); xcc++) {
+ m = get_mqd(mqd + size * xcc);
+
+ checkpoint_mqd(mm, m,
+ (uint8_t *)mqd_dst + sizeof(*m) * xcc,
+ (uint8_t *)ctl_stack_dst + m->cp_hqd_cntl_stack_size * xcc);
+ }
+}
+
static void restore_mqd(struct mqd_manager *mm, void **mqd,
struct kfd_mem_obj *mqd_mem_obj, uint64_t *gart_addr,
struct queue_properties *qp,
@@ -764,13 +782,35 @@ static void restore_mqd_v9_4_3(struct mqd_manager *mm, void **mqd,
const void *mqd_src,
const void *ctl_stack_src, u32 ctl_stack_size)
{
- restore_mqd(mm, mqd, mqd_mem_obj, gart_addr, qp, mqd_src, ctl_stack_src, ctl_stack_size);
- if (amdgpu_sriov_multi_vf_mode(mm->dev->adev)) {
- struct v9_mqd *m;
+ struct kfd_mem_obj xcc_mqd_mem_obj;
+ u32 mqd_ctl_stack_size;
+ struct v9_mqd *m;
+ u32 num_xcc;
+ int xcc;
- m = (struct v9_mqd *) mqd_mem_obj->cpu_ptr;
- m->cp_hqd_pq_doorbell_control |= 1 <<
- CP_HQD_PQ_DOORBELL_CONTROL__DOORBELL_MODE__SHIFT;
+ uint64_t offset = mm->mqd_stride(mm, qp);
+
+ mm->dev->dqm->current_logical_xcc_start++;
+
+ num_xcc = NUM_XCC(mm->dev->xcc_mask);
+ mqd_ctl_stack_size = ctl_stack_size / num_xcc;
+
+ memset(&xcc_mqd_mem_obj, 0x0, sizeof(struct kfd_mem_obj));
+
+ /* Set the MQD pointer and gart address to XCC0 MQD */
+ *mqd = mqd_mem_obj->cpu_ptr;
+ if (gart_addr)
+ *gart_addr = mqd_mem_obj->gpu_addr;
+
+ for (xcc = 0; xcc < num_xcc; xcc++) {
+ get_xcc_mqd(mqd_mem_obj, &xcc_mqd_mem_obj, offset * xcc);
+ restore_mqd(mm, (void **)&m,
+ &xcc_mqd_mem_obj,
+ NULL,
+ qp,
+ (uint8_t *)mqd_src + xcc * sizeof(*m),
+ (uint8_t *)ctl_stack_src + xcc * mqd_ctl_stack_size,
+ mqd_ctl_stack_size);
}
}
static int destroy_mqd_v9_4_3(struct mqd_manager *mm, void *mqd,
@@ -906,7 +946,6 @@ struct mqd_manager *mqd_manager_init_v9(enum KFD_MQD_TYPE type,
mqd->free_mqd = kfd_free_mqd_cp;
mqd->is_occupied = kfd_is_occupied_cp;
mqd->get_checkpoint_info = get_checkpoint_info;
- mqd->checkpoint_mqd = checkpoint_mqd;
mqd->mqd_size = sizeof(struct v9_mqd);
mqd->mqd_stride = mqd_stride_v9;
#if defined(CONFIG_DEBUG_FS)
@@ -918,16 +957,18 @@ struct mqd_manager *mqd_manager_init_v9(enum KFD_MQD_TYPE type,
mqd->init_mqd = init_mqd_v9_4_3;
mqd->load_mqd = load_mqd_v9_4_3;
mqd->update_mqd = update_mqd_v9_4_3;
- mqd->restore_mqd = restore_mqd_v9_4_3;
mqd->destroy_mqd = destroy_mqd_v9_4_3;
mqd->get_wave_state = get_wave_state_v9_4_3;
+ mqd->checkpoint_mqd = checkpoint_mqd_v9_4_3;
+ mqd->restore_mqd = restore_mqd_v9_4_3;
} else {
mqd->init_mqd = init_mqd;
mqd->load_mqd = load_mqd;
mqd->update_mqd = update_mqd;
- mqd->restore_mqd = restore_mqd;
mqd->destroy_mqd = kfd_destroy_mqd_cp;
mqd->get_wave_state = get_wave_state;
+ mqd->checkpoint_mqd = checkpoint_mqd;
+ mqd->restore_mqd = restore_mqd;
}
break;
case KFD_MQD_TYPE_HIQ:
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_process_queue_manager.c b/drivers/gpu/drm/amd/amdkfd/kfd_process_queue_manager.c
index c643e0ccec52..7fbb5c274ccc 100644
--- a/drivers/gpu/drm/amd/amdkfd/kfd_process_queue_manager.c
+++ b/drivers/gpu/drm/amd/amdkfd/kfd_process_queue_manager.c
@@ -914,7 +914,10 @@ static int criu_checkpoint_queues_device(struct kfd_process_device *pdd,
q_data = (struct kfd_criu_queue_priv_data *)q_private_data;
- /* data stored in this order: priv_data, mqd, ctl_stack */
+ /*
+ * data stored in this order:
+ * priv_data, mqd[xcc0], mqd[xcc1],..., ctl_stack[xcc0], ctl_stack[xcc1]...
+ */
q_data->mqd_size = mqd_size;
q_data->ctl_stack_size = ctl_stack_size;
@@ -963,7 +966,7 @@ int kfd_criu_checkpoint_queues(struct kfd_process *p,
}
static void set_queue_properties_from_criu(struct queue_properties *qp,
- struct kfd_criu_queue_priv_data *q_data)
+ struct kfd_criu_queue_priv_data *q_data, uint32_t num_xcc)
{
qp->is_interop = false;
qp->queue_percent = q_data->q_percent;
@@ -976,7 +979,11 @@ static void set_queue_properties_from_criu(struct queue_properties *qp,
qp->eop_ring_buffer_size = q_data->eop_ring_buffer_size;
qp->ctx_save_restore_area_address = q_data->ctx_save_restore_area_address;
qp->ctx_save_restore_area_size = q_data->ctx_save_restore_area_size;
- qp->ctl_stack_size = q_data->ctl_stack_size;
+ if (q_data->type == KFD_QUEUE_TYPE_COMPUTE)
+ qp->ctl_stack_size = q_data->ctl_stack_size / num_xcc;
+ else
+ qp->ctl_stack_size = q_data->ctl_stack_size;
+
qp->type = q_data->type;
qp->format = q_data->format;
}
@@ -1036,12 +1043,15 @@ int kfd_criu_restore_queue(struct kfd_process *p,
goto exit;
}
- /* data stored in this order: mqd, ctl_stack */
+ /*
+ * data stored in this order:
+ * mqd[xcc0], mqd[xcc1],..., ctl_stack[xcc0], ctl_stack[xcc1]...
+ */
mqd = q_extra_data;
ctl_stack = mqd + q_data->mqd_size;
memset(&qp, 0, sizeof(qp));
- set_queue_properties_from_criu(&qp, q_data);
+ set_queue_properties_from_criu(&qp, q_data, NUM_XCC(pdd->dev->adev->gfx.xcc_mask));
print_queue_properties(&qp);
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_svm.c b/drivers/gpu/drm/amd/amdkfd/kfd_svm.c
index a0f22ea6d15a..e23b5a0f31f2 100644
--- a/drivers/gpu/drm/amd/amdkfd/kfd_svm.c
+++ b/drivers/gpu/drm/amd/amdkfd/kfd_svm.c
@@ -1189,7 +1189,7 @@ svm_nodes_in_same_hive(struct kfd_node *node_a, struct kfd_node *node_b)
}
static uint64_t
-svm_range_get_pte_flags(struct kfd_node *node,
+svm_range_get_pte_flags(struct kfd_node *node, struct amdgpu_vm *vm,
struct svm_range *prange, int domain)
{
struct kfd_node *bo_node;
@@ -1292,10 +1292,6 @@ svm_range_get_pte_flags(struct kfd_node *node,
AMDGPU_VM_MTYPE_UC : AMDGPU_VM_MTYPE_NC;
}
- mapping_flags |= AMDGPU_VM_PAGE_READABLE | AMDGPU_VM_PAGE_WRITEABLE;
-
- if (flags & KFD_IOCTL_SVM_FLAG_GPU_RO)
- mapping_flags &= ~AMDGPU_VM_PAGE_WRITEABLE;
if (flags & KFD_IOCTL_SVM_FLAG_GPU_EXEC)
mapping_flags |= AMDGPU_VM_PAGE_EXECUTABLE;
@@ -1305,7 +1301,10 @@ svm_range_get_pte_flags(struct kfd_node *node,
if (gc_ip_version >= IP_VERSION(12, 0, 0))
pte_flags |= AMDGPU_PTE_IS_PTE;
- pte_flags |= amdgpu_gem_va_map_flags(node->adev, mapping_flags);
+ amdgpu_gmc_get_vm_pte(node->adev, vm, NULL, mapping_flags, &pte_flags);
+ pte_flags |= AMDGPU_PTE_READABLE;
+ if (!(flags & KFD_IOCTL_SVM_FLAG_GPU_RO))
+ pte_flags |= AMDGPU_PTE_WRITEABLE;
return pte_flags;
}
@@ -1412,7 +1411,7 @@ svm_range_map_to_gpu(struct kfd_process_device *pdd, struct svm_range *prange,
pr_debug("Mapping range [0x%lx 0x%llx] on domain: %s\n",
last_start, prange->start + i, last_domain ? "GPU" : "CPU");
- pte_flags = svm_range_get_pte_flags(pdd->dev, prange, last_domain);
+ pte_flags = svm_range_get_pte_flags(pdd->dev, vm, prange, last_domain);
if (readonly)
pte_flags &= ~AMDGPU_PTE_WRITEABLE;
diff --git a/drivers/gpu/drm/amd/amdxcp/amdgpu_xcp_drv.c b/drivers/gpu/drm/amd/amdxcp/amdgpu_xcp_drv.c
index 8bc36f04b1b7..44009aa8216e 100644
--- a/drivers/gpu/drm/amd/amdxcp/amdgpu_xcp_drv.c
+++ b/drivers/gpu/drm/amd/amdxcp/amdgpu_xcp_drv.c
@@ -46,18 +46,29 @@ static const struct drm_driver amdgpu_xcp_driver = {
static int8_t pdev_num;
static struct xcp_device *xcp_dev[MAX_XCP_PLATFORM_DEVICE];
+static DEFINE_MUTEX(xcp_mutex);
int amdgpu_xcp_drm_dev_alloc(struct drm_device **ddev)
{
struct platform_device *pdev;
struct xcp_device *pxcp_dev;
char dev_name[20];
- int ret;
+ int ret, i;
+
+ guard(mutex)(&xcp_mutex);
if (pdev_num >= MAX_XCP_PLATFORM_DEVICE)
return -ENODEV;
- snprintf(dev_name, sizeof(dev_name), "amdgpu_xcp_%d", pdev_num);
+ for (i = 0; i < MAX_XCP_PLATFORM_DEVICE; i++) {
+ if (!xcp_dev[i])
+ break;
+ }
+
+ if (i >= MAX_XCP_PLATFORM_DEVICE)
+ return -ENODEV;
+
+ snprintf(dev_name, sizeof(dev_name), "amdgpu_xcp_%d", i);
pdev = platform_device_register_simple(dev_name, -1, NULL, 0);
if (IS_ERR(pdev))
return PTR_ERR(pdev);
@@ -73,8 +84,8 @@ int amdgpu_xcp_drm_dev_alloc(struct drm_device **ddev)
goto out_devres;
}
- xcp_dev[pdev_num] = pxcp_dev;
- xcp_dev[pdev_num]->pdev = pdev;
+ xcp_dev[i] = pxcp_dev;
+ xcp_dev[i]->pdev = pdev;
*ddev = &pxcp_dev->drm;
pdev_num++;
@@ -89,16 +100,43 @@ out_unregister:
}
EXPORT_SYMBOL(amdgpu_xcp_drm_dev_alloc);
-void amdgpu_xcp_drv_release(void)
+static void free_xcp_dev(int8_t index)
{
- for (--pdev_num; pdev_num >= 0; --pdev_num) {
- struct platform_device *pdev = xcp_dev[pdev_num]->pdev;
+ if ((index < MAX_XCP_PLATFORM_DEVICE) && (xcp_dev[index])) {
+ struct platform_device *pdev = xcp_dev[index]->pdev;
devres_release_group(&pdev->dev, NULL);
platform_device_unregister(pdev);
- xcp_dev[pdev_num] = NULL;
+
+ xcp_dev[index] = NULL;
+ pdev_num--;
+ }
+}
+
+void amdgpu_xcp_drm_dev_free(struct drm_device *ddev)
+{
+ int8_t i;
+
+ guard(mutex)(&xcp_mutex);
+
+ for (i = 0; i < MAX_XCP_PLATFORM_DEVICE; i++) {
+ if ((xcp_dev[i]) && (&xcp_dev[i]->drm == ddev)) {
+ free_xcp_dev(i);
+ break;
+ }
+ }
+}
+EXPORT_SYMBOL(amdgpu_xcp_drm_dev_free);
+
+void amdgpu_xcp_drv_release(void)
+{
+ int8_t i;
+
+ guard(mutex)(&xcp_mutex);
+
+ for (i = 0; pdev_num && i < MAX_XCP_PLATFORM_DEVICE; i++) {
+ free_xcp_dev(i);
}
- pdev_num = 0;
}
EXPORT_SYMBOL(amdgpu_xcp_drv_release);
diff --git a/drivers/gpu/drm/amd/amdxcp/amdgpu_xcp_drv.h b/drivers/gpu/drm/amd/amdxcp/amdgpu_xcp_drv.h
index c1c4b679bf95..580a1602c8e3 100644
--- a/drivers/gpu/drm/amd/amdxcp/amdgpu_xcp_drv.h
+++ b/drivers/gpu/drm/amd/amdxcp/amdgpu_xcp_drv.h
@@ -25,5 +25,6 @@
#define _AMDGPU_XCP_DRV_H_
int amdgpu_xcp_drm_dev_alloc(struct drm_device **ddev);
+void amdgpu_xcp_drm_dev_free(struct drm_device *ddev);
void amdgpu_xcp_drv_release(void);
#endif /* _AMDGPU_XCP_DRV_H_ */
diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
index c71167ffdb76..31ea57edeb45 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
@@ -530,6 +530,50 @@ static void dm_pflip_high_irq(void *interrupt_params)
amdgpu_crtc->crtc_id, amdgpu_crtc, vrr_active, (int)!e);
}
+static void dm_handle_vmin_vmax_update(struct work_struct *offload_work)
+{
+ struct vupdate_offload_work *work = container_of(offload_work, struct vupdate_offload_work, work);
+ struct amdgpu_device *adev = work->adev;
+ struct dc_stream_state *stream = work->stream;
+ struct dc_crtc_timing_adjust *adjust = work->adjust;
+
+ mutex_lock(&adev->dm.dc_lock);
+ dc_stream_adjust_vmin_vmax(adev->dm.dc, stream, adjust);
+ mutex_unlock(&adev->dm.dc_lock);
+
+ dc_stream_release(stream);
+ kfree(work->adjust);
+ kfree(work);
+}
+
+static void schedule_dc_vmin_vmax(struct amdgpu_device *adev,
+ struct dc_stream_state *stream,
+ struct dc_crtc_timing_adjust *adjust)
+{
+ struct vupdate_offload_work *offload_work = kzalloc(sizeof(*offload_work), GFP_KERNEL);
+ if (!offload_work) {
+ drm_dbg_driver(adev_to_drm(adev), "Failed to allocate vupdate_offload_work\n");
+ return;
+ }
+
+ struct dc_crtc_timing_adjust *adjust_copy = kzalloc(sizeof(*adjust_copy), GFP_KERNEL);
+ if (!adjust_copy) {
+ drm_dbg_driver(adev_to_drm(adev), "Failed to allocate adjust_copy\n");
+ kfree(offload_work);
+ return;
+ }
+
+ dc_stream_retain(stream);
+ memcpy(adjust_copy, adjust, sizeof(*adjust_copy));
+
+ INIT_WORK(&offload_work->work, dm_handle_vmin_vmax_update);
+ offload_work->adev = adev;
+ offload_work->stream = stream;
+ offload_work->adjust = adjust_copy;
+
+ queue_work(system_wq, &offload_work->work);
+}
+
static void dm_vupdate_high_irq(void *interrupt_params)
{
struct common_irq_params *irq_params = interrupt_params;
@@ -568,6 +612,11 @@ static void dm_vupdate_high_irq(void *interrupt_params)
* if a pageflip happened inside front-porch.
*/
if (vrr_active) {
+ bool replay_en = acrtc->dm_irq_params.stream->link->replay_settings.replay_feature_enabled;
+ bool psr_en = acrtc->dm_irq_params.stream->link->psr_settings.psr_feature_enabled;
+ bool fs_active_var_en = acrtc->dm_irq_params.freesync_config.state
+ == VRR_STATE_ACTIVE_VARIABLE;
+
amdgpu_dm_crtc_handle_vblank(acrtc);
/* BTR processing for pre-DCE12 ASICs */
@@ -579,10 +628,11 @@ static void dm_vupdate_high_irq(void *interrupt_params)
acrtc->dm_irq_params.stream,
&acrtc->dm_irq_params.vrr_params);
- dc_stream_adjust_vmin_vmax(
- adev->dm.dc,
- acrtc->dm_irq_params.stream,
- &acrtc->dm_irq_params.vrr_params.adjust);
+ if (fs_active_var_en || (!fs_active_var_en && !replay_en && !psr_en)) {
+ schedule_dc_vmin_vmax(adev,
+ acrtc->dm_irq_params.stream,
+ &acrtc->dm_irq_params.vrr_params.adjust);
+ }
spin_unlock_irqrestore(&adev_to_drm(adev)->event_lock, flags);
}
}
@@ -665,15 +715,20 @@ static void dm_crtc_high_irq(void *interrupt_params)
spin_lock_irqsave(&adev_to_drm(adev)->event_lock, flags);
if (acrtc->dm_irq_params.stream &&
- acrtc->dm_irq_params.vrr_params.supported &&
- acrtc->dm_irq_params.freesync_config.state ==
- VRR_STATE_ACTIVE_VARIABLE) {
+ acrtc->dm_irq_params.vrr_params.supported) {
+ bool replay_en = acrtc->dm_irq_params.stream->link->replay_settings.replay_feature_enabled;
+ bool psr_en = acrtc->dm_irq_params.stream->link->psr_settings.psr_feature_enabled;
+ bool fs_active_var_en = acrtc->dm_irq_params.freesync_config.state == VRR_STATE_ACTIVE_VARIABLE;
+
mod_freesync_handle_v_update(adev->dm.freesync_module,
acrtc->dm_irq_params.stream,
&acrtc->dm_irq_params.vrr_params);
- dc_stream_adjust_vmin_vmax(adev->dm.dc, acrtc->dm_irq_params.stream,
- &acrtc->dm_irq_params.vrr_params.adjust);
+ /* update vmin_vmax only if freesync is enabled, or only if PSR and REPLAY are disabled */
+ if (fs_active_var_en || (!fs_active_var_en && !replay_en && !psr_en)) {
+ schedule_dc_vmin_vmax(adev, acrtc->dm_irq_params.stream,
+ &acrtc->dm_irq_params.vrr_params.adjust);
+ }
}
/*
@@ -4745,16 +4800,16 @@ static int get_brightness_range(const struct amdgpu_dm_backlight_caps *caps,
return 1;
}
-/* Rescale from [min..max] to [0..MAX_BACKLIGHT_LEVEL] */
+/* Rescale from [min..max] to [0..AMDGPU_MAX_BL_LEVEL] */
static inline u32 scale_input_to_fw(int min, int max, u64 input)
{
- return DIV_ROUND_CLOSEST_ULL(input * MAX_BACKLIGHT_LEVEL, max - min);
+ return DIV_ROUND_CLOSEST_ULL(input * AMDGPU_MAX_BL_LEVEL, max - min);
}
-/* Rescale from [0..MAX_BACKLIGHT_LEVEL] to [min..max] */
+/* Rescale from [0..AMDGPU_MAX_BL_LEVEL] to [min..max] */
static inline u32 scale_fw_to_input(int min, int max, u64 input)
{
- return min + DIV_ROUND_CLOSEST_ULL(input * (max - min), MAX_BACKLIGHT_LEVEL);
+ return min + DIV_ROUND_CLOSEST_ULL(input * (max - min), AMDGPU_MAX_BL_LEVEL);
}
static void convert_custom_brightness(const struct amdgpu_dm_backlight_caps *caps,
diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h
index 67c3a7a967f2..94f312bae9ac 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h
@@ -153,6 +153,20 @@ struct idle_workqueue {
bool running;
};
+/**
+ * struct dm_vupdate_work - Work data for periodic action in idle
+ * @work: Kernel work data for the work event
+ * @adev: amdgpu_device back pointer
+ * @stream: DC stream associated with the crtc
+ * @adjust: DC CRTC timing adjust to be applied to the crtc
+ */
+struct vupdate_offload_work {
+ struct work_struct work;
+ struct amdgpu_device *adev;
+ struct dc_stream_state *stream;
+ struct dc_crtc_timing_adjust *adjust;
+};
+
#define MAX_LUMINANCE_DATA_POINTS 99
/**
diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crtc.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crtc.c
index 2551823382f8..010172f930ae 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crtc.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crtc.c
@@ -661,6 +661,15 @@ static int amdgpu_dm_crtc_helper_atomic_check(struct drm_crtc *crtc,
return -EINVAL;
}
+ if (!state->legacy_cursor_update && amdgpu_dm_crtc_vrr_active(dm_crtc_state)) {
+ struct drm_plane_state *primary_state;
+
+ /* Pull in primary plane for correct VRR handling */
+ primary_state = drm_atomic_get_plane_state(state, crtc->primary);
+ if (IS_ERR(primary_state))
+ return PTR_ERR(primary_state);
+ }
+
/* In some use cases, like reset, no stream is attached */
if (!dm_crtc_state->stream)
return 0;
diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c
index 137f18d41f1b..32281bf62f70 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c
@@ -1763,14 +1763,17 @@ static bool dp_get_link_current_set_bw(struct drm_dp_aux *aux, uint32_t *cur_lin
union lane_count_set lane_count;
u8 dp_link_encoding;
u8 link_bw_set = 0;
+ u8 data[16] = {0};
*cur_link_bw = 0;
- if (drm_dp_dpcd_read(aux, DP_MAIN_LINK_CHANNEL_CODING_SET, &dp_link_encoding, 1) != 1 ||
- drm_dp_dpcd_read(aux, DP_LANE_COUNT_SET, &lane_count.raw, 1) != 1 ||
- drm_dp_dpcd_read(aux, DP_LINK_BW_SET, &link_bw_set, 1) != 1)
+ if (drm_dp_dpcd_read(aux, DP_LINK_BW_SET, data, 16) != 16)
return false;
+ dp_link_encoding = data[DP_MAIN_LINK_CHANNEL_CODING_SET - DP_LINK_BW_SET];
+ link_bw_set = data[DP_LINK_BW_SET - DP_LINK_BW_SET];
+ lane_count.raw = data[DP_LANE_COUNT_SET - DP_LINK_BW_SET];
+
switch (dp_link_encoding) {
case DP_8b_10b_ENCODING:
link_rate = link_bw_set;
diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/clk_mgr.c
index 33b9d36619ff..4071851f9e86 100644
--- a/drivers/gpu/drm/amd/display/dc/clk_mgr/clk_mgr.c
+++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/clk_mgr.c
@@ -158,7 +158,6 @@ struct clk_mgr *dc_clk_mgr_create(struct dc_context *ctx, struct pp_smu_funcs *p
return NULL;
}
dce60_clk_mgr_construct(ctx, clk_mgr);
- dce_clk_mgr_construct(ctx, clk_mgr);
return &clk_mgr->base;
}
#endif
diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dce100/dce_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dce100/dce_clk_mgr.c
index 26feefbb8990..f5ad0a177038 100644
--- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dce100/dce_clk_mgr.c
+++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dce100/dce_clk_mgr.c
@@ -245,6 +245,11 @@ int dce_set_clock(
pxl_clk_params.target_pixel_clock_100hz = requested_clk_khz * 10;
pxl_clk_params.pll_id = CLOCK_SOURCE_ID_DFS;
+ /* DCE 6.0, DCE 6.4: engine clock is the same as PLL0 */
+ if (clk_mgr_base->ctx->dce_version == DCE_VERSION_6_0 ||
+ clk_mgr_base->ctx->dce_version == DCE_VERSION_6_4)
+ pxl_clk_params.pll_id = CLOCK_SOURCE_ID_PLL0;
+
if (clk_mgr_dce->dfs_bypass_active)
pxl_clk_params.flags.SET_DISPCLK_DFS_BYPASS = true;
diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c
index 9e2ef0e724fc..7aee02d56292 100644
--- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c
+++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c
@@ -563,6 +563,7 @@ static void vg_clk_mgr_helper_populate_bw_params(
{
int i, j;
struct clk_bw_params *bw_params = clk_mgr->base.bw_params;
+ uint32_t max_dispclk = 0, max_dppclk = 0;
j = -1;
@@ -584,6 +585,15 @@ static void vg_clk_mgr_helper_populate_bw_params(
return;
}
+ /* dispclk and dppclk can be max at any voltage, same number of levels for both */
+ if (clock_table->NumDispClkLevelsEnabled <= VG_NUM_DISPCLK_DPM_LEVELS &&
+ clock_table->NumDispClkLevelsEnabled <= VG_NUM_DPPCLK_DPM_LEVELS) {
+ max_dispclk = find_max_clk_value(clock_table->DispClocks, clock_table->NumDispClkLevelsEnabled);
+ max_dppclk = find_max_clk_value(clock_table->DppClocks, clock_table->NumDispClkLevelsEnabled);
+ } else {
+ ASSERT(0);
+ }
+
bw_params->clk_table.num_entries = j + 1;
for (i = 0; i < bw_params->clk_table.num_entries - 1; i++, j--) {
@@ -591,11 +601,17 @@ static void vg_clk_mgr_helper_populate_bw_params(
bw_params->clk_table.entries[i].memclk_mhz = clock_table->DfPstateTable[j].memclk;
bw_params->clk_table.entries[i].voltage = clock_table->DfPstateTable[j].voltage;
bw_params->clk_table.entries[i].dcfclk_mhz = find_dcfclk_for_voltage(clock_table, clock_table->DfPstateTable[j].voltage);
+
+ /* Now update clocks we do read */
+ bw_params->clk_table.entries[i].dispclk_mhz = max_dispclk;
+ bw_params->clk_table.entries[i].dppclk_mhz = max_dppclk;
}
bw_params->clk_table.entries[i].fclk_mhz = clock_table->DfPstateTable[j].fclk;
bw_params->clk_table.entries[i].memclk_mhz = clock_table->DfPstateTable[j].memclk;
bw_params->clk_table.entries[i].voltage = clock_table->DfPstateTable[j].voltage;
bw_params->clk_table.entries[i].dcfclk_mhz = find_max_clk_value(clock_table->DcfClocks, VG_NUM_DCFCLK_DPM_LEVELS);
+ bw_params->clk_table.entries[i].dispclk_mhz = find_max_clk_value(clock_table->DispClocks, VG_NUM_DISPCLK_DPM_LEVELS);
+ bw_params->clk_table.entries[i].dppclk_mhz = find_max_clk_value(clock_table->DppClocks, VG_NUM_DPPCLK_DPM_LEVELS);
bw_params->vram_type = bios_info->memory_type;
bw_params->num_channels = bios_info->ma_channel_number;
diff --git a/drivers/gpu/drm/amd/display/dc/core/dc.c b/drivers/gpu/drm/amd/display/dc/core/dc.c
index cf3893a2f8ce..242bcb30dd34 100644
--- a/drivers/gpu/drm/amd/display/dc/core/dc.c
+++ b/drivers/gpu/drm/amd/display/dc/core/dc.c
@@ -940,17 +940,18 @@ static void dc_destruct(struct dc *dc)
if (dc->link_srv)
link_destroy_link_service(&dc->link_srv);
- if (dc->ctx->gpio_service)
- dal_gpio_service_destroy(&dc->ctx->gpio_service);
+ if (dc->ctx) {
+ if (dc->ctx->gpio_service)
+ dal_gpio_service_destroy(&dc->ctx->gpio_service);
- if (dc->ctx->created_bios)
- dal_bios_parser_destroy(&dc->ctx->dc_bios);
+ if (dc->ctx->created_bios)
+ dal_bios_parser_destroy(&dc->ctx->dc_bios);
+ kfree(dc->ctx->logger);
+ dc_perf_trace_destroy(&dc->ctx->perf_trace);
- kfree(dc->ctx->logger);
- dc_perf_trace_destroy(&dc->ctx->perf_trace);
-
- kfree(dc->ctx);
- dc->ctx = NULL;
+ kfree(dc->ctx);
+ dc->ctx = NULL;
+ }
kfree(dc->bw_vbios);
dc->bw_vbios = NULL;
@@ -6338,3 +6339,21 @@ bool dc_can_clear_cursor_limit(struct dc *dc)
return false;
}
+
+void dc_get_underflow_debug_data_for_otg(struct dc *dc, int primary_otg_inst,
+ struct dc_underflow_debug_data *out_data)
+{
+ struct timing_generator *tg = NULL;
+
+ for (int i = 0; i < MAX_PIPES; i++) {
+ if (dc->res_pool->timing_generators[i] &&
+ dc->res_pool->timing_generators[i]->inst == primary_otg_inst) {
+ tg = dc->res_pool->timing_generators[i];
+ break;
+ }
+ }
+
+ dc_exit_ips_for_hw_access(dc);
+ if (dc->hwss.get_underflow_debug_data)
+ dc->hwss.get_underflow_debug_data(dc, tg, out_data);
+}
diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_resource.c b/drivers/gpu/drm/amd/display/dc/core/dc_resource.c
index 4d6181e7c612..d712548b1927 100644
--- a/drivers/gpu/drm/amd/display/dc/core/dc_resource.c
+++ b/drivers/gpu/drm/amd/display/dc/core/dc_resource.c
@@ -165,7 +165,13 @@ enum dce_version resource_parse_asic_id(struct hw_asic_id asic_id)
case FAMILY_NV:
dc_version = DCN_VERSION_2_0;
- if (asic_id.chip_id == DEVICE_ID_NV_13FE || asic_id.chip_id == DEVICE_ID_NV_143F) {
+ if (asic_id.chip_id == DEVICE_ID_NV_13FE ||
+ asic_id.chip_id == DEVICE_ID_NV_143F ||
+ asic_id.chip_id == DEVICE_ID_NV_13F9 ||
+ asic_id.chip_id == DEVICE_ID_NV_13FA ||
+ asic_id.chip_id == DEVICE_ID_NV_13FB ||
+ asic_id.chip_id == DEVICE_ID_NV_13FC ||
+ asic_id.chip_id == DEVICE_ID_NV_13DB) {
dc_version = DCN_VERSION_2_01;
break;
}
diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h
index 5653c1673aec..18c68e531f71 100644
--- a/drivers/gpu/drm/amd/display/dc/dc.h
+++ b/drivers/gpu/drm/amd/display/dc/dc.h
@@ -55,7 +55,7 @@ struct aux_payload;
struct set_config_cmd_payload;
struct dmub_notification;
-#define DC_VER "3.2.343"
+#define DC_VER "3.2.344"
/**
* MAX_SURFACES - representative of the upper bound of surfaces that can be piped to a single CRTC
@@ -1073,6 +1073,7 @@ struct dc_debug_options {
unsigned int force_mall_ss_num_ways;
bool alloc_extra_way_for_cursor;
uint32_t subvp_extra_lines;
+ bool disable_force_pstate_allow_on_hw_release;
bool force_usr_allow;
/* uses value at boot and disables switch */
bool disable_dtb_ref_clk_switch;
@@ -1311,6 +1312,32 @@ union dc_3dlut_state {
};
+#define MATRIX_9C__DIM_128_ALIGNED_LEN 16 // 9+8 : 9 * 8 + 7 * 8 = 72 + 56 = 128 % 128 = 0
+#define MATRIX_17C__DIM_128_ALIGNED_LEN 32 //17+15: 17 * 8 + 15 * 8 = 136 + 120 = 256 % 128 = 0
+#define MATRIX_33C__DIM_128_ALIGNED_LEN 64 //17+47: 17 * 8 + 47 * 8 = 136 + 376 = 512 % 128 = 0
+
+struct lut_rgb {
+ uint16_t b;
+ uint16_t g;
+ uint16_t r;
+ uint16_t padding;
+};
+
+//this structure maps directly to how the lut will read it from memory
+struct lut_mem_mapping {
+ union {
+ //NATIVE MODE 1, 2
+ //RGB layout [b][g][r] //red is 128 byte aligned
+ //BGR layout [r][g][b] //blue is 128 byte aligned
+ struct lut_rgb rgb_17c[17][17][MATRIX_17C__DIM_128_ALIGNED_LEN];
+ struct lut_rgb rgb_33c[33][33][MATRIX_33C__DIM_128_ALIGNED_LEN];
+
+ //TRANSFORMED
+ uint16_t linear_rgb[(33*33*33*4/128+1)*128];
+ };
+ uint16_t size;
+};
+
struct dc_rmcm_3dlut {
bool isInUse;
const struct dc_stream_state *stream;
@@ -1792,6 +1819,23 @@ struct dc_surface_update {
struct dc_bias_and_scale bias_and_scale;
};
+struct dc_underflow_debug_data {
+ uint32_t otg_inst;
+ uint32_t otg_underflow;
+ uint32_t h_position;
+ uint32_t v_position;
+ uint32_t otg_frame_count;
+ struct dc_underflow_per_hubp_debug_data {
+ uint32_t hubp_underflow;
+ uint32_t hubp_in_blank;
+ uint32_t hubp_readline;
+ uint32_t det_config_error;
+ } hubps[MAX_PIPES];
+ uint32_t curr_det_sizes[MAX_PIPES];
+ uint32_t target_det_sizes[MAX_PIPES];
+ uint32_t compbuf_config_error;
+};
+
/*
* Create a new surface with default parameters;
*/
@@ -2686,4 +2730,17 @@ bool dc_is_timing_changed(struct dc_stream_state *cur_stream,
bool dc_is_cursor_limit_pending(struct dc *dc);
bool dc_can_clear_cursor_limit(struct dc *dc);
+/**
+ * dc_get_underflow_debug_data_for_otg() - Retrieve underflow debug data.
+ *
+ * @dc: Pointer to the display core context.
+ * @primary_otg_inst: Instance index of the primary OTG that underflowed.
+ * @out_data: Pointer to a dc_underflow_debug_data struct to be filled with debug information.
+ *
+ * This function collects and logs underflow-related HW states when underflow happens,
+ * including OTG underflow status, current read positions, frame count, and per-HUBP debug data.
+ * The results are stored in the provided out_data structure for further analysis or logging.
+ */
+void dc_get_underflow_debug_data_for_otg(struct dc *dc, int primary_otg_inst, struct dc_underflow_debug_data *out_data);
+
#endif /* DC_INTERFACE_H_ */
diff --git a/drivers/gpu/drm/amd/display/dc/dml/dcn301/dcn301_fpu.c b/drivers/gpu/drm/amd/display/dc/dml/dcn301/dcn301_fpu.c
index 0c0b2d67c9cd..2066a65c69bb 100644
--- a/drivers/gpu/drm/amd/display/dc/dml/dcn301/dcn301_fpu.c
+++ b/drivers/gpu/drm/amd/display/dc/dml/dcn301/dcn301_fpu.c
@@ -326,7 +326,7 @@ void dcn301_fpu_update_bw_bounding_box(struct dc *dc, struct clk_bw_params *bw_p
struct dcn301_resource_pool *pool = TO_DCN301_RES_POOL(dc->res_pool);
struct clk_limit_table *clk_table = &bw_params->clk_table;
unsigned int i, closest_clk_lvl;
- int j;
+ int j = 0, max_dispclk_mhz = 0, max_dppclk_mhz = 0;
dc_assert_fp_enabled();
@@ -338,6 +338,15 @@ void dcn301_fpu_update_bw_bounding_box(struct dc *dc, struct clk_bw_params *bw_p
dcn3_01_soc.num_chans = bw_params->num_channels;
ASSERT(clk_table->num_entries);
+
+ /* Prepass to find max clocks independent of voltage level. */
+ for (i = 0; i < clk_table->num_entries; ++i) {
+ if (clk_table->entries[i].dispclk_mhz > max_dispclk_mhz)
+ max_dispclk_mhz = clk_table->entries[i].dispclk_mhz;
+ if (clk_table->entries[i].dppclk_mhz > max_dppclk_mhz)
+ max_dppclk_mhz = clk_table->entries[i].dppclk_mhz;
+ }
+
for (i = 0; i < clk_table->num_entries; i++) {
/* loop backwards*/
for (closest_clk_lvl = 0, j = dcn3_01_soc.num_states - 1; j >= 0; j--) {
@@ -353,8 +362,13 @@ void dcn301_fpu_update_bw_bounding_box(struct dc *dc, struct clk_bw_params *bw_p
s[i].socclk_mhz = clk_table->entries[i].socclk_mhz;
s[i].dram_speed_mts = clk_table->entries[i].memclk_mhz * 2;
- s[i].dispclk_mhz = dcn3_01_soc.clock_limits[closest_clk_lvl].dispclk_mhz;
- s[i].dppclk_mhz = dcn3_01_soc.clock_limits[closest_clk_lvl].dppclk_mhz;
+ /* Clocks independent of voltage level. */
+ s[i].dispclk_mhz = max_dispclk_mhz ? max_dispclk_mhz :
+ dcn3_01_soc.clock_limits[closest_clk_lvl].dispclk_mhz;
+
+ s[i].dppclk_mhz = max_dppclk_mhz ? max_dppclk_mhz :
+ dcn3_01_soc.clock_limits[closest_clk_lvl].dppclk_mhz;
+
s[i].dram_bw_per_chan_gbps =
dcn3_01_soc.clock_limits[closest_clk_lvl].dram_bw_per_chan_gbps;
s[i].dscclk_mhz = dcn3_01_soc.clock_limits[closest_clk_lvl].dscclk_mhz;
diff --git a/drivers/gpu/drm/amd/display/dc/hubbub/dcn30/dcn30_hubbub.c b/drivers/gpu/drm/amd/display/dc/hubbub/dcn30/dcn30_hubbub.c
index d347bb06577a..e7e5f6d4778e 100644
--- a/drivers/gpu/drm/amd/display/dc/hubbub/dcn30/dcn30_hubbub.c
+++ b/drivers/gpu/drm/amd/display/dc/hubbub/dcn30/dcn30_hubbub.c
@@ -440,6 +440,35 @@ void hubbub3_init_watermarks(struct hubbub *hubbub)
REG_WRITE(DCHUBBUB_ARB_ALLOW_DRAM_CLK_CHANGE_WATERMARK_D, reg);
}
+void hubbub3_get_det_sizes(struct hubbub *hubbub, uint32_t *curr_det_sizes, uint32_t *target_det_sizes)
+{
+ struct dcn20_hubbub *hubbub1 = TO_DCN20_HUBBUB(hubbub);
+
+ REG_GET_2(DCHUBBUB_DET0_CTRL, DET0_SIZE_CURRENT, &curr_det_sizes[0],
+ DET0_SIZE, &target_det_sizes[0]);
+
+ REG_GET_2(DCHUBBUB_DET1_CTRL, DET1_SIZE_CURRENT, &curr_det_sizes[1],
+ DET1_SIZE, &target_det_sizes[1]);
+
+ REG_GET_2(DCHUBBUB_DET2_CTRL, DET2_SIZE_CURRENT, &curr_det_sizes[2],
+ DET2_SIZE, &target_det_sizes[2]);
+
+ REG_GET_2(DCHUBBUB_DET3_CTRL, DET3_SIZE_CURRENT, &curr_det_sizes[3],
+ DET3_SIZE, &target_det_sizes[3]);
+
+}
+
+uint32_t hubbub3_compbuf_config_error(struct hubbub *hubbub)
+{
+ struct dcn20_hubbub *hubbub1 = TO_DCN20_HUBBUB(hubbub);
+ uint32_t compbuf_config_error = 0;
+
+ REG_GET(DCHUBBUB_COMPBUF_CTRL, CONFIG_ERROR,
+ &compbuf_config_error);
+
+ return compbuf_config_error;
+}
+
static const struct hubbub_funcs hubbub30_funcs = {
.update_dchub = hubbub2_update_dchub,
.init_dchub_sys_ctx = hubbub3_init_dchub_sys_ctx,
@@ -457,6 +486,8 @@ static const struct hubbub_funcs hubbub30_funcs = {
.force_pstate_change_control = hubbub3_force_pstate_change_control,
.init_watermarks = hubbub3_init_watermarks,
.hubbub_read_state = hubbub2_read_state,
+ .get_det_sizes = hubbub3_get_det_sizes,
+ .compbuf_config_error = hubbub3_compbuf_config_error,
};
void hubbub3_construct(struct dcn20_hubbub *hubbub3,
diff --git a/drivers/gpu/drm/amd/display/dc/hubbub/dcn30/dcn30_hubbub.h b/drivers/gpu/drm/amd/display/dc/hubbub/dcn30/dcn30_hubbub.h
index ca6233e8f1f4..49a469969d36 100644
--- a/drivers/gpu/drm/amd/display/dc/hubbub/dcn30/dcn30_hubbub.h
+++ b/drivers/gpu/drm/amd/display/dc/hubbub/dcn30/dcn30_hubbub.h
@@ -133,4 +133,10 @@ void hubbub3_force_pstate_change_control(struct hubbub *hubbub,
void hubbub3_init_watermarks(struct hubbub *hubbub);
+void hubbub3_get_det_sizes(struct hubbub *hubbub,
+ uint32_t *curr_det_sizes,
+ uint32_t *target_det_sizes);
+
+uint32_t hubbub3_compbuf_config_error(struct hubbub *hubbub);
+
#endif
diff --git a/drivers/gpu/drm/amd/display/dc/hubbub/dcn31/dcn31_hubbub.c b/drivers/gpu/drm/amd/display/dc/hubbub/dcn31/dcn31_hubbub.c
index b98505b240a7..cdb20251a154 100644
--- a/drivers/gpu/drm/amd/display/dc/hubbub/dcn31/dcn31_hubbub.c
+++ b/drivers/gpu/drm/amd/display/dc/hubbub/dcn31/dcn31_hubbub.c
@@ -1071,6 +1071,8 @@ static const struct hubbub_funcs hubbub31_funcs = {
.program_compbuf_size = dcn31_program_compbuf_size,
.init_crb = dcn31_init_crb,
.hubbub_read_state = hubbub2_read_state,
+ .get_det_sizes = hubbub3_get_det_sizes,
+ .compbuf_config_error = hubbub3_compbuf_config_error,
};
void hubbub31_construct(struct dcn20_hubbub *hubbub31,
diff --git a/drivers/gpu/drm/amd/display/dc/hubbub/dcn32/dcn32_hubbub.c b/drivers/gpu/drm/amd/display/dc/hubbub/dcn32/dcn32_hubbub.c
index 32a6be543105..92957398ac0a 100644
--- a/drivers/gpu/drm/amd/display/dc/hubbub/dcn32/dcn32_hubbub.c
+++ b/drivers/gpu/drm/amd/display/dc/hubbub/dcn32/dcn32_hubbub.c
@@ -1009,6 +1009,8 @@ static const struct hubbub_funcs hubbub32_funcs = {
.force_usr_retraining_allow = hubbub32_force_usr_retraining_allow,
.set_request_limit = hubbub32_set_request_limit,
.get_mall_en = hubbub32_get_mall_en,
+ .get_det_sizes = hubbub3_get_det_sizes,
+ .compbuf_config_error = hubbub3_compbuf_config_error,
};
void hubbub32_construct(struct dcn20_hubbub *hubbub2,
diff --git a/drivers/gpu/drm/amd/display/dc/hubbub/dcn35/dcn35_hubbub.c b/drivers/gpu/drm/amd/display/dc/hubbub/dcn35/dcn35_hubbub.c
index 6d41953011f5..a443722a8632 100644
--- a/drivers/gpu/drm/amd/display/dc/hubbub/dcn35/dcn35_hubbub.c
+++ b/drivers/gpu/drm/amd/display/dc/hubbub/dcn35/dcn35_hubbub.c
@@ -589,6 +589,8 @@ static const struct hubbub_funcs hubbub35_funcs = {
.hubbub_read_state = hubbub2_read_state,
.force_usr_retraining_allow = hubbub32_force_usr_retraining_allow,
.dchubbub_init = hubbub35_init,
+ .get_det_sizes = hubbub3_get_det_sizes,
+ .compbuf_config_error = hubbub3_compbuf_config_error,
};
void hubbub35_construct(struct dcn20_hubbub *hubbub2,
diff --git a/drivers/gpu/drm/amd/display/dc/hubbub/dcn401/dcn401_hubbub.c b/drivers/gpu/drm/amd/display/dc/hubbub/dcn401/dcn401_hubbub.c
index 92fab471b183..a36273a52880 100644
--- a/drivers/gpu/drm/amd/display/dc/hubbub/dcn401/dcn401_hubbub.c
+++ b/drivers/gpu/drm/amd/display/dc/hubbub/dcn401/dcn401_hubbub.c
@@ -1247,6 +1247,8 @@ static const struct hubbub_funcs hubbub4_01_funcs = {
.program_compbuf_segments = dcn401_program_compbuf_segments,
.wait_for_det_update = dcn401_wait_for_det_update,
.program_arbiter = dcn401_program_arbiter,
+ .get_det_sizes = hubbub3_get_det_sizes,
+ .compbuf_config_error = hubbub3_compbuf_config_error,
};
void hubbub401_construct(struct dcn20_hubbub *hubbub2,
diff --git a/drivers/gpu/drm/amd/display/dc/hubp/dcn10/dcn10_hubp.h b/drivers/gpu/drm/amd/display/dc/hubp/dcn10/dcn10_hubp.h
index f8f991785d4f..cf2eb9793008 100644
--- a/drivers/gpu/drm/amd/display/dc/hubp/dcn10/dcn10_hubp.h
+++ b/drivers/gpu/drm/amd/display/dc/hubp/dcn10/dcn10_hubp.h
@@ -104,7 +104,8 @@
SRI(DCN_SURF1_TTU_CNTL1, HUBPREQ, id),\
SRI(DCN_CUR0_TTU_CNTL0, HUBPREQ, id),\
SRI(DCN_CUR0_TTU_CNTL1, HUBPREQ, id),\
- SRI(HUBP_CLK_CNTL, HUBP, id)
+ SRI(HUBP_CLK_CNTL, HUBP, id),\
+ SRI(HUBPRET_READ_LINE_VALUE, HUBPRET, id)
/* Register address initialization macro for ASICs with VM */
#define HUBP_REG_LIST_DCN_VM(id)\
@@ -249,7 +250,8 @@
uint32_t CURSOR_POSITION; \
uint32_t CURSOR_HOT_SPOT; \
uint32_t CURSOR_DST_OFFSET; \
- uint32_t HUBP_CLK_CNTL
+ uint32_t HUBP_CLK_CNTL; \
+ uint32_t HUBPRET_READ_LINE_VALUE
#define HUBP_SF(reg_name, field_name, post_fix)\
.field_name = reg_name ## __ ## field_name ## post_fix
@@ -622,6 +624,8 @@
type DCN_VM_SYSTEM_APERTURE_DEFAULT_SYSTEM;\
type DCN_VM_SYSTEM_APERTURE_DEFAULT_ADDR_MSB;\
type DCN_VM_SYSTEM_APERTURE_DEFAULT_ADDR_LSB;\
+ type PIPE_READ_LINE;\
+ type HUBP_SEG_ALLOC_ERR_STATUS;\
/* todo: get these from GVM instead of reading registers ourselves */\
type PAGE_DIRECTORY_ENTRY_HI32;\
type PAGE_DIRECTORY_ENTRY_LO32;\
@@ -671,6 +675,7 @@ struct dcn_fl_regs_st {
uint32_t lut_done;
uint32_t lut_addr_mode;
uint32_t lut_width;
+ uint32_t lut_mpc_width;
uint32_t lut_tmz;
uint32_t lut_crossbar_sel_r;
uint32_t lut_crossbar_sel_g;
diff --git a/drivers/gpu/drm/amd/display/dc/hubp/dcn20/dcn20_hubp.h b/drivers/gpu/drm/amd/display/dc/hubp/dcn20/dcn20_hubp.h
index 62369be070ea..f325db555102 100644
--- a/drivers/gpu/drm/amd/display/dc/hubp/dcn20/dcn20_hubp.h
+++ b/drivers/gpu/drm/amd/display/dc/hubp/dcn20/dcn20_hubp.h
@@ -264,6 +264,7 @@
type HUBP_3DLUT_DONE;\
type HUBP_3DLUT_ADDRESSING_MODE;\
type HUBP_3DLUT_WIDTH;\
+ type HUBP_3DLUT_MPC_WIDTH;\
type HUBP_3DLUT_TMZ;\
type HUBP_3DLUT_CROSSBAR_SELECT_Y_G;\
type HUBP_3DLUT_CROSSBAR_SELECT_CB_B;\
diff --git a/drivers/gpu/drm/amd/display/dc/hubp/dcn30/dcn30_hubp.c b/drivers/gpu/drm/amd/display/dc/hubp/dcn30/dcn30_hubp.c
index 0da70b50e86d..556214b2227d 100644
--- a/drivers/gpu/drm/amd/display/dc/hubp/dcn30/dcn30_hubp.c
+++ b/drivers/gpu/drm/amd/display/dc/hubp/dcn30/dcn30_hubp.c
@@ -505,6 +505,30 @@ void hubp3_init(struct hubp *hubp)
hubp_reset(hubp);
}
+uint32_t hubp3_get_current_read_line(struct hubp *hubp)
+{
+ uint32_t read_line = 0;
+ struct dcn20_hubp *hubp2 = TO_DCN20_HUBP(hubp);
+
+ REG_GET(HUBPRET_READ_LINE_VALUE,
+ PIPE_READ_LINE,
+ &read_line);
+
+ return read_line;
+}
+
+unsigned int hubp3_get_underflow_status(struct hubp *hubp)
+{
+ uint32_t hubp_underflow = 0;
+ struct dcn20_hubp *hubp2 = TO_DCN20_HUBP(hubp);
+
+ REG_GET(DCHUBP_CNTL,
+ HUBP_UNDERFLOW_STATUS,
+ &hubp_underflow);
+
+ return hubp_underflow;
+}
+
static struct hubp_funcs dcn30_hubp_funcs = {
.hubp_enable_tripleBuffer = hubp2_enable_triplebuffer,
.hubp_is_triplebuffer_enabled = hubp2_is_triplebuffer_enabled,
@@ -534,6 +558,8 @@ static struct hubp_funcs dcn30_hubp_funcs = {
.hubp_soft_reset = hubp1_soft_reset,
.hubp_set_flip_int = hubp1_set_flip_int,
.hubp_clear_tiling = hubp3_clear_tiling,
+ .hubp_get_underflow_status = hubp3_get_underflow_status,
+ .hubp_get_current_read_line = hubp3_get_current_read_line,
};
bool hubp3_construct(
diff --git a/drivers/gpu/drm/amd/display/dc/hubp/dcn30/dcn30_hubp.h b/drivers/gpu/drm/amd/display/dc/hubp/dcn30/dcn30_hubp.h
index b7d7adf0b58c..842f4eb72cc8 100644
--- a/drivers/gpu/drm/amd/display/dc/hubp/dcn30/dcn30_hubp.h
+++ b/drivers/gpu/drm/amd/display/dc/hubp/dcn30/dcn30_hubp.h
@@ -243,7 +243,8 @@
HUBP_SF(HUBPREQ0_FLIP_PARAMETERS_6, REFCYC_PER_META_CHUNK_FLIP_C, mask_sh),\
HUBP_SF(HUBPREQ0_VBLANK_PARAMETERS_5, REFCYC_PER_VM_GROUP_VBLANK, mask_sh),\
HUBP_SF(HUBPREQ0_VBLANK_PARAMETERS_6, REFCYC_PER_VM_REQ_VBLANK, mask_sh),\
- HUBP_SF(HUBP0_DCHUBP_REQ_SIZE_CONFIG, VM_GROUP_SIZE, mask_sh)
+ HUBP_SF(HUBP0_DCHUBP_REQ_SIZE_CONFIG, VM_GROUP_SIZE, mask_sh),\
+ HUBP_SF(HUBPRET0_HUBPRET_READ_LINE_VALUE, PIPE_READ_LINE, mask_sh)
bool hubp3_construct(
struct dcn20_hubp *hubp2,
@@ -299,6 +300,11 @@ void hubp3_init(struct hubp *hubp);
void hubp3_clear_tiling(struct hubp *hubp);
+uint32_t hubp3_get_current_read_line(struct hubp *hubp);
+
+uint32_t hubp3_get_underflow_status(struct hubp *hubp);
+
+
#endif /* __DC_HUBP_DCN30_H__ */
diff --git a/drivers/gpu/drm/amd/display/dc/hubp/dcn31/dcn31_hubp.c b/drivers/gpu/drm/amd/display/dc/hubp/dcn31/dcn31_hubp.c
index 7fd582a8a4ba..47101847c2b7 100644
--- a/drivers/gpu/drm/amd/display/dc/hubp/dcn31/dcn31_hubp.c
+++ b/drivers/gpu/drm/amd/display/dc/hubp/dcn31/dcn31_hubp.c
@@ -68,6 +68,18 @@ void hubp31_program_extended_blank_value(
hubp31_program_extended_blank(hubp, min_dst_y_next_start_optimized);
}
+uint32_t hubp31_get_det_config_error(struct hubp *hubp)
+{
+ uint32_t config_error = 0;
+ struct dcn20_hubp *hubp2 = TO_DCN20_HUBP(hubp);
+
+ REG_GET(DCHUBP_CNTL,
+ HUBP_SEG_ALLOC_ERR_STATUS,
+ &config_error);
+
+ return config_error;
+}
+
static struct hubp_funcs dcn31_hubp_funcs = {
.hubp_enable_tripleBuffer = hubp2_enable_triplebuffer,
.hubp_is_triplebuffer_enabled = hubp2_is_triplebuffer_enabled,
@@ -98,6 +110,9 @@ static struct hubp_funcs dcn31_hubp_funcs = {
.hubp_in_blank = hubp1_in_blank,
.program_extended_blank = hubp31_program_extended_blank,
.hubp_clear_tiling = hubp3_clear_tiling,
+ .hubp_get_underflow_status = hubp3_get_underflow_status,
+ .hubp_get_current_read_line = hubp3_get_current_read_line,
+ .hubp_get_det_config_error = hubp31_get_det_config_error,
};
bool hubp31_construct(
diff --git a/drivers/gpu/drm/amd/display/dc/hubp/dcn31/dcn31_hubp.h b/drivers/gpu/drm/amd/display/dc/hubp/dcn31/dcn31_hubp.h
index d688db79b750..5952c4671507 100644
--- a/drivers/gpu/drm/amd/display/dc/hubp/dcn31/dcn31_hubp.h
+++ b/drivers/gpu/drm/amd/display/dc/hubp/dcn31/dcn31_hubp.h
@@ -228,7 +228,9 @@
HUBP_SF(HUBPREQ0_FLIP_PARAMETERS_6, REFCYC_PER_META_CHUNK_FLIP_C, mask_sh),\
HUBP_SF(HUBPREQ0_VBLANK_PARAMETERS_5, REFCYC_PER_VM_GROUP_VBLANK, mask_sh),\
HUBP_SF(HUBPREQ0_VBLANK_PARAMETERS_6, REFCYC_PER_VM_REQ_VBLANK, mask_sh),\
- HUBP_SF(HUBP0_DCHUBP_REQ_SIZE_CONFIG, VM_GROUP_SIZE, mask_sh)
+ HUBP_SF(HUBP0_DCHUBP_REQ_SIZE_CONFIG, VM_GROUP_SIZE, mask_sh),\
+ HUBP_SF(HUBPRET0_HUBPRET_READ_LINE_VALUE, PIPE_READ_LINE, mask_sh),\
+ HUBP_SF(HUBP0_DCHUBP_CNTL, HUBP_SEG_ALLOC_ERR_STATUS, mask_sh)
bool hubp31_construct(
@@ -246,4 +248,6 @@ void hubp31_set_unbounded_requesting(struct hubp *hubp, bool enable);
void hubp31_program_extended_blank_value(
struct hubp *hubp, unsigned int min_dst_y_next_start_optimized);
+uint32_t hubp31_get_det_config_error(struct hubp *hubp);
+
#endif /* __DC_HUBP_DCN31_H__ */
diff --git a/drivers/gpu/drm/amd/display/dc/hubp/dcn32/dcn32_hubp.c b/drivers/gpu/drm/amd/display/dc/hubp/dcn32/dcn32_hubp.c
index f3a21c623f44..a5f23bb2a76a 100644
--- a/drivers/gpu/drm/amd/display/dc/hubp/dcn32/dcn32_hubp.c
+++ b/drivers/gpu/drm/amd/display/dc/hubp/dcn32/dcn32_hubp.c
@@ -206,6 +206,9 @@ static struct hubp_funcs dcn32_hubp_funcs = {
.hubp_update_mall_sel = hubp32_update_mall_sel,
.hubp_prepare_subvp_buffering = hubp32_prepare_subvp_buffering,
.hubp_clear_tiling = hubp3_clear_tiling,
+ .hubp_get_underflow_status = hubp3_get_underflow_status,
+ .hubp_get_current_read_line = hubp3_get_current_read_line,
+ .hubp_get_det_config_error = hubp31_get_det_config_error,
};
bool hubp32_construct(
diff --git a/drivers/gpu/drm/amd/display/dc/hubp/dcn35/dcn35_hubp.c b/drivers/gpu/drm/amd/display/dc/hubp/dcn35/dcn35_hubp.c
index 6d060ba12da8..b140808f21af 100644
--- a/drivers/gpu/drm/amd/display/dc/hubp/dcn35/dcn35_hubp.c
+++ b/drivers/gpu/drm/amd/display/dc/hubp/dcn35/dcn35_hubp.c
@@ -218,6 +218,9 @@ static struct hubp_funcs dcn35_hubp_funcs = {
.hubp_in_blank = hubp1_in_blank,
.program_extended_blank = hubp31_program_extended_blank_value,
.hubp_clear_tiling = hubp3_clear_tiling,
+ .hubp_get_underflow_status = hubp3_get_underflow_status,
+ .hubp_get_current_read_line = hubp3_get_current_read_line,
+ .hubp_get_det_config_error = hubp31_get_det_config_error,
};
bool hubp35_construct(
diff --git a/drivers/gpu/drm/amd/display/dc/hubp/dcn401/dcn401_hubp.c b/drivers/gpu/drm/amd/display/dc/hubp/dcn401/dcn401_hubp.c
index 705b98b1b6cc..0fcbc6a35be6 100644
--- a/drivers/gpu/drm/amd/display/dc/hubp/dcn401/dcn401_hubp.c
+++ b/drivers/gpu/drm/amd/display/dc/hubp/dcn401/dcn401_hubp.c
@@ -127,6 +127,43 @@ void hubp401_program_3dlut_fl_format(struct hubp *hubp, enum hubp_3dlut_fl_forma
REG_UPDATE(_3DLUT_FL_CONFIG, HUBP0_3DLUT_FL_FORMAT, format);
}
+void hubp401_program_3dlut_fl_config(
+ struct hubp *hubp,
+ struct hubp_fl_3dlut_config *cfg)
+{
+ struct dcn20_hubp *hubp2 = TO_DCN20_HUBP(hubp);
+
+ uint32_t mpc_width = {(cfg->width == 17) ? 0 : 1};
+ uint32_t width = {cfg->width};
+
+ if (cfg->layout == DC_CM2_GPU_MEM_LAYOUT_1D_PACKED_LINEAR)
+ width = (cfg->width == 17) ? 4916 : 35940;
+
+ REG_UPDATE_2(_3DLUT_FL_CONFIG,
+ HUBP0_3DLUT_FL_MODE, cfg->mode,
+ HUBP0_3DLUT_FL_FORMAT, cfg->format);
+
+ REG_UPDATE_2(_3DLUT_FL_BIAS_SCALE,
+ HUBP0_3DLUT_FL_BIAS, cfg->bias,
+ HUBP0_3DLUT_FL_SCALE, cfg->scale);
+
+ REG_UPDATE(HUBP_3DLUT_ADDRESS_HIGH,
+ HUBP_3DLUT_ADDRESS_HIGH, cfg->address.lut3d.addr.high_part);
+ REG_UPDATE(HUBP_3DLUT_ADDRESS_LOW,
+ HUBP_3DLUT_ADDRESS_LOW, cfg->address.lut3d.addr.low_part);
+
+ //cross bar
+ REG_UPDATE_8(HUBP_3DLUT_CONTROL,
+ HUBP_3DLUT_MPC_WIDTH, mpc_width,
+ HUBP_3DLUT_WIDTH, width,
+ HUBP_3DLUT_CROSSBAR_SELECT_CR_R, cfg->crossbar_bit_slice_cr_r,
+ HUBP_3DLUT_CROSSBAR_SELECT_Y_G, cfg->crossbar_bit_slice_y_g,
+ HUBP_3DLUT_CROSSBAR_SELECT_CB_B, cfg->crossbar_bit_slice_cb_b,
+ HUBP_3DLUT_ADDRESSING_MODE, cfg->addr_mode,
+ HUBP_3DLUT_TMZ, cfg->protection_bits,
+ HUBP_3DLUT_ENABLE, cfg->enabled ? 1 : 0);
+}
+
void hubp401_update_mall_sel(struct hubp *hubp, uint32_t mall_sel, bool c_cursor)
{
struct dcn20_hubp *hubp2 = TO_DCN20_HUBP(hubp);
@@ -1033,6 +1070,10 @@ static struct hubp_funcs dcn401_hubp_funcs = {
.hubp_program_3dlut_fl_crossbar = hubp401_program_3dlut_fl_crossbar,
.hubp_get_3dlut_fl_done = hubp401_get_3dlut_fl_done,
.hubp_clear_tiling = hubp401_clear_tiling,
+ .hubp_program_3dlut_fl_config = hubp401_program_3dlut_fl_config,
+ .hubp_get_underflow_status = hubp3_get_underflow_status,
+ .hubp_get_current_read_line = hubp3_get_current_read_line,
+ .hubp_get_det_config_error = hubp31_get_det_config_error,
};
bool hubp401_construct(
diff --git a/drivers/gpu/drm/amd/display/dc/hubp/dcn401/dcn401_hubp.h b/drivers/gpu/drm/amd/display/dc/hubp/dcn401/dcn401_hubp.h
index 608e6153fa68..fdabbeec8ffa 100644
--- a/drivers/gpu/drm/amd/display/dc/hubp/dcn401/dcn401_hubp.h
+++ b/drivers/gpu/drm/amd/display/dc/hubp/dcn401/dcn401_hubp.h
@@ -252,7 +252,9 @@
HUBP_SF(HUBP0_DCHUBP_MCACHEID_CONFIG, MCACHEID_MALL_PREF_1H_P0, mask_sh),\
HUBP_SF(HUBP0_DCHUBP_MCACHEID_CONFIG, MCACHEID_MALL_PREF_2H_P0, mask_sh),\
HUBP_SF(HUBP0_DCHUBP_MCACHEID_CONFIG, MCACHEID_MALL_PREF_1H_P1, mask_sh),\
- HUBP_SF(HUBP0_DCHUBP_MCACHEID_CONFIG, MCACHEID_MALL_PREF_2H_P1, mask_sh)
+ HUBP_SF(HUBP0_DCHUBP_MCACHEID_CONFIG, MCACHEID_MALL_PREF_2H_P1, mask_sh),\
+ HUBP_SF(HUBPRET0_HUBPRET_READ_LINE_VALUE, PIPE_READ_LINE, mask_sh),\
+ HUBP_SF(HUBP0_DCHUBP_CNTL, HUBP_SEG_ALLOC_ERR_STATUS, mask_sh)
void hubp401_update_mall_sel(struct hubp *hubp, uint32_t mall_sel, bool c_cursor);
@@ -349,6 +351,10 @@ void hubp401_program_3dlut_fl_format(struct hubp *hubp, enum hubp_3dlut_fl_forma
void hubp401_program_3dlut_fl_mode(struct hubp *hubp, enum hubp_3dlut_fl_mode mode);
+void hubp401_program_3dlut_fl_config(
+ struct hubp *hubp,
+ struct hubp_fl_3dlut_config *cfg);
+
void hubp401_clear_tiling(struct hubp *hubp);
void hubp401_vready_at_or_After_vsync(struct hubp *hubp,
diff --git a/drivers/gpu/drm/amd/display/dc/hwss/dcn10/dcn10_hwseq.c b/drivers/gpu/drm/amd/display/dc/hwss/dcn10/dcn10_hwseq.c
index 39910f73ecd0..79c9bea78c47 100644
--- a/drivers/gpu/drm/amd/display/dc/hwss/dcn10/dcn10_hwseq.c
+++ b/drivers/gpu/drm/amd/display/dc/hwss/dcn10/dcn10_hwseq.c
@@ -328,19 +328,25 @@ static void dcn10_log_hubp_states(struct dc *dc, void *log_ctx)
}
DTN_INFO("\n=======HUBP FL======\n");
- DTN_INFO(
- "HUBP FL: Enabled Done adr_mode width tmz xbar_sel_R xbar_sel_G xbar_sel_B adr_hi adr_low REFCYC Bias Scale Mode Format\n");
+ char pLabels[18][50] = {
+ "inst", "Enabled ", "Done ", "adr_mode ", "width ", "mpc_width ",
+ "tmz", "xbar_sel_R", "xbar_sel_G", "xbar_sel_B", "adr_hi ",
+ "adr_low", "REFCYC", "Bias", "Scale", "Mode",
+ "Format", "prefetch"};
+
for (i = 0; i < pool->pipe_count; i++) {
struct dcn_hubp_state *s = &(TO_DCN10_HUBP(pool->hubps[i])->state);
struct dcn_fl_regs_st *fl_regs = &s->fl_regs;
+ struct _vcs_dpi_display_dlg_regs_st *dlg_regs = &s->dlg_attr;
if (!s->blank_en) {
- DTN_INFO("[%2d]: %5xh %6xh %5d %6d %8xh %2xh %6xh %6d %8d %8d %7d %8xh %5x %5x %5x",
+ uint32_t values[] = {
pool->hubps[i]->inst,
fl_regs->lut_enable,
fl_regs->lut_done,
fl_regs->lut_addr_mode,
fl_regs->lut_width,
+ fl_regs->lut_mpc_width,
fl_regs->lut_tmz,
fl_regs->lut_crossbar_sel_r,
fl_regs->lut_crossbar_sel_g,
@@ -351,8 +357,13 @@ static void dcn10_log_hubp_states(struct dc *dc, void *log_ctx)
fl_regs->lut_fl_bias,
fl_regs->lut_fl_scale,
fl_regs->lut_fl_mode,
- fl_regs->lut_fl_format);
- DTN_INFO("\n");
+ fl_regs->lut_fl_format,
+ dlg_regs->dst_y_prefetch};
+
+ int num_elements = 18;
+
+ for (int j = 0; j < num_elements; j++)
+ DTN_INFO("%s \t %8xh\n", pLabels[j], values[j]);
}
}
@@ -541,19 +552,43 @@ static void dcn10_log_color_state(struct dc *dc,
dc->caps.color.mpc.ogam_ram,
dc->caps.color.mpc.ocsc);
DTN_INFO("===== MPC RMCM 3DLUT =====\n");
- DTN_INFO("MPCC: SIZE MODE MODE_CUR RD_SEL 30BIT_EN WR_EN_MASK RAM_SEL OUT_NORM_FACTOR FL_SEL OUT_OFFSET OUT_SCALE FL_DONE SOFT_UNDERFLOW HARD_UNDERFLOW MEM_PWR_ST FORCE DIS MODE\n");
+ char pLabels[19][50] = {
+ "MPCC", "SIZE", "MODE", "MODE_CUR", "RD_SEL",
+ "30BIT_EN", "WR_EN_MASK", "RAM_SEL", "OUT_NORM_FACTOR", "FL_SEL",
+ "OUT_OFFSET", "OUT_SCALE", "FL_DONE", "SOFT_UNDERFLOW", "HARD_UNDERFLOW",
+ "MEM_PWR_ST", "FORCE", "DIS", "MODE"};
+
for (i = 0; i < pool->mpcc_count; i++) {
struct mpcc_state s = {0};
pool->mpc->funcs->read_mpcc_state(pool->mpc, i, &s);
- if (s.opp_id != 0xf)
- DTN_INFO("[%2d]: %4xh %4xh %6xh %4x %4x %4x %4x %4x %4xh %4xh %6xh %4x %4x %4x %4x %4x %4x %4x\n",
- i, s.rmcm_regs.rmcm_3dlut_size, s.rmcm_regs.rmcm_3dlut_mode, s.rmcm_regs.rmcm_3dlut_mode_cur,
- s.rmcm_regs.rmcm_3dlut_read_sel, s.rmcm_regs.rmcm_3dlut_30bit_en, s.rmcm_regs.rmcm_3dlut_wr_en_mask,
- s.rmcm_regs.rmcm_3dlut_ram_sel, s.rmcm_regs.rmcm_3dlut_out_norm_factor, s.rmcm_regs.rmcm_3dlut_fl_sel,
- s.rmcm_regs.rmcm_3dlut_out_offset_r, s.rmcm_regs.rmcm_3dlut_out_scale_r, s.rmcm_regs.rmcm_3dlut_fl_done,
- s.rmcm_regs.rmcm_3dlut_fl_soft_underflow, s.rmcm_regs.rmcm_3dlut_fl_hard_underflow, s.rmcm_regs.rmcm_3dlut_mem_pwr_state,
- s.rmcm_regs.rmcm_3dlut_mem_pwr_force, s.rmcm_regs.rmcm_3dlut_mem_pwr_dis, s.rmcm_regs.rmcm_3dlut_mem_pwr_mode);
+ if (s.opp_id != 0xf) {
+ uint32_t values[] = {
+ i,
+ s.rmcm_regs.rmcm_3dlut_size,
+ s.rmcm_regs.rmcm_3dlut_mode,
+ s.rmcm_regs.rmcm_3dlut_mode_cur,
+ s.rmcm_regs.rmcm_3dlut_read_sel,
+ s.rmcm_regs.rmcm_3dlut_30bit_en,
+ s.rmcm_regs.rmcm_3dlut_wr_en_mask,
+ s.rmcm_regs.rmcm_3dlut_ram_sel,
+ s.rmcm_regs.rmcm_3dlut_out_norm_factor,
+ s.rmcm_regs.rmcm_3dlut_fl_sel,
+ s.rmcm_regs.rmcm_3dlut_out_offset_r,
+ s.rmcm_regs.rmcm_3dlut_out_scale_r,
+ s.rmcm_regs.rmcm_3dlut_fl_done,
+ s.rmcm_regs.rmcm_3dlut_fl_soft_underflow,
+ s.rmcm_regs.rmcm_3dlut_fl_hard_underflow,
+ s.rmcm_regs.rmcm_3dlut_mem_pwr_state,
+ s.rmcm_regs.rmcm_3dlut_mem_pwr_force,
+ s.rmcm_regs.rmcm_3dlut_mem_pwr_dis,
+ s.rmcm_regs.rmcm_3dlut_mem_pwr_mode};
+
+ int num_elements = 19;
+
+ for (int j = 0; j < num_elements; j++)
+ DTN_INFO("%s \t %8xh\n", pLabels[j], values[j]);
+ }
}
DTN_INFO("\n");
DTN_INFO("===== MPC RMCM Shaper =====\n");
diff --git a/drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_hwseq.c b/drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_hwseq.c
index 37a239219dfe..139a63101488 100644
--- a/drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_hwseq.c
+++ b/drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_hwseq.c
@@ -1228,3 +1228,51 @@ void dcn30_wait_for_all_pending_updates(const struct pipe_ctx *pipe_ctx)
}
}
}
+
+void dcn30_get_underflow_debug_data(const struct dc *dc,
+ struct timing_generator *tg,
+ struct dc_underflow_debug_data *out_data)
+{
+ struct hubbub *hubbub = dc->res_pool->hubbub;
+
+ if (tg) {
+ uint32_t v_blank_start = 0, v_blank_end = 0;
+
+ out_data->otg_inst = tg->inst;
+
+ tg->funcs->get_scanoutpos(tg,
+ &v_blank_start,
+ &v_blank_end,
+ &out_data->h_position,
+ &out_data->v_position);
+
+ out_data->otg_frame_count = tg->funcs->get_frame_count(tg);
+
+ out_data->otg_underflow = tg->funcs->is_optc_underflow_occurred(tg);
+ }
+
+ for (int i = 0; i < MAX_PIPES; i++) {
+ struct hubp *hubp = dc->res_pool->hubps[i];
+
+ if (hubp) {
+ if (hubp->funcs->hubp_get_underflow_status)
+ out_data->hubps[i].hubp_underflow = hubp->funcs->hubp_get_underflow_status(hubp);
+
+ if (hubp->funcs->hubp_in_blank)
+ out_data->hubps[i].hubp_in_blank = hubp->funcs->hubp_in_blank(hubp);
+
+ if (hubp->funcs->hubp_get_current_read_line)
+ out_data->hubps[i].hubp_readline = hubp->funcs->hubp_get_current_read_line(hubp);
+
+ if (hubp->funcs->hubp_get_det_config_error)
+ out_data->hubps[i].det_config_error = hubp->funcs->hubp_get_det_config_error(hubp);
+ }
+ }
+
+ if (hubbub->funcs->get_det_sizes)
+ hubbub->funcs->get_det_sizes(hubbub, out_data->curr_det_sizes, out_data->target_det_sizes);
+
+ if (hubbub->funcs->compbuf_config_error)
+ out_data->compbuf_config_error = hubbub->funcs->compbuf_config_error(hubbub);
+
+}
diff --git a/drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_hwseq.h b/drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_hwseq.h
index 4b90b781c4f2..40afbbfb5b9c 100644
--- a/drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_hwseq.h
+++ b/drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_hwseq.h
@@ -29,6 +29,7 @@
#include "hw_sequencer_private.h"
struct dc;
+struct dc_underflow_debug_data;
void dcn30_init_hw(struct dc *dc);
void dcn30_program_all_writeback_pipes_in_tree(
@@ -98,4 +99,8 @@ void dcn30_prepare_bandwidth(struct dc *dc,
void dcn30_wait_for_all_pending_updates(const struct pipe_ctx *pipe_ctx);
+void dcn30_get_underflow_debug_data(const struct dc *dc,
+ struct timing_generator *tg,
+ struct dc_underflow_debug_data *out_data);
+
#endif /* __DC_HWSS_DCN30_H__ */
diff --git a/drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_init.c b/drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_init.c
index 2ac5d54d1626..d7ff55669bac 100644
--- a/drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_init.c
+++ b/drivers/gpu/drm/amd/display/dc/hwss/dcn30/dcn30_init.c
@@ -110,6 +110,7 @@ static const struct hw_sequencer_funcs dcn30_funcs = {
.update_visual_confirm_color = dcn10_update_visual_confirm_color,
.is_abm_supported = dcn21_is_abm_supported,
.wait_for_all_pending_updates = dcn30_wait_for_all_pending_updates,
+ .get_underflow_debug_data = dcn30_get_underflow_debug_data,
};
static const struct hwseq_private_funcs dcn30_private_funcs = {
diff --git a/drivers/gpu/drm/amd/display/dc/hwss/dcn31/dcn31_init.c b/drivers/gpu/drm/amd/display/dc/hwss/dcn31/dcn31_init.c
index 556f4fe57eda..5a6a459da224 100644
--- a/drivers/gpu/drm/amd/display/dc/hwss/dcn31/dcn31_init.c
+++ b/drivers/gpu/drm/amd/display/dc/hwss/dcn31/dcn31_init.c
@@ -112,6 +112,7 @@ static const struct hw_sequencer_funcs dcn31_funcs = {
.exit_optimized_pwr_state = dcn21_exit_optimized_pwr_state,
.update_visual_confirm_color = dcn10_update_visual_confirm_color,
.setup_hpo_hw_control = dcn31_setup_hpo_hw_control,
+ .get_underflow_debug_data = dcn30_get_underflow_debug_data,
};
static const struct hwseq_private_funcs dcn31_private_funcs = {
diff --git a/drivers/gpu/drm/amd/display/dc/hwss/dcn314/dcn314_init.c b/drivers/gpu/drm/amd/display/dc/hwss/dcn314/dcn314_init.c
index f5112742edf9..a99145a30230 100644
--- a/drivers/gpu/drm/amd/display/dc/hwss/dcn314/dcn314_init.c
+++ b/drivers/gpu/drm/amd/display/dc/hwss/dcn314/dcn314_init.c
@@ -115,6 +115,7 @@ static const struct hw_sequencer_funcs dcn314_funcs = {
.update_visual_confirm_color = dcn10_update_visual_confirm_color,
.calculate_pix_rate_divider = dcn314_calculate_pix_rate_divider,
.setup_hpo_hw_control = dcn31_setup_hpo_hw_control,
+ .get_underflow_debug_data = dcn30_get_underflow_debug_data,
};
static const struct hwseq_private_funcs dcn314_private_funcs = {
diff --git a/drivers/gpu/drm/amd/display/dc/hwss/dcn32/dcn32_init.c b/drivers/gpu/drm/amd/display/dc/hwss/dcn32/dcn32_init.c
index b971356d30b1..c19ef075c882 100644
--- a/drivers/gpu/drm/amd/display/dc/hwss/dcn32/dcn32_init.c
+++ b/drivers/gpu/drm/amd/display/dc/hwss/dcn32/dcn32_init.c
@@ -121,6 +121,7 @@ static const struct hw_sequencer_funcs dcn32_funcs = {
.calculate_pix_rate_divider = dcn32_calculate_pix_rate_divider,
.program_outstanding_updates = dcn32_program_outstanding_updates,
.wait_for_all_pending_updates = dcn30_wait_for_all_pending_updates,
+ .get_underflow_debug_data = dcn30_get_underflow_debug_data,
};
static const struct hwseq_private_funcs dcn32_private_funcs = {
diff --git a/drivers/gpu/drm/amd/display/dc/hwss/dcn35/dcn35_init.c b/drivers/gpu/drm/amd/display/dc/hwss/dcn35/dcn35_init.c
index a3ccf805bd16..52cc488416ac 100644
--- a/drivers/gpu/drm/amd/display/dc/hwss/dcn35/dcn35_init.c
+++ b/drivers/gpu/drm/amd/display/dc/hwss/dcn35/dcn35_init.c
@@ -128,6 +128,7 @@ static const struct hw_sequencer_funcs dcn35_funcs = {
.enable_plane = dcn20_enable_plane,
.update_dchubp_dpp = dcn20_update_dchubp_dpp,
.post_unlock_reset_opp = dcn20_post_unlock_reset_opp,
+ .get_underflow_debug_data = dcn30_get_underflow_debug_data,
};
static const struct hwseq_private_funcs dcn35_private_funcs = {
diff --git a/drivers/gpu/drm/amd/display/dc/hwss/dcn351/dcn351_init.c b/drivers/gpu/drm/amd/display/dc/hwss/dcn351/dcn351_init.c
index 58f2be2a326b..e34efcb7bde5 100644
--- a/drivers/gpu/drm/amd/display/dc/hwss/dcn351/dcn351_init.c
+++ b/drivers/gpu/drm/amd/display/dc/hwss/dcn351/dcn351_init.c
@@ -123,6 +123,7 @@ static const struct hw_sequencer_funcs dcn351_funcs = {
.set_long_vtotal = dcn35_set_long_vblank,
.calculate_pix_rate_divider = dcn32_calculate_pix_rate_divider,
.setup_hpo_hw_control = dcn35_setup_hpo_hw_control,
+ .get_underflow_debug_data = dcn30_get_underflow_debug_data,
};
static const struct hwseq_private_funcs dcn351_private_funcs = {
diff --git a/drivers/gpu/drm/amd/display/dc/hwss/dcn401/dcn401_hwseq.c b/drivers/gpu/drm/amd/display/dc/hwss/dcn401/dcn401_hwseq.c
index fb949aeb1244..d5b5e2ce6ff6 100644
--- a/drivers/gpu/drm/amd/display/dc/hwss/dcn401/dcn401_hwseq.c
+++ b/drivers/gpu/drm/amd/display/dc/hwss/dcn401/dcn401_hwseq.c
@@ -1621,20 +1621,28 @@ void dcn401_unblank_stream(struct pipe_ctx *pipe_ctx,
void dcn401_hardware_release(struct dc *dc)
{
- dc_dmub_srv_fams2_update_config(dc, dc->current_state, false);
-
- /* If pstate unsupported, or still supported
- * by firmware, force it supported by dcn
- */
- if (dc->current_state) {
- if ((!dc->clk_mgr->clks.p_state_change_support ||
- dc->current_state->bw_ctx.bw.dcn.fams2_global_config.features.bits.enable) &&
- dc->res_pool->hubbub->funcs->force_pstate_change_control)
- dc->res_pool->hubbub->funcs->force_pstate_change_control(
- dc->res_pool->hubbub, true, true);
-
- dc->current_state->bw_ctx.bw.dcn.clk.p_state_change_support = true;
- dc->clk_mgr->funcs->update_clocks(dc->clk_mgr, dc->current_state, true);
+ if (!dc->debug.disable_force_pstate_allow_on_hw_release) {
+ dc_dmub_srv_fams2_update_config(dc, dc->current_state, false);
+
+ /* If pstate unsupported, or still supported
+ * by firmware, force it supported by dcn
+ */
+ if (dc->current_state) {
+ if ((!dc->clk_mgr->clks.p_state_change_support ||
+ dc->current_state->bw_ctx.bw.dcn.fams2_global_config.features.bits.enable) &&
+ dc->res_pool->hubbub->funcs->force_pstate_change_control)
+ dc->res_pool->hubbub->funcs->force_pstate_change_control(
+ dc->res_pool->hubbub, true, true);
+
+ dc->current_state->bw_ctx.bw.dcn.clk.p_state_change_support = true;
+ dc->clk_mgr->funcs->update_clocks(dc->clk_mgr, dc->current_state, true);
+ }
+ } else {
+ if (dc->current_state) {
+ dc->clk_mgr->clks.p_state_change_support = false;
+ dc->clk_mgr->funcs->update_clocks(dc->clk_mgr, dc->current_state, true);
+ }
+ dc_dmub_srv_fams2_update_config(dc, dc->current_state, false);
}
}
diff --git a/drivers/gpu/drm/amd/display/dc/hwss/dcn401/dcn401_init.c b/drivers/gpu/drm/amd/display/dc/hwss/dcn401/dcn401_init.c
index fe7aceb2f510..d6e11b7e4fce 100644
--- a/drivers/gpu/drm/amd/display/dc/hwss/dcn401/dcn401_init.c
+++ b/drivers/gpu/drm/amd/display/dc/hwss/dcn401/dcn401_init.c
@@ -104,6 +104,7 @@ static const struct hw_sequencer_funcs dcn401_funcs = {
.enable_plane = dcn20_enable_plane,
.update_dchubp_dpp = dcn20_update_dchubp_dpp,
.post_unlock_reset_opp = dcn20_post_unlock_reset_opp,
+ .get_underflow_debug_data = dcn30_get_underflow_debug_data,
};
static const struct hwseq_private_funcs dcn401_private_funcs = {
diff --git a/drivers/gpu/drm/amd/display/dc/hwss/hw_sequencer.h b/drivers/gpu/drm/amd/display/dc/hwss/hw_sequencer.h
index 9df8030e37f7..1723bbcf2c46 100644
--- a/drivers/gpu/drm/amd/display/dc/hwss/hw_sequencer.h
+++ b/drivers/gpu/drm/amd/display/dc/hwss/hw_sequencer.h
@@ -47,6 +47,7 @@ struct link_resource;
struct dc_dmub_cmd;
struct pg_block_update;
struct drr_params;
+struct dc_underflow_debug_data;
struct subvp_pipe_control_lock_fast_params {
struct dc *dc;
@@ -475,6 +476,9 @@ struct hw_sequencer_funcs {
struct dc_state *context);
void (*post_unlock_reset_opp)(struct dc *dc,
struct pipe_ctx *opp_head);
+ void (*get_underflow_debug_data)(const struct dc *dc,
+ struct timing_generator *tg,
+ struct dc_underflow_debug_data *out_data);
};
void color_space_to_black_color(
diff --git a/drivers/gpu/drm/amd/display/dc/inc/hw/dchubbub.h b/drivers/gpu/drm/amd/display/dc/inc/hw/dchubbub.h
index 52b745667ef7..9bee45b36629 100644
--- a/drivers/gpu/drm/amd/display/dc/inc/hw/dchubbub.h
+++ b/drivers/gpu/drm/amd/display/dc/inc/hw/dchubbub.h
@@ -229,6 +229,8 @@ struct hubbub_funcs {
void (*program_compbuf_segments)(struct hubbub *hubbub, unsigned compbuf_size_seg, bool safe_to_increase);
void (*wait_for_det_update)(struct hubbub *hubbub, int hubp_inst);
bool (*program_arbiter)(struct hubbub *hubbub, struct dml2_display_arb_regs *arb_regs, bool safe_to_lower);
+ void (*get_det_sizes)(struct hubbub *hubbub, uint32_t *curr_det_sizes, uint32_t *target_det_sizes);
+ uint32_t (*compbuf_config_error)(struct hubbub *hubbub);
};
struct hubbub {
diff --git a/drivers/gpu/drm/amd/display/dc/inc/hw/hubp.h b/drivers/gpu/drm/amd/display/dc/inc/hw/hubp.h
index cee29e89ec5c..2b874d2cc61c 100644
--- a/drivers/gpu/drm/amd/display/dc/inc/hw/hubp.h
+++ b/drivers/gpu/drm/amd/display/dc/inc/hw/hubp.h
@@ -89,7 +89,7 @@ enum hubp_3dlut_fl_addressing_mode {
enum hubp_3dlut_fl_width {
hubp_3dlut_fl_width_17 = 17,
hubp_3dlut_fl_width_33 = 33,
- hubp_3dlut_fl_width_transformed = 4916
+ hubp_3dlut_fl_width_transformed = 4916, //mpc default
};
enum hubp_3dlut_fl_crossbar_bit_slice {
@@ -99,6 +99,22 @@ enum hubp_3dlut_fl_crossbar_bit_slice {
hubp_3dlut_fl_crossbar_bit_slice_48_63 = 3
};
+struct hubp_fl_3dlut_config {
+ bool enabled;
+ enum hubp_3dlut_fl_width width;
+ enum hubp_3dlut_fl_mode mode;
+ enum hubp_3dlut_fl_format format;
+ uint16_t bias;
+ uint16_t scale;
+ struct dc_plane_address address;
+ enum hubp_3dlut_fl_addressing_mode addr_mode;
+ enum dc_cm2_gpu_mem_layout layout;
+ uint8_t protection_bits;
+ enum hubp_3dlut_fl_crossbar_bit_slice crossbar_bit_slice_y_g;
+ enum hubp_3dlut_fl_crossbar_bit_slice crossbar_bit_slice_cb_b;
+ enum hubp_3dlut_fl_crossbar_bit_slice crossbar_bit_slice_cr_r;
+};
+
struct hubp {
const struct hubp_funcs *funcs;
struct dc_context *ctx;
@@ -288,7 +304,10 @@ struct hubp_funcs {
enum hubp_3dlut_fl_crossbar_bit_slice bit_slice_cb_b,
enum hubp_3dlut_fl_crossbar_bit_slice bit_slice_cr_r);
int (*hubp_get_3dlut_fl_done)(struct hubp *hubp);
+ void (*hubp_program_3dlut_fl_config)(struct hubp *hubp, struct hubp_fl_3dlut_config *cfg);
void (*hubp_clear_tiling)(struct hubp *hubp);
+ uint32_t (*hubp_get_current_read_line)(struct hubp *hubp);
+ uint32_t (*hubp_get_det_config_error)(struct hubp *hubp);
};
#endif
diff --git a/drivers/gpu/drm/amd/display/dc/inc/hw/mpc.h b/drivers/gpu/drm/amd/display/dc/inc/hw/mpc.h
index 7641439f6ca0..14f0304e3eb9 100644
--- a/drivers/gpu/drm/amd/display/dc/inc/hw/mpc.h
+++ b/drivers/gpu/drm/amd/display/dc/inc/hw/mpc.h
@@ -115,6 +115,16 @@ enum MCM_LUT_ID {
MCM_LUT_SHAPER
};
+struct mpc_fl_3dlut_config {
+ bool enabled;
+ uint16_t width;
+ bool select_lut_bank_a;
+ uint16_t bit_depth;
+ int hubp_index;
+ uint16_t bias;
+ uint16_t scale;
+};
+
union mcm_lut_params {
const struct pwl_params *pwl;
const struct tetrahedral_params *lut3d;
@@ -1098,6 +1108,7 @@ struct mpc_funcs {
* MPC RMCM new HW sequential programming functions
*/
struct {
+ void (*fl_3dlut_configure)(struct mpc *mpc, struct mpc_fl_3dlut_config *cfg, int mpcc_id);
void (*enable_3dlut_fl)(struct mpc *mpc, bool enable, int mpcc_id);
void (*update_3dlut_fast_load_select)(struct mpc *mpc, int mpcc_id, int hubp_idx);
void (*program_lut_read_write_control)(struct mpc *mpc, const enum MCM_LUT_ID id,
diff --git a/drivers/gpu/drm/amd/display/dc/link/protocols/link_edp_panel_control.c b/drivers/gpu/drm/amd/display/dc/link/protocols/link_edp_panel_control.c
index be714cbf6615..2c3e2945124a 100644
--- a/drivers/gpu/drm/amd/display/dc/link/protocols/link_edp_panel_control.c
+++ b/drivers/gpu/drm/amd/display/dc/link/protocols/link_edp_panel_control.c
@@ -1046,7 +1046,7 @@ bool edp_setup_replay(struct dc_link *link, const struct dc_stream_state *stream
if (link->replay_settings.config.alpm_mode == DC_ALPM_AUXLESS) {
alpm_config.bits.ALPM_MODE_SEL = 1;
- alpm_config.bits.ACDS_PERIOD_DURATION = 1;
+ alpm_config.bits.ACDS_PERIOD_DURATION = 0;
}
dm_helpers_dp_write_dpcd(
diff --git a/drivers/gpu/drm/amd/display/dc/resource/dce60/dce60_resource.c b/drivers/gpu/drm/amd/display/dc/resource/dce60/dce60_resource.c
index 58b59d52dc9d..53b60044653f 100644
--- a/drivers/gpu/drm/amd/display/dc/resource/dce60/dce60_resource.c
+++ b/drivers/gpu/drm/amd/display/dc/resource/dce60/dce60_resource.c
@@ -373,7 +373,7 @@ static const struct resource_caps res_cap = {
.num_timing_generator = 6,
.num_audio = 6,
.num_stream_encoder = 6,
- .num_pll = 2,
+ .num_pll = 3,
.num_ddc = 6,
};
@@ -389,7 +389,7 @@ static const struct resource_caps res_cap_64 = {
.num_timing_generator = 2,
.num_audio = 2,
.num_stream_encoder = 2,
- .num_pll = 2,
+ .num_pll = 3,
.num_ddc = 2,
};
@@ -973,21 +973,24 @@ static bool dce60_construct(
if (bp->fw_info_valid && bp->fw_info.external_clock_source_frequency_for_dp != 0) {
pool->base.dp_clock_source =
- dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_EXTERNAL, NULL, true);
+ dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_EXTERNAL, NULL, true);
+ /* DCE 6.0 and 6.4: PLL0 can only be used with DP. Don't initialize it here. */
pool->base.clock_sources[0] =
- dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL0, &clk_src_regs[0], false);
+ dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[1], false);
pool->base.clock_sources[1] =
- dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[1], false);
+ dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL2, &clk_src_regs[2], false);
pool->base.clk_src_count = 2;
} else {
pool->base.dp_clock_source =
- dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL0, &clk_src_regs[0], true);
+ dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL0, &clk_src_regs[0], true);
pool->base.clock_sources[0] =
- dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[1], false);
- pool->base.clk_src_count = 1;
+ dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[1], false);
+ pool->base.clock_sources[1] =
+ dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL2, &clk_src_regs[2], false);
+ pool->base.clk_src_count = 2;
}
if (pool->base.dp_clock_source == NULL) {
@@ -1365,21 +1368,24 @@ static bool dce64_construct(
if (bp->fw_info_valid && bp->fw_info.external_clock_source_frequency_for_dp != 0) {
pool->base.dp_clock_source =
- dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_EXTERNAL, NULL, true);
+ dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_EXTERNAL, NULL, true);
+ /* DCE 6.0 and 6.4: PLL0 can only be used with DP. Don't initialize it here. */
pool->base.clock_sources[0] =
- dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[0], false);
+ dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[1], false);
pool->base.clock_sources[1] =
- dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL2, &clk_src_regs[1], false);
+ dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL2, &clk_src_regs[2], false);
pool->base.clk_src_count = 2;
} else {
pool->base.dp_clock_source =
- dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[0], true);
+ dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL0, &clk_src_regs[0], true);
pool->base.clock_sources[0] =
- dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL2, &clk_src_regs[1], false);
- pool->base.clk_src_count = 1;
+ dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL1, &clk_src_regs[1], false);
+ pool->base.clock_sources[1] =
+ dce60_clock_source_create(ctx, bp, CLOCK_SOURCE_ID_PLL2, &clk_src_regs[2], false);
+ pool->base.clk_src_count = 2;
}
if (pool->base.dp_clock_source == NULL) {
diff --git a/drivers/gpu/drm/amd/display/dc/resource/dcn32/dcn32_resource.h b/drivers/gpu/drm/amd/display/dc/resource/dcn32/dcn32_resource.h
index 82f966cf4ed2..20d714596021 100644
--- a/drivers/gpu/drm/amd/display/dc/resource/dcn32/dcn32_resource.h
+++ b/drivers/gpu/drm/amd/display/dc/resource/dcn32/dcn32_resource.h
@@ -1141,7 +1141,8 @@ unsigned int dcn32_get_max_hw_cursor_size(const struct dc *dc,
SRI_ARR(DCN_SURF1_TTU_CNTL1, HUBPREQ, id), \
SRI_ARR(DCN_CUR0_TTU_CNTL0, HUBPREQ, id), \
SRI_ARR(DCN_CUR0_TTU_CNTL1, HUBPREQ, id), \
- SRI_ARR(HUBP_CLK_CNTL, HUBP, id)
+ SRI_ARR(HUBP_CLK_CNTL, HUBP, id), \
+ SRI_ARR(HUBPRET_READ_LINE_VALUE, HUBPRET, id)
#define HUBP_REG_LIST_DCN2_COMMON_RI(id) \
HUBP_REG_LIST_DCN_RI(id), HUBP_REG_LIST_DCN_VM_RI(id), \
SRI_ARR(PREFETCH_SETTINGS, HUBPREQ, id), \
diff --git a/drivers/gpu/drm/amd/display/dc/resource/dcn401/dcn401_resource.c b/drivers/gpu/drm/amd/display/dc/resource/dcn401/dcn401_resource.c
index b3988e38d0a6..068c123ea8a8 100644
--- a/drivers/gpu/drm/amd/display/dc/resource/dcn401/dcn401_resource.c
+++ b/drivers/gpu/drm/amd/display/dc/resource/dcn401/dcn401_resource.c
@@ -708,6 +708,7 @@ static const struct dc_debug_options debug_defaults_drv = {
},
.use_max_lb = true,
.force_disable_subvp = false,
+ .disable_force_pstate_allow_on_hw_release = false,
.exit_idle_opt_for_cursor_updates = true,
.using_dml2 = true,
.using_dml21 = true,
diff --git a/drivers/gpu/drm/amd/display/dc/resource/dcn401/dcn401_resource.h b/drivers/gpu/drm/amd/display/dc/resource/dcn401/dcn401_resource.h
index 2ae6831c31ef..0fc66487d800 100644
--- a/drivers/gpu/drm/amd/display/dc/resource/dcn401/dcn401_resource.h
+++ b/drivers/gpu/drm/amd/display/dc/resource/dcn401/dcn401_resource.h
@@ -140,7 +140,8 @@ void dcn401_prepare_mcache_programming(struct dc *dc, struct dc_state *context);
SRI_ARR(UCLK_PSTATE_FORCE, HUBPREQ, id), \
HUBP_3DLUT_FL_REG_LIST_DCN401(id), \
SRI_ARR(DCSURF_VIEWPORT_MCACHE_SPLIT_COORDINATE, HUBP, id), \
- SRI_ARR(DCHUBP_MCACHEID_CONFIG, HUBP, id)
+ SRI_ARR(DCHUBP_MCACHEID_CONFIG, HUBP, id), \
+ SRI_ARR(HUBPRET_READ_LINE_VALUE, HUBPRET, id)
/* ABM */
#define ABM_DCN401_REG_LIST_RI(id) \
diff --git a/drivers/gpu/drm/amd/display/dmub/dmub_srv.h b/drivers/gpu/drm/amd/display/dmub/dmub_srv.h
index 0bafb6710761..87b761ac3135 100644
--- a/drivers/gpu/drm/amd/display/dmub/dmub_srv.h
+++ b/drivers/gpu/drm/amd/display/dmub/dmub_srv.h
@@ -316,6 +316,7 @@ struct dmub_srv_hw_params {
bool disable_sldo_opt;
bool enable_non_transparent_setconfig;
bool lower_hbr3_phy_ssc;
+ bool override_hbr3_pll_vco;
};
/**
diff --git a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h
index dcae768c2cf4..79b5b1bb9b93 100644
--- a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h
+++ b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h
@@ -843,7 +843,8 @@ union dmub_fw_boot_options {
uint32_t ips_sequential_ono: 1; /**< 1 to enable sequential ONO IPS sequence */
uint32_t disable_sldo_opt: 1; /**< 1 to disable SLDO optimizations */
uint32_t lower_hbr3_phy_ssc: 1; /**< 1 to lower hbr3 phy ssc to 0.125 percent */
- uint32_t reserved : 6; /**< reserved */
+ uint32_t override_hbr3_pll_vco: 1; /**< 1 to override the hbr3 pll vco to 0 */
+ uint32_t reserved : 5; /**< reserved */
} bits; /**< boot bits */
uint32_t all; /**< 32-bit access to bits */
};
diff --git a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn31.c b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn31.c
index 3f38db752b84..4777c7203b2c 100644
--- a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn31.c
+++ b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn31.c
@@ -377,6 +377,7 @@ void dmub_dcn31_enable_dmub_boot_options(struct dmub_srv *dmub, const struct dmu
boot_options.bits.dpia_hpd_int_enable_supported = params->dpia_hpd_int_enable_supported;
boot_options.bits.power_optimization = params->power_optimization;
boot_options.bits.lower_hbr3_phy_ssc = params->lower_hbr3_phy_ssc;
+ boot_options.bits.override_hbr3_pll_vco = params->override_hbr3_pll_vco;
boot_options.bits.sel_mux_phy_c_d_phy_f_g = (dmub->asic == DMUB_ASIC_DCN31B) ? 1 : 0;
diff --git a/drivers/gpu/drm/amd/display/include/dal_asic_id.h b/drivers/gpu/drm/amd/display/include/dal_asic_id.h
index 5fc29164e4b4..8aea50aa9533 100644
--- a/drivers/gpu/drm/amd/display/include/dal_asic_id.h
+++ b/drivers/gpu/drm/amd/display/include/dal_asic_id.h
@@ -213,6 +213,11 @@ enum {
#endif
#define DEVICE_ID_NV_13FE 0x13FE // CYAN_SKILLFISH
#define DEVICE_ID_NV_143F 0x143F
+#define DEVICE_ID_NV_13F9 0x13F9
+#define DEVICE_ID_NV_13FA 0x13FA
+#define DEVICE_ID_NV_13FB 0x13FB
+#define DEVICE_ID_NV_13FC 0x13FC
+#define DEVICE_ID_NV_13DB 0x13DB
#define FAMILY_VGH 144
#define DEVICE_ID_VGH_163F 0x163F
#define DEVICE_ID_VGH_1435 0x1435
diff --git a/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c b/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c
index 756afe78a6e5..b47cb4a5f488 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c
@@ -77,6 +77,9 @@ static void smu_power_profile_mode_get(struct smu_context *smu,
static void smu_power_profile_mode_put(struct smu_context *smu,
enum PP_SMC_POWER_PROFILE profile_mode);
static enum smu_clk_type smu_convert_to_smuclk(enum pp_clock_type type);
+static int smu_od_edit_dpm_table(void *handle,
+ enum PP_OD_DPM_TABLE_COMMAND type,
+ long *input, uint32_t size);
static int smu_sys_get_pp_feature_mask(void *handle,
char *buf)
@@ -2195,6 +2198,7 @@ static int smu_resume(struct amdgpu_ip_block *ip_block)
int ret;
struct amdgpu_device *adev = ip_block->adev;
struct smu_context *smu = adev->powerplay.pp_handle;
+ struct smu_dpm_context *smu_dpm_ctx = &(smu->smu_dpm);
if (amdgpu_sriov_multi_vf_mode(adev))
return 0;
@@ -2226,6 +2230,18 @@ static int smu_resume(struct amdgpu_ip_block *ip_block)
adev->pm.dpm_enabled = true;
+ if (smu->current_power_limit) {
+ ret = smu_set_power_limit(smu, smu->current_power_limit);
+ if (ret && ret != -EOPNOTSUPP)
+ return ret;
+ }
+
+ if (smu_dpm_ctx->dpm_level == AMD_DPM_FORCED_LEVEL_MANUAL) {
+ ret = smu_od_edit_dpm_table(smu, PP_OD_COMMIT_DPM_TABLE, NULL, 0);
+ if (ret)
+ return ret;
+ }
+
dev_info(adev->dev, "SMU is resumed successfully!\n");
return 0;
diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu11/arcturus_ppt.c b/drivers/gpu/drm/amd/pm/swsmu/smu11/arcturus_ppt.c
index 9ad46f545d15..599eddb5a67d 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/smu11/arcturus_ppt.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/smu11/arcturus_ppt.c
@@ -1897,7 +1897,7 @@ static ssize_t arcturus_get_gpu_metrics(struct smu_context *smu,
ret = smu_cmn_get_metrics_table(smu,
&metrics,
- true);
+ false);
if (ret)
return ret;
diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu13/aldebaran_ppt.c b/drivers/gpu/drm/amd/pm/swsmu/smu13/aldebaran_ppt.c
index c63d2e28954d..b067147b7c41 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/smu13/aldebaran_ppt.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/smu13/aldebaran_ppt.c
@@ -1781,7 +1781,7 @@ static ssize_t aldebaran_get_gpu_metrics(struct smu_context *smu,
ret = smu_cmn_get_metrics_table(smu,
&metrics,
- true);
+ false);
if (ret)
return ret;
diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_6_ppt.c b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_6_ppt.c
index 9cc294f4708b..a0ce108aab44 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_6_ppt.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_6_ppt.c
@@ -177,7 +177,7 @@ static const struct cmn2asic_msg_mapping smu_v13_0_6_message_map[SMU_MSG_MAX_COU
MSG_MAP(SetThrottlingPolicy, PPSMC_MSG_SetThrottlingPolicy, 0),
MSG_MAP(ResetSDMA, PPSMC_MSG_ResetSDMA, 0),
MSG_MAP(ResetVCN, PPSMC_MSG_ResetVCN, 0),
- MSG_MAP(GetStaticMetricsTable, PPSMC_MSG_GetStaticMetricsTable, 0),
+ MSG_MAP(GetStaticMetricsTable, PPSMC_MSG_GetStaticMetricsTable, 1),
};
// clang-format on
@@ -402,14 +402,28 @@ static void smu_v13_0_6_init_caps(struct smu_context *smu)
if ((pgm == 7 && fw_ver >= 0x7550E00) ||
(pgm == 0 && fw_ver >= 0x00557E00))
smu_v13_0_6_cap_set(smu, SMU_CAP(HST_LIMIT_METRICS));
- if ((pgm == 0 && fw_ver >= 0x00557F01) ||
- (pgm == 7 && fw_ver >= 0x7551000)) {
- smu_v13_0_6_cap_set(smu, SMU_CAP(STATIC_METRICS));
- smu_v13_0_6_cap_set(smu, SMU_CAP(BOARD_VOLTAGE));
+
+ if (amdgpu_sriov_vf(adev)) {
+ if ((pgm == 0 && fw_ver >= 0x00558000) ||
+ (pgm == 7 && fw_ver >= 0x7551000)) {
+ smu_v13_0_6_cap_set(smu,
+ SMU_CAP(STATIC_METRICS));
+ smu_v13_0_6_cap_set(smu,
+ SMU_CAP(BOARD_VOLTAGE));
+ smu_v13_0_6_cap_set(smu, SMU_CAP(PLDM_VERSION));
+ }
+ } else {
+ if ((pgm == 0 && fw_ver >= 0x00557F01) ||
+ (pgm == 7 && fw_ver >= 0x7551000)) {
+ smu_v13_0_6_cap_set(smu,
+ SMU_CAP(STATIC_METRICS));
+ smu_v13_0_6_cap_set(smu,
+ SMU_CAP(BOARD_VOLTAGE));
+ }
+ if ((pgm == 0 && fw_ver >= 0x00558000) ||
+ (pgm == 7 && fw_ver >= 0x7551000))
+ smu_v13_0_6_cap_set(smu, SMU_CAP(PLDM_VERSION));
}
- if ((pgm == 0 && fw_ver >= 0x00558000) ||
- (pgm == 7 && fw_ver >= 0x7551000))
- smu_v13_0_6_cap_set(smu, SMU_CAP(PLDM_VERSION));
}
if (((pgm == 7) && (fw_ver >= 0x7550700)) ||
((pgm == 0) && (fw_ver >= 0x00557900)) ||
diff --git a/drivers/gpu/drm/bridge/aux-bridge.c b/drivers/gpu/drm/bridge/aux-bridge.c
index b63304d3a80f..b3e4cdff61d6 100644
--- a/drivers/gpu/drm/bridge/aux-bridge.c
+++ b/drivers/gpu/drm/bridge/aux-bridge.c
@@ -18,6 +18,7 @@ static void drm_aux_bridge_release(struct device *dev)
{
struct auxiliary_device *adev = to_auxiliary_dev(dev);
+ of_node_put(dev->of_node);
ida_free(&drm_aux_bridge_ida, adev->id);
kfree(adev);
@@ -65,6 +66,7 @@ int drm_aux_bridge_register(struct device *parent)
ret = auxiliary_device_init(adev);
if (ret) {
+ of_node_put(adev->dev.of_node);
ida_free(&drm_aux_bridge_ida, adev->id);
kfree(adev);
return ret;
diff --git a/drivers/gpu/drm/drm_bridge.c b/drivers/gpu/drm/drm_bridge.c
index dd45d9b504d8..4bde00083047 100644
--- a/drivers/gpu/drm/drm_bridge.c
+++ b/drivers/gpu/drm/drm_bridge.c
@@ -1227,6 +1227,7 @@ EXPORT_SYMBOL(drm_atomic_bridge_chain_check);
/**
* drm_bridge_detect - check if anything is attached to the bridge output
* @bridge: bridge control structure
+ * @connector: attached connector
*
* If the bridge supports output detection, as reported by the
* DRM_BRIDGE_OP_DETECT bridge ops flag, call &drm_bridge_funcs.detect for the
diff --git a/drivers/gpu/drm/drm_gem.c b/drivers/gpu/drm/drm_gem.c
index a15ce72920ac..6a44351e58b7 100644
--- a/drivers/gpu/drm/drm_gem.c
+++ b/drivers/gpu/drm/drm_gem.c
@@ -646,7 +646,7 @@ struct page **drm_gem_get_pages(struct drm_gem_object *obj)
i = 0;
while (i < npages) {
long nr;
- folio = shmem_read_folio_gfp(mapping, i, 0,
+ folio = shmem_read_folio_gfp(mapping, i,
mapping_gfp_mask(mapping));
if (IS_ERR(folio))
goto fail;
diff --git a/drivers/gpu/drm/i915/gem/i915_gem_shmem.c b/drivers/gpu/drm/i915/gem/i915_gem_shmem.c
index 28bccf3d71ef..e3d188455f67 100644
--- a/drivers/gpu/drm/i915/gem/i915_gem_shmem.c
+++ b/drivers/gpu/drm/i915/gem/i915_gem_shmem.c
@@ -70,7 +70,6 @@ int shmem_sg_alloc_table(struct drm_i915_private *i915, struct sg_table *st,
struct scatterlist *sg;
unsigned long next_pfn = 0; /* suppress gcc warning */
gfp_t noreclaim;
- size_t chunk;
int ret;
if (overflows_type(size / PAGE_SIZE, page_count))
@@ -96,7 +95,6 @@ int shmem_sg_alloc_table(struct drm_i915_private *i915, struct sg_table *st,
mapping_set_unevictable(mapping);
noreclaim = mapping_gfp_constraint(mapping, ~__GFP_RECLAIM);
noreclaim |= __GFP_NORETRY | __GFP_NOWARN;
- chunk = mapping_max_folio_size(mapping);
sg = st->sgl;
st->nents = 0;
@@ -108,13 +106,10 @@ int shmem_sg_alloc_table(struct drm_i915_private *i915, struct sg_table *st,
0,
}, *s = shrink;
gfp_t gfp = noreclaim;
- loff_t bytes = (page_count - i) << PAGE_SHIFT;
- loff_t pos = i << PAGE_SHIFT;
- bytes = min_t(loff_t, chunk, bytes);
do {
cond_resched();
- folio = shmem_read_folio_gfp(mapping, i, pos + bytes, gfp);
+ folio = shmem_read_folio_gfp(mapping, i, gfp);
if (!IS_ERR(folio))
break;
diff --git a/drivers/gpu/drm/ttm/ttm_backup.c b/drivers/gpu/drm/ttm/ttm_backup.c
index b04b5860b068..32530c75f038 100644
--- a/drivers/gpu/drm/ttm/ttm_backup.c
+++ b/drivers/gpu/drm/ttm/ttm_backup.c
@@ -102,7 +102,7 @@ ttm_backup_backup_page(struct file *backup, struct page *page,
struct folio *to_folio;
int ret;
- to_folio = shmem_read_folio_gfp(mapping, idx, 0, alloc_gfp);
+ to_folio = shmem_read_folio_gfp(mapping, idx, alloc_gfp);
if (IS_ERR(to_folio))
return PTR_ERR(to_folio);
diff --git a/drivers/gpu/drm/xe/Kconfig b/drivers/gpu/drm/xe/Kconfig
index 2bb2bc052120..714d5702dfd7 100644
--- a/drivers/gpu/drm/xe/Kconfig
+++ b/drivers/gpu/drm/xe/Kconfig
@@ -5,6 +5,7 @@ config DRM_XE
depends on KUNIT || !KUNIT
depends on INTEL_VSEC || !INTEL_VSEC
depends on X86_PLATFORM_DEVICES || !(X86 && ACPI)
+ depends on PAGE_SIZE_4KB || COMPILE_TEST || BROKEN
select INTERVAL_TREE
# we need shmfs for the swappable backing store, and in particular
# the shmem_readpage() which depends upon tmpfs
diff --git a/drivers/gpu/drm/xe/abi/guc_actions_abi.h b/drivers/gpu/drm/xe/abi/guc_actions_abi.h
index 81eb046aeebf..d8cf68a0516d 100644
--- a/drivers/gpu/drm/xe/abi/guc_actions_abi.h
+++ b/drivers/gpu/drm/xe/abi/guc_actions_abi.h
@@ -193,6 +193,14 @@ enum xe_guc_register_context_multi_lrc_param_offsets {
XE_GUC_REGISTER_CONTEXT_MULTI_LRC_MSG_MIN_LEN = 11,
};
+enum xe_guc_context_wq_item_offsets {
+ XE_GUC_CONTEXT_WQ_HEADER_DATA_0_TYPE_LEN = 0,
+ XE_GUC_CONTEXT_WQ_EL_INFO_DATA_1_CTX_DESC_LOW,
+ XE_GUC_CONTEXT_WQ_EL_INFO_DATA_2_GUCCTX_RINGTAIL_FREEZEPOCS,
+ XE_GUC_CONTEXT_WQ_EL_INFO_DATA_3_WI_FENCE_ID,
+ XE_GUC_CONTEXT_WQ_EL_CHILD_LIST_DATA_4_RINGTAIL,
+};
+
enum xe_guc_report_status {
XE_GUC_REPORT_STATUS_UNKNOWN = 0x0,
XE_GUC_REPORT_STATUS_ACKED = 0x1,
diff --git a/drivers/gpu/drm/xe/xe_device.c b/drivers/gpu/drm/xe/xe_device.c
index c754374f1a8d..57edbc63da6f 100644
--- a/drivers/gpu/drm/xe/xe_device.c
+++ b/drivers/gpu/drm/xe/xe_device.c
@@ -822,10 +822,6 @@ int xe_device_probe(struct xe_device *xe)
return err;
}
- err = xe_devcoredump_init(xe);
- if (err)
- return err;
-
/*
* From here on, if a step fails, make sure a Driver-FLR is triggereed
*/
@@ -890,6 +886,10 @@ int xe_device_probe(struct xe_device *xe)
XE_WA(xe->tiles->media_gt, 15015404425_disable))
XE_DEVICE_WA_DISABLE(xe, 15015404425);
+ err = xe_devcoredump_init(xe);
+ if (err)
+ return err;
+
xe_nvm_init(xe);
err = xe_heci_gsc_init(xe);
diff --git a/drivers/gpu/drm/xe/xe_exec_queue.c b/drivers/gpu/drm/xe/xe_exec_queue.c
index d5958518ef00..6c176183ed58 100644
--- a/drivers/gpu/drm/xe/xe_exec_queue.c
+++ b/drivers/gpu/drm/xe/xe_exec_queue.c
@@ -1076,3 +1076,51 @@ int xe_exec_queue_last_fence_test_dep(struct xe_exec_queue *q, struct xe_vm *vm)
return err;
}
+
+/**
+ * xe_exec_queue_contexts_hwsp_rebase - Re-compute GGTT references
+ * within all LRCs of a queue.
+ * @q: the &xe_exec_queue struct instance containing target LRCs
+ * @scratch: scratch buffer to be used as temporary storage
+ *
+ * Returns: zero on success, negative error code on failure
+ */
+int xe_exec_queue_contexts_hwsp_rebase(struct xe_exec_queue *q, void *scratch)
+{
+ int i;
+ int err = 0;
+
+ for (i = 0; i < q->width; ++i) {
+ xe_lrc_update_memirq_regs_with_address(q->lrc[i], q->hwe, scratch);
+ xe_lrc_update_hwctx_regs_with_address(q->lrc[i]);
+ err = xe_lrc_setup_wa_bb_with_scratch(q->lrc[i], q->hwe, scratch);
+ if (err)
+ break;
+ }
+
+ return err;
+}
+
+/**
+ * xe_exec_queue_jobs_ring_restore - Re-emit ring commands of requests pending on given queue.
+ * @q: the &xe_exec_queue struct instance
+ */
+void xe_exec_queue_jobs_ring_restore(struct xe_exec_queue *q)
+{
+ struct xe_gpu_scheduler *sched = &q->guc->sched;
+ struct xe_sched_job *job;
+
+ /*
+ * This routine is used within VF migration recovery. This means
+ * using the lock here introduces a restriction: we cannot wait
+ * for any GFX HW response while the lock is taken.
+ */
+ spin_lock(&sched->base.job_list_lock);
+ list_for_each_entry(job, &sched->base.pending_list, drm.list) {
+ if (xe_sched_job_is_error(job))
+ continue;
+
+ q->ring_ops->emit_job(job);
+ }
+ spin_unlock(&sched->base.job_list_lock);
+}
diff --git a/drivers/gpu/drm/xe/xe_exec_queue.h b/drivers/gpu/drm/xe/xe_exec_queue.h
index 17bc50a7f05a..4d416f23001c 100644
--- a/drivers/gpu/drm/xe/xe_exec_queue.h
+++ b/drivers/gpu/drm/xe/xe_exec_queue.h
@@ -90,4 +90,8 @@ int xe_exec_queue_last_fence_test_dep(struct xe_exec_queue *q,
struct xe_vm *vm);
void xe_exec_queue_update_run_ticks(struct xe_exec_queue *q);
+int xe_exec_queue_contexts_hwsp_rebase(struct xe_exec_queue *q, void *scratch);
+
+void xe_exec_queue_jobs_ring_restore(struct xe_exec_queue *q);
+
#endif
diff --git a/drivers/gpu/drm/xe/xe_gpu_scheduler.c b/drivers/gpu/drm/xe/xe_gpu_scheduler.c
index 869b43a4151d..455ccaf17314 100644
--- a/drivers/gpu/drm/xe/xe_gpu_scheduler.c
+++ b/drivers/gpu/drm/xe/xe_gpu_scheduler.c
@@ -101,6 +101,19 @@ void xe_sched_submission_stop(struct xe_gpu_scheduler *sched)
cancel_work_sync(&sched->work_process_msg);
}
+/**
+ * xe_sched_submission_stop_async - Stop further runs of submission tasks on a scheduler.
+ * @sched: the &xe_gpu_scheduler struct instance
+ *
+ * This call disables further runs of scheduling work queue. It does not wait
+ * for any in-progress runs to finish, only makes sure no further runs happen
+ * afterwards.
+ */
+void xe_sched_submission_stop_async(struct xe_gpu_scheduler *sched)
+{
+ drm_sched_wqueue_stop(&sched->base);
+}
+
void xe_sched_submission_resume_tdr(struct xe_gpu_scheduler *sched)
{
drm_sched_resume_timeout(&sched->base, sched->base.timeout);
diff --git a/drivers/gpu/drm/xe/xe_gpu_scheduler.h b/drivers/gpu/drm/xe/xe_gpu_scheduler.h
index 308061f0cf37..e548b2aed95a 100644
--- a/drivers/gpu/drm/xe/xe_gpu_scheduler.h
+++ b/drivers/gpu/drm/xe/xe_gpu_scheduler.h
@@ -21,6 +21,7 @@ void xe_sched_fini(struct xe_gpu_scheduler *sched);
void xe_sched_submission_start(struct xe_gpu_scheduler *sched);
void xe_sched_submission_stop(struct xe_gpu_scheduler *sched);
+void xe_sched_submission_stop_async(struct xe_gpu_scheduler *sched);
void xe_sched_submission_resume_tdr(struct xe_gpu_scheduler *sched);
diff --git a/drivers/gpu/drm/xe/xe_gt.c b/drivers/gpu/drm/xe/xe_gt.c
index 5a79c6e3208b..390394bbaadc 100644
--- a/drivers/gpu/drm/xe/xe_gt.c
+++ b/drivers/gpu/drm/xe/xe_gt.c
@@ -41,6 +41,7 @@
#include "xe_gt_topology.h"
#include "xe_guc_exec_queue_types.h"
#include "xe_guc_pc.h"
+#include "xe_guc_submit.h"
#include "xe_hw_fence.h"
#include "xe_hw_engine_class_sysfs.h"
#include "xe_irq.h"
@@ -802,6 +803,11 @@ static int do_gt_restart(struct xe_gt *gt)
return 0;
}
+static int gt_wait_reset_unblock(struct xe_gt *gt)
+{
+ return xe_guc_wait_reset_unblock(&gt->uc.guc);
+}
+
static int gt_reset(struct xe_gt *gt)
{
unsigned int fw_ref;
@@ -816,6 +822,10 @@ static int gt_reset(struct xe_gt *gt)
xe_gt_info(gt, "reset started\n");
+ err = gt_wait_reset_unblock(gt);
+ if (!err)
+ xe_gt_warn(gt, "reset block failed to get lifted");
+
xe_pm_runtime_get(gt_to_xe(gt));
if (xe_fault_inject_gt_reset()) {
diff --git a/drivers/gpu/drm/xe/xe_gt_debugfs.c b/drivers/gpu/drm/xe/xe_gt_debugfs.c
index 8d4b66ca38b7..bf3a67b5951c 100644
--- a/drivers/gpu/drm/xe/xe_gt_debugfs.c
+++ b/drivers/gpu/drm/xe/xe_gt_debugfs.c
@@ -29,6 +29,7 @@
#include "xe_pm.h"
#include "xe_reg_sr.h"
#include "xe_reg_whitelist.h"
+#include "xe_sa.h"
#include "xe_sriov.h"
#include "xe_tuning.h"
#include "xe_uc_debugfs.h"
@@ -128,7 +129,7 @@ static int sa_info(struct xe_gt *gt, struct drm_printer *p)
xe_pm_runtime_get(gt_to_xe(gt));
drm_suballoc_dump_debug_info(&tile->mem.kernel_bb_pool->base, p,
- tile->mem.kernel_bb_pool->gpu_addr);
+ xe_sa_manager_gpu_addr(tile->mem.kernel_bb_pool));
xe_pm_runtime_put(gt_to_xe(gt));
return 0;
@@ -152,7 +153,7 @@ static int sa_info_vf_ccs(struct xe_gt *gt, struct drm_printer *p)
drm_printf(p, "ccs %s bb suballoc info\n", ctx_id ? "write" : "read");
drm_printf(p, "-------------------------\n");
- drm_suballoc_dump_debug_info(&bb_pool->base, p, bb_pool->gpu_addr);
+ drm_suballoc_dump_debug_info(&bb_pool->base, p, xe_sa_manager_gpu_addr(bb_pool));
drm_puts(p, "\n");
}
diff --git a/drivers/gpu/drm/xe/xe_gt_sriov_pf.c b/drivers/gpu/drm/xe/xe_gt_sriov_pf.c
index 35489fa81825..c4dda87b47cc 100644
--- a/drivers/gpu/drm/xe/xe_gt_sriov_pf.c
+++ b/drivers/gpu/drm/xe/xe_gt_sriov_pf.c
@@ -16,6 +16,7 @@
#include "xe_gt_sriov_pf_migration.h"
#include "xe_gt_sriov_pf_service.h"
#include "xe_gt_sriov_printk.h"
+#include "xe_guc_submit.h"
#include "xe_mmio.h"
#include "xe_pm.h"
@@ -47,9 +48,21 @@ static int pf_alloc_metadata(struct xe_gt *gt)
static void pf_init_workers(struct xe_gt *gt)
{
+ xe_gt_assert(gt, IS_SRIOV_PF(gt_to_xe(gt)));
INIT_WORK(&gt->sriov.pf.workers.restart, pf_worker_restart_func);
}
+static void pf_fini_workers(struct xe_gt *gt)
+{
+ xe_gt_assert(gt, IS_SRIOV_PF(gt_to_xe(gt)));
+
+ if (disable_work_sync(&gt->sriov.pf.workers.restart)) {
+ xe_gt_sriov_dbg_verbose(gt, "pending restart disabled!\n");
+ /* release an rpm reference taken on the worker's behalf */
+ xe_pm_runtime_put(gt_to_xe(gt));
+ }
+}
+
/**
* xe_gt_sriov_pf_init_early - Prepare SR-IOV PF data structures on PF.
* @gt: the &xe_gt to initialize
@@ -79,6 +92,21 @@ int xe_gt_sriov_pf_init_early(struct xe_gt *gt)
return 0;
}
+static void pf_fini_action(void *arg)
+{
+ struct xe_gt *gt = arg;
+
+ pf_fini_workers(gt);
+}
+
+static int pf_init_late(struct xe_gt *gt)
+{
+ struct xe_device *xe = gt_to_xe(gt);
+
+ xe_gt_assert(gt, IS_SRIOV_PF(xe));
+ return devm_add_action_or_reset(xe->drm.dev, pf_fini_action, gt);
+}
+
/**
* xe_gt_sriov_pf_init - Prepare SR-IOV PF data structures on PF.
* @gt: the &xe_gt to initialize
@@ -95,7 +123,15 @@ int xe_gt_sriov_pf_init(struct xe_gt *gt)
if (err)
return err;
- return xe_gt_sriov_pf_migration_init(gt);
+ err = xe_gt_sriov_pf_migration_init(gt);
+ if (err)
+ return err;
+
+ err = pf_init_late(gt);
+ if (err)
+ return err;
+
+ return 0;
}
static bool pf_needs_enable_ggtt_guest_update(struct xe_device *xe)
@@ -176,8 +212,11 @@ static void pf_cancel_restart(struct xe_gt *gt)
{
xe_gt_assert(gt, IS_SRIOV_PF(gt_to_xe(gt)));
- if (cancel_work_sync(&gt->sriov.pf.workers.restart))
+ if (cancel_work_sync(&gt->sriov.pf.workers.restart)) {
xe_gt_sriov_dbg_verbose(gt, "pending restart canceled!\n");
+ /* release an rpm reference taken on the worker's behalf */
+ xe_pm_runtime_put(gt_to_xe(gt));
+ }
}
/**
@@ -195,9 +234,12 @@ static void pf_restart(struct xe_gt *gt)
{
struct xe_device *xe = gt_to_xe(gt);
- xe_pm_runtime_get(xe);
+ xe_gt_assert(gt, !xe_pm_runtime_suspended(xe));
+
xe_gt_sriov_pf_config_restart(gt);
xe_gt_sriov_pf_control_restart(gt);
+
+ /* release an rpm reference taken on our behalf */
xe_pm_runtime_put(xe);
xe_gt_sriov_dbg(gt, "restart completed\n");
@@ -216,8 +258,13 @@ static void pf_queue_restart(struct xe_gt *gt)
xe_gt_assert(gt, IS_SRIOV_PF(xe));
- if (!queue_work(xe->sriov.wq, &gt->sriov.pf.workers.restart))
+ /* take an rpm reference on behalf of the worker */
+ xe_pm_runtime_get_noresume(xe);
+
+ if (!queue_work(xe->sriov.wq, &gt->sriov.pf.workers.restart)) {
xe_gt_sriov_dbg(gt, "restart already in queue!\n");
+ xe_pm_runtime_put(xe);
+ }
}
/**
@@ -230,3 +277,27 @@ void xe_gt_sriov_pf_restart(struct xe_gt *gt)
{
pf_queue_restart(gt);
}
+
+static void pf_flush_restart(struct xe_gt *gt)
+{
+ xe_gt_assert(gt, IS_SRIOV_PF(gt_to_xe(gt)));
+ flush_work(&gt->sriov.pf.workers.restart);
+}
+
+/**
+ * xe_gt_sriov_pf_wait_ready() - Wait until per-GT PF SR-IOV support is ready.
+ * @gt: the &xe_gt
+ *
+ * This function can only be called on PF.
+ *
+ * Return: 0 on success or a negative error code on failure.
+ */
+int xe_gt_sriov_pf_wait_ready(struct xe_gt *gt)
+{
+ /* don't wait if there is another ongoing reset */
+ if (xe_guc_read_stopped(&gt->uc.guc))
+ return -EBUSY;
+
+ pf_flush_restart(gt);
+ return 0;
+}
diff --git a/drivers/gpu/drm/xe/xe_gt_sriov_pf.h b/drivers/gpu/drm/xe/xe_gt_sriov_pf.h
index e2b2ff8132dc..e7fde3f9937a 100644
--- a/drivers/gpu/drm/xe/xe_gt_sriov_pf.h
+++ b/drivers/gpu/drm/xe/xe_gt_sriov_pf.h
@@ -11,6 +11,7 @@ struct xe_gt;
#ifdef CONFIG_PCI_IOV
int xe_gt_sriov_pf_init_early(struct xe_gt *gt);
int xe_gt_sriov_pf_init(struct xe_gt *gt);
+int xe_gt_sriov_pf_wait_ready(struct xe_gt *gt);
void xe_gt_sriov_pf_init_hw(struct xe_gt *gt);
void xe_gt_sriov_pf_sanitize_hw(struct xe_gt *gt, unsigned int vfid);
void xe_gt_sriov_pf_stop_prepare(struct xe_gt *gt);
diff --git a/drivers/gpu/drm/xe/xe_gt_sriov_pf_config.c b/drivers/gpu/drm/xe/xe_gt_sriov_pf_config.c
index f00cce81f1ff..c8f0320d032f 100644
--- a/drivers/gpu/drm/xe/xe_gt_sriov_pf_config.c
+++ b/drivers/gpu/drm/xe/xe_gt_sriov_pf_config.c
@@ -1434,7 +1434,8 @@ fail:
return err;
}
-static void pf_release_vf_config_lmem(struct xe_gt *gt, struct xe_gt_sriov_config *config)
+/* Return: %true if there was an LMEM provisioned, %false otherwise */
+static bool pf_release_vf_config_lmem(struct xe_gt *gt, struct xe_gt_sriov_config *config)
{
xe_gt_assert(gt, IS_DGFX(gt_to_xe(gt)));
xe_gt_assert(gt, xe_gt_is_main_type(gt));
@@ -1443,7 +1444,9 @@ static void pf_release_vf_config_lmem(struct xe_gt *gt, struct xe_gt_sriov_confi
if (config->lmem_obj) {
xe_bo_unpin_map_no_vm(config->lmem_obj);
config->lmem_obj = NULL;
+ return true;
}
+ return false;
}
static int pf_provision_vf_lmem(struct xe_gt *gt, unsigned int vfid, u64 size)
@@ -2021,12 +2024,13 @@ static void pf_release_vf_config(struct xe_gt *gt, unsigned int vfid)
{
struct xe_gt_sriov_config *config = pf_pick_vf_config(gt, vfid);
struct xe_device *xe = gt_to_xe(gt);
+ bool released;
if (xe_gt_is_main_type(gt)) {
pf_release_vf_config_ggtt(gt, config);
if (IS_DGFX(xe)) {
- pf_release_vf_config_lmem(gt, config);
- if (xe_device_has_lmtt(xe))
+ released = pf_release_vf_config_lmem(gt, config);
+ if (released && xe_device_has_lmtt(xe))
pf_update_vf_lmtt(xe, vfid);
}
}
diff --git a/drivers/gpu/drm/xe/xe_gt_sriov_pf_debugfs.c b/drivers/gpu/drm/xe/xe_gt_sriov_pf_debugfs.c
index bf679b21f485..3ed245e04d0c 100644
--- a/drivers/gpu/drm/xe/xe_gt_sriov_pf_debugfs.c
+++ b/drivers/gpu/drm/xe/xe_gt_sriov_pf_debugfs.c
@@ -22,6 +22,7 @@
#include "xe_gt_sriov_pf_policy.h"
#include "xe_gt_sriov_pf_service.h"
#include "xe_pm.h"
+#include "xe_sriov_pf.h"
/*
* /sys/kernel/debug/dri/0/
@@ -205,7 +206,8 @@ static int CONFIG##_set(void *data, u64 val) \
return -EOVERFLOW; \
\
xe_pm_runtime_get(xe); \
- err = xe_gt_sriov_pf_config_set_##CONFIG(gt, vfid, val); \
+ err = xe_sriov_pf_wait_ready(xe) ?: \
+ xe_gt_sriov_pf_config_set_##CONFIG(gt, vfid, val); \
xe_pm_runtime_put(xe); \
\
return err; \
diff --git a/drivers/gpu/drm/xe/xe_gt_sriov_vf.c b/drivers/gpu/drm/xe/xe_gt_sriov_vf.c
index b282838d59e6..0461d5513487 100644
--- a/drivers/gpu/drm/xe/xe_gt_sriov_vf.c
+++ b/drivers/gpu/drm/xe/xe_gt_sriov_vf.c
@@ -25,6 +25,7 @@
#include "xe_guc.h"
#include "xe_guc_hxg_helpers.h"
#include "xe_guc_relay.h"
+#include "xe_lrc.h"
#include "xe_mmio.h"
#include "xe_sriov.h"
#include "xe_sriov_vf.h"
@@ -751,6 +752,19 @@ failed:
}
/**
+ * xe_gt_sriov_vf_default_lrcs_hwsp_rebase - Update GGTT references in HWSP of default LRCs.
+ * @gt: the &xe_gt struct instance
+ */
+void xe_gt_sriov_vf_default_lrcs_hwsp_rebase(struct xe_gt *gt)
+{
+ struct xe_hw_engine *hwe;
+ enum xe_hw_engine_id id;
+
+ for_each_hw_engine(hwe, gt, id)
+ xe_default_lrc_update_memirq_regs_with_address(hwe);
+}
+
+/**
* xe_gt_sriov_vf_migrated_event_handler - Start a VF migration recovery,
* or just mark that a GuC is ready for it.
* @gt: the &xe_gt struct instance linked to target GuC
diff --git a/drivers/gpu/drm/xe/xe_gt_sriov_vf.h b/drivers/gpu/drm/xe/xe_gt_sriov_vf.h
index e0357f341a2d..0af1dc769fe0 100644
--- a/drivers/gpu/drm/xe/xe_gt_sriov_vf.h
+++ b/drivers/gpu/drm/xe/xe_gt_sriov_vf.h
@@ -21,6 +21,7 @@ void xe_gt_sriov_vf_guc_versions(struct xe_gt *gt,
int xe_gt_sriov_vf_query_config(struct xe_gt *gt);
int xe_gt_sriov_vf_connect(struct xe_gt *gt);
int xe_gt_sriov_vf_query_runtime(struct xe_gt *gt);
+void xe_gt_sriov_vf_default_lrcs_hwsp_rebase(struct xe_gt *gt);
int xe_gt_sriov_vf_notify_resfix_done(struct xe_gt *gt);
void xe_gt_sriov_vf_migrated_event_handler(struct xe_gt *gt);
diff --git a/drivers/gpu/drm/xe/xe_guc_buf.c b/drivers/gpu/drm/xe/xe_guc_buf.c
index 14a07dca48e7..502ca3a4ee60 100644
--- a/drivers/gpu/drm/xe/xe_guc_buf.c
+++ b/drivers/gpu/drm/xe/xe_guc_buf.c
@@ -164,7 +164,7 @@ u64 xe_guc_cache_gpu_addr_from_ptr(struct xe_guc_buf_cache *cache, const void *p
if (offset < 0 || offset + size > cache->sam->base.size)
return 0;
- return cache->sam->gpu_addr + offset;
+ return xe_sa_manager_gpu_addr(cache->sam) + offset;
}
#if IS_BUILTIN(CONFIG_DRM_XE_KUNIT_TEST)
diff --git a/drivers/gpu/drm/xe/xe_guc_capture.c b/drivers/gpu/drm/xe/xe_guc_capture.c
index 859a3ba91be5..243dad3e2418 100644
--- a/drivers/gpu/drm/xe/xe_guc_capture.c
+++ b/drivers/gpu/drm/xe/xe_guc_capture.c
@@ -1817,6 +1817,12 @@ void xe_engine_snapshot_print(struct xe_hw_engine_snapshot *snapshot, struct drm
str_yes_no(snapshot->kernel_reserved));
for (type = GUC_STATE_CAPTURE_TYPE_GLOBAL; type < GUC_STATE_CAPTURE_TYPE_MAX; type++) {
+ /*
+ * FIXME: During devcoredump print we should avoid accessing the
+ * driver pointers for gt or engine. Printing should be done only
+ * using the snapshot captured. Here we are accessing the gt
+ * pointer. It should be fixed.
+ */
list = xe_guc_capture_get_reg_desc_list(gt, GUC_CAPTURE_LIST_INDEX_PF, type,
capture_class, false);
snapshot_print_by_list_order(snapshot, p, type, list);
diff --git a/drivers/gpu/drm/xe/xe_guc_submit.c b/drivers/gpu/drm/xe/xe_guc_submit.c
index 751da5cd1d44..1185b23b1384 100644
--- a/drivers/gpu/drm/xe/xe_guc_submit.c
+++ b/drivers/gpu/drm/xe/xe_guc_submit.c
@@ -671,12 +671,18 @@ static void wq_item_append(struct xe_exec_queue *q)
if (wq_wait_for_space(q, wqi_size))
return;
+ xe_gt_assert(guc_to_gt(guc), i == XE_GUC_CONTEXT_WQ_HEADER_DATA_0_TYPE_LEN);
wqi[i++] = FIELD_PREP(WQ_TYPE_MASK, WQ_TYPE_MULTI_LRC) |
FIELD_PREP(WQ_LEN_MASK, len_dw);
+ xe_gt_assert(guc_to_gt(guc), i == XE_GUC_CONTEXT_WQ_EL_INFO_DATA_1_CTX_DESC_LOW);
wqi[i++] = xe_lrc_descriptor(q->lrc[0]);
+ xe_gt_assert(guc_to_gt(guc), i ==
+ XE_GUC_CONTEXT_WQ_EL_INFO_DATA_2_GUCCTX_RINGTAIL_FREEZEPOCS);
wqi[i++] = FIELD_PREP(WQ_GUC_ID_MASK, q->guc->id) |
FIELD_PREP(WQ_RING_TAIL_MASK, q->lrc[0]->ring.tail / sizeof(u64));
+ xe_gt_assert(guc_to_gt(guc), i == XE_GUC_CONTEXT_WQ_EL_INFO_DATA_3_WI_FENCE_ID);
wqi[i++] = 0;
+ xe_gt_assert(guc_to_gt(guc), i == XE_GUC_CONTEXT_WQ_EL_CHILD_LIST_DATA_4_RINGTAIL);
for (j = 1; j < q->width; ++j) {
struct xe_lrc *lrc = q->lrc[j];
@@ -697,6 +703,50 @@ static void wq_item_append(struct xe_exec_queue *q)
parallel_write(xe, map, wq_desc.tail, q->guc->wqi_tail);
}
+static int wq_items_rebase(struct xe_exec_queue *q)
+{
+ struct xe_guc *guc = exec_queue_to_guc(q);
+ struct xe_device *xe = guc_to_xe(guc);
+ struct iosys_map map = xe_lrc_parallel_map(q->lrc[0]);
+ int i = q->guc->wqi_head;
+
+ /* the ring starts after a header struct */
+ iosys_map_incr(&map, offsetof(struct guc_submit_parallel_scratch, wq[0]));
+
+ while ((i % WQ_SIZE) != (q->guc->wqi_tail % WQ_SIZE)) {
+ u32 len_dw, type, val;
+
+ if (drm_WARN_ON_ONCE(&xe->drm, i < 0 || i > 2 * WQ_SIZE))
+ break;
+
+ val = xe_map_rd_ring_u32(xe, &map, i / sizeof(u32) +
+ XE_GUC_CONTEXT_WQ_HEADER_DATA_0_TYPE_LEN,
+ WQ_SIZE / sizeof(u32));
+ len_dw = FIELD_GET(WQ_LEN_MASK, val);
+ type = FIELD_GET(WQ_TYPE_MASK, val);
+
+ if (drm_WARN_ON_ONCE(&xe->drm, len_dw >= WQ_SIZE / sizeof(u32)))
+ break;
+
+ if (type == WQ_TYPE_MULTI_LRC) {
+ val = xe_lrc_descriptor(q->lrc[0]);
+ xe_map_wr_ring_u32(xe, &map, i / sizeof(u32) +
+ XE_GUC_CONTEXT_WQ_EL_INFO_DATA_1_CTX_DESC_LOW,
+ WQ_SIZE / sizeof(u32), val);
+ } else if (drm_WARN_ON_ONCE(&xe->drm, type != WQ_TYPE_NOOP)) {
+ break;
+ }
+
+ i += (len_dw + 1) * sizeof(u32);
+ }
+
+ if ((i % WQ_SIZE) != (q->guc->wqi_tail % WQ_SIZE)) {
+ xe_gt_err(q->gt, "Exec queue fixups incomplete - wqi parse failed\n");
+ return -EBADMSG;
+ }
+ return 0;
+}
+
#define RESUME_PENDING ~0x0ull
static void submit_exec_queue(struct xe_exec_queue *q)
{
@@ -781,6 +831,30 @@ guc_exec_queue_run_job(struct drm_sched_job *drm_job)
return fence;
}
+/**
+ * xe_guc_jobs_ring_rebase - Re-emit ring commands of requests pending
+ * on all queues under a guc.
+ * @guc: the &xe_guc struct instance
+ */
+void xe_guc_jobs_ring_rebase(struct xe_guc *guc)
+{
+ struct xe_exec_queue *q;
+ unsigned long index;
+
+ /*
+ * This routine is used within VF migration recovery. This means
+ * using the lock here introduces a restriction: we cannot wait
+ * for any GFX HW response while the lock is taken.
+ */
+ mutex_lock(&guc->submission_state.lock);
+ xa_for_each(&guc->submission_state.exec_queue_lookup, index, q) {
+ if (exec_queue_killed_or_banned_or_wedged(q))
+ continue;
+ xe_exec_queue_jobs_ring_restore(q);
+ }
+ mutex_unlock(&guc->submission_state.lock);
+}
+
static void guc_exec_queue_free_job(struct drm_sched_job *drm_job)
{
struct xe_sched_job *job = to_xe_sched_job(drm_job);
@@ -1777,6 +1851,43 @@ static void guc_exec_queue_stop(struct xe_guc *guc, struct xe_exec_queue *q)
}
}
+/**
+ * xe_guc_submit_reset_block - Disallow reset calls on given GuC.
+ * @guc: the &xe_guc struct instance
+ */
+int xe_guc_submit_reset_block(struct xe_guc *guc)
+{
+ return atomic_fetch_or(1, &guc->submission_state.reset_blocked);
+}
+
+/**
+ * xe_guc_submit_reset_unblock - Allow back reset calls on given GuC.
+ * @guc: the &xe_guc struct instance
+ */
+void xe_guc_submit_reset_unblock(struct xe_guc *guc)
+{
+ atomic_set_release(&guc->submission_state.reset_blocked, 0);
+ wake_up_all(&guc->ct.wq);
+}
+
+static int guc_submit_reset_is_blocked(struct xe_guc *guc)
+{
+ return atomic_read_acquire(&guc->submission_state.reset_blocked);
+}
+
+/* Maximum time of blocking reset */
+#define RESET_BLOCK_PERIOD_MAX (HZ * 5)
+
+/**
+ * xe_guc_wait_reset_unblock - Wait until reset blocking flag is lifted, or timeout.
+ * @guc: the &xe_guc struct instance
+ */
+int xe_guc_wait_reset_unblock(struct xe_guc *guc)
+{
+ return wait_event_timeout(guc->ct.wq,
+ !guc_submit_reset_is_blocked(guc), RESET_BLOCK_PERIOD_MAX);
+}
+
int xe_guc_submit_reset_prepare(struct xe_guc *guc)
{
int ret;
@@ -1830,6 +1941,19 @@ void xe_guc_submit_stop(struct xe_guc *guc)
}
+/**
+ * xe_guc_submit_pause - Stop further runs of submission tasks on given GuC.
+ * @guc: the &xe_guc struct instance whose scheduler is to be disabled
+ */
+void xe_guc_submit_pause(struct xe_guc *guc)
+{
+ struct xe_exec_queue *q;
+ unsigned long index;
+
+ xa_for_each(&guc->submission_state.exec_queue_lookup, index, q)
+ xe_sched_submission_stop_async(&q->guc->sched);
+}
+
static void guc_exec_queue_start(struct xe_exec_queue *q)
{
struct xe_gpu_scheduler *sched = &q->guc->sched;
@@ -1870,6 +1994,28 @@ int xe_guc_submit_start(struct xe_guc *guc)
return 0;
}
+static void guc_exec_queue_unpause(struct xe_exec_queue *q)
+{
+ struct xe_gpu_scheduler *sched = &q->guc->sched;
+
+ xe_sched_submission_start(sched);
+}
+
+/**
+ * xe_guc_submit_unpause - Allow further runs of submission tasks on given GuC.
+ * @guc: the &xe_guc struct instance whose scheduler is to be enabled
+ */
+void xe_guc_submit_unpause(struct xe_guc *guc)
+{
+ struct xe_exec_queue *q;
+ unsigned long index;
+
+ xa_for_each(&guc->submission_state.exec_queue_lookup, index, q)
+ guc_exec_queue_unpause(q);
+
+ wake_up_all(&guc->ct.wq);
+}
+
static struct xe_exec_queue *
g2h_exec_queue_lookup(struct xe_guc *guc, u32 guc_id)
{
@@ -2427,3 +2573,32 @@ void xe_guc_submit_print(struct xe_guc *guc, struct drm_printer *p)
guc_exec_queue_print(q, p);
mutex_unlock(&guc->submission_state.lock);
}
+
+/**
+ * xe_guc_contexts_hwsp_rebase - Re-compute GGTT references within all
+ * exec queues registered to given GuC.
+ * @guc: the &xe_guc struct instance
+ * @scratch: scratch buffer to be used as temporary storage
+ *
+ * Returns: zero on success, negative error code on failure.
+ */
+int xe_guc_contexts_hwsp_rebase(struct xe_guc *guc, void *scratch)
+{
+ struct xe_exec_queue *q;
+ unsigned long index;
+ int err = 0;
+
+ mutex_lock(&guc->submission_state.lock);
+ xa_for_each(&guc->submission_state.exec_queue_lookup, index, q) {
+ err = xe_exec_queue_contexts_hwsp_rebase(q, scratch);
+ if (err)
+ break;
+ if (xe_exec_queue_is_parallel(q))
+ err = wq_items_rebase(q);
+ if (err)
+ break;
+ }
+ mutex_unlock(&guc->submission_state.lock);
+
+ return err;
+}
diff --git a/drivers/gpu/drm/xe/xe_guc_submit.h b/drivers/gpu/drm/xe/xe_guc_submit.h
index 8f64e799283b..6b5df5d0956b 100644
--- a/drivers/gpu/drm/xe/xe_guc_submit.h
+++ b/drivers/gpu/drm/xe/xe_guc_submit.h
@@ -18,6 +18,11 @@ int xe_guc_submit_reset_prepare(struct xe_guc *guc);
void xe_guc_submit_reset_wait(struct xe_guc *guc);
void xe_guc_submit_stop(struct xe_guc *guc);
int xe_guc_submit_start(struct xe_guc *guc);
+void xe_guc_submit_pause(struct xe_guc *guc);
+void xe_guc_submit_unpause(struct xe_guc *guc);
+int xe_guc_submit_reset_block(struct xe_guc *guc);
+void xe_guc_submit_reset_unblock(struct xe_guc *guc);
+int xe_guc_wait_reset_unblock(struct xe_guc *guc);
void xe_guc_submit_wedge(struct xe_guc *guc);
int xe_guc_read_stopped(struct xe_guc *guc);
@@ -29,6 +34,8 @@ int xe_guc_exec_queue_memory_cat_error_handler(struct xe_guc *guc, u32 *msg,
int xe_guc_exec_queue_reset_failure_handler(struct xe_guc *guc, u32 *msg, u32 len);
int xe_guc_error_capture_handler(struct xe_guc *guc, u32 *msg, u32 len);
+void xe_guc_jobs_ring_rebase(struct xe_guc *guc);
+
struct xe_guc_submit_exec_queue_snapshot *
xe_guc_exec_queue_snapshot_capture(struct xe_exec_queue *q);
void
@@ -41,4 +48,6 @@ xe_guc_exec_queue_snapshot_free(struct xe_guc_submit_exec_queue_snapshot *snapsh
void xe_guc_submit_print(struct xe_guc *guc, struct drm_printer *p);
void xe_guc_register_exec_queue(struct xe_exec_queue *q, int ctx_type);
+int xe_guc_contexts_hwsp_rebase(struct xe_guc *guc, void *scratch);
+
#endif
diff --git a/drivers/gpu/drm/xe/xe_guc_types.h b/drivers/gpu/drm/xe/xe_guc_types.h
index 1fde7614fcc5..c7b9642b41ba 100644
--- a/drivers/gpu/drm/xe/xe_guc_types.h
+++ b/drivers/gpu/drm/xe/xe_guc_types.h
@@ -85,6 +85,12 @@ struct xe_guc {
struct xarray exec_queue_lookup;
/** @submission_state.stopped: submissions are stopped */
atomic_t stopped;
+ /**
+ * @submission_state.reset_blocked: reset attempts are blocked;
+ * blocking reset in order to delay it may be required if running
+ * an operation which is sensitive to resets.
+ */
+ atomic_t reset_blocked;
/** @submission_state.lock: protects submission state */
struct mutex lock;
/** @submission_state.enabled: submission is enabled */
diff --git a/drivers/gpu/drm/xe/xe_lrc.c b/drivers/gpu/drm/xe/xe_lrc.c
index 540f044bf425..8760c4c2ca38 100644
--- a/drivers/gpu/drm/xe/xe_lrc.c
+++ b/drivers/gpu/drm/xe/xe_lrc.c
@@ -41,7 +41,6 @@
#define LRC_PPHWSP_SIZE SZ_4K
#define LRC_INDIRECT_CTX_BO_SIZE SZ_4K
#define LRC_INDIRECT_RING_STATE_SIZE SZ_4K
-#define LRC_WA_BB_SIZE SZ_4K
/*
* Layout of the LRC and associated data allocated as
@@ -697,7 +696,13 @@ u32 xe_lrc_regs_offset(struct xe_lrc *lrc)
return xe_lrc_pphwsp_offset(lrc) + LRC_PPHWSP_SIZE;
}
-static size_t lrc_reg_size(struct xe_device *xe)
+/**
+ * xe_lrc_reg_size() - Get size of the LRC registers area within queues
+ * @xe: the &xe_device struct instance
+ *
+ * Returns: Size of the LRC registers area for current platform
+ */
+size_t xe_lrc_reg_size(struct xe_device *xe)
{
if (GRAPHICS_VERx100(xe) >= 1250)
return 96 * sizeof(u32);
@@ -707,7 +712,7 @@ static size_t lrc_reg_size(struct xe_device *xe)
size_t xe_lrc_skip_size(struct xe_device *xe)
{
- return LRC_PPHWSP_SIZE + lrc_reg_size(xe);
+ return LRC_PPHWSP_SIZE + xe_lrc_reg_size(xe);
}
static inline u32 __xe_lrc_seqno_offset(struct xe_lrc *lrc)
@@ -948,6 +953,47 @@ static void *empty_lrc_data(struct xe_hw_engine *hwe)
return data;
}
+/**
+ * xe_default_lrc_update_memirq_regs_with_address - Re-compute GGTT references in default LRC
+ * of given engine.
+ * @hwe: the &xe_hw_engine struct instance
+ */
+void xe_default_lrc_update_memirq_regs_with_address(struct xe_hw_engine *hwe)
+{
+ struct xe_gt *gt = hwe->gt;
+ u32 *regs;
+
+ if (!gt->default_lrc[hwe->class])
+ return;
+
+ regs = gt->default_lrc[hwe->class] + LRC_PPHWSP_SIZE;
+ set_memory_based_intr(regs, hwe);
+}
+
+/**
+ * xe_lrc_update_memirq_regs_with_address - Re-compute GGTT references in mem interrupt data
+ * for given LRC.
+ * @lrc: the &xe_lrc struct instance
+ * @hwe: the &xe_hw_engine struct instance
+ * @regs: scratch buffer to be used as temporary storage
+ */
+void xe_lrc_update_memirq_regs_with_address(struct xe_lrc *lrc, struct xe_hw_engine *hwe,
+ u32 *regs)
+{
+ struct xe_gt *gt = hwe->gt;
+ struct iosys_map map;
+ size_t regs_len;
+
+ if (!xe_device_uses_memirq(gt_to_xe(gt)))
+ return;
+
+ map = __xe_lrc_regs_map(lrc);
+ regs_len = xe_lrc_reg_size(gt_to_xe(gt));
+ xe_map_memcpy_from(gt_to_xe(gt), regs, &map, 0, regs_len);
+ set_memory_based_intr(regs, hwe);
+ xe_map_memcpy_to(gt_to_xe(gt), &map, 0, regs, regs_len);
+}
+
static void xe_lrc_set_ppgtt(struct xe_lrc *lrc, struct xe_vm *vm)
{
u64 desc = xe_vm_pdp4_descriptor(vm, gt_to_tile(lrc->gt));
@@ -1102,13 +1148,11 @@ static int setup_bo(struct bo_setup_state *state)
ssize_t remain;
if (state->lrc->bo->vmap.is_iomem) {
- state->buffer = kmalloc(state->max_size, GFP_KERNEL);
if (!state->buffer)
return -ENOMEM;
state->ptr = state->buffer;
} else {
state->ptr = state->lrc->bo->vmap.vaddr + state->offset;
- state->buffer = NULL;
}
remain = state->max_size / sizeof(u32);
@@ -1133,7 +1177,6 @@ static int setup_bo(struct bo_setup_state *state)
return 0;
fail:
- kfree(state->buffer);
return -ENOSPC;
}
@@ -1145,10 +1188,16 @@ static void finish_bo(struct bo_setup_state *state)
xe_map_memcpy_to(gt_to_xe(state->lrc->gt), &state->lrc->bo->vmap,
state->offset, state->buffer,
state->written * sizeof(u32));
- kfree(state->buffer);
}
-static int setup_wa_bb(struct xe_lrc *lrc, struct xe_hw_engine *hwe)
+/**
+ * xe_lrc_setup_wa_bb_with_scratch - Execute all wa bb setup callbacks.
+ * @lrc: the &xe_lrc struct instance
+ * @hwe: the &xe_hw_engine struct instance
+ * @scratch: preallocated scratch buffer for temporary storage
+ * Return: 0 on success, negative error code on failure
+ */
+int xe_lrc_setup_wa_bb_with_scratch(struct xe_lrc *lrc, struct xe_hw_engine *hwe, u32 *scratch)
{
static const struct bo_setup funcs[] = {
{ .setup = setup_timestamp_wa },
@@ -1159,6 +1208,7 @@ static int setup_wa_bb(struct xe_lrc *lrc, struct xe_hw_engine *hwe)
.lrc = lrc,
.hwe = hwe,
.max_size = LRC_WA_BB_SIZE,
+ .buffer = scratch,
.reserve_dw = 1,
.offset = __xe_lrc_wa_bb_offset(lrc),
.funcs = funcs,
@@ -1181,6 +1231,21 @@ static int setup_wa_bb(struct xe_lrc *lrc, struct xe_hw_engine *hwe)
return 0;
}
+static int setup_wa_bb(struct xe_lrc *lrc, struct xe_hw_engine *hwe)
+{
+ u32 *buf = NULL;
+ int ret;
+
+ if (lrc->bo->vmap.is_iomem)
+ buf = kmalloc(LRC_WA_BB_SIZE, GFP_KERNEL);
+
+ ret = xe_lrc_setup_wa_bb_with_scratch(lrc, hwe, buf);
+
+ kfree(buf);
+
+ return ret;
+}
+
static int
setup_indirect_ctx(struct xe_lrc *lrc, struct xe_hw_engine *hwe)
{
@@ -1191,6 +1256,7 @@ setup_indirect_ctx(struct xe_lrc *lrc, struct xe_hw_engine *hwe)
.lrc = lrc,
.hwe = hwe,
.max_size = (63 * 64) /* max 63 cachelines */,
+ .buffer = NULL,
.offset = __xe_lrc_indirect_ctx_offset(lrc),
};
int ret;
@@ -1207,9 +1273,14 @@ setup_indirect_ctx(struct xe_lrc *lrc, struct xe_hw_engine *hwe)
if (xe_gt_WARN_ON(lrc->gt, !state.funcs))
return 0;
+ if (lrc->bo->vmap.is_iomem)
+ state.buffer = kmalloc(state.max_size, GFP_KERNEL);
+
ret = setup_bo(&state);
- if (ret)
+ if (ret) {
+ kfree(state.buffer);
return ret;
+ }
/*
* Align to 64B cacheline so there's no garbage at the end for CS to
@@ -1221,6 +1292,7 @@ setup_indirect_ctx(struct xe_lrc *lrc, struct xe_hw_engine *hwe)
}
finish_bo(&state);
+ kfree(state.buffer);
xe_lrc_write_ctx_reg(lrc,
CTX_CS_INDIRECT_CTX,
@@ -1439,6 +1511,23 @@ void xe_lrc_destroy(struct kref *ref)
kfree(lrc);
}
+/**
+ * xe_lrc_update_hwctx_regs_with_address - Re-compute GGTT references within given LRC.
+ * @lrc: the &xe_lrc struct instance
+ */
+void xe_lrc_update_hwctx_regs_with_address(struct xe_lrc *lrc)
+{
+ if (xe_lrc_has_indirect_ring_state(lrc)) {
+ xe_lrc_write_ctx_reg(lrc, CTX_INDIRECT_RING_STATE,
+ __xe_lrc_indirect_ring_ggtt_addr(lrc));
+
+ xe_lrc_write_indirect_ctx_reg(lrc, INDIRECT_CTX_RING_START,
+ __xe_lrc_ring_ggtt_addr(lrc));
+ } else {
+ xe_lrc_write_ctx_reg(lrc, CTX_RING_START, __xe_lrc_ring_ggtt_addr(lrc));
+ }
+}
+
void xe_lrc_set_ring_tail(struct xe_lrc *lrc, u32 tail)
{
if (xe_lrc_has_indirect_ring_state(lrc))
diff --git a/drivers/gpu/drm/xe/xe_lrc.h b/drivers/gpu/drm/xe/xe_lrc.h
index b6c8053c581b..188565465779 100644
--- a/drivers/gpu/drm/xe/xe_lrc.h
+++ b/drivers/gpu/drm/xe/xe_lrc.h
@@ -42,6 +42,8 @@ struct xe_lrc_snapshot {
#define LRC_PPHWSP_FLUSH_INVAL_SCRATCH_ADDR (0x34 * 4)
#define LRC_PPHWSP_PXP_INVAL_SCRATCH_ADDR (0x40 * 4)
+#define LRC_WA_BB_SIZE SZ_4K
+
#define XE_LRC_CREATE_RUNALONE 0x1
#define XE_LRC_CREATE_PXP 0x2
struct xe_lrc *xe_lrc_create(struct xe_hw_engine *hwe, struct xe_vm *vm,
@@ -88,6 +90,10 @@ bool xe_lrc_ring_is_idle(struct xe_lrc *lrc);
u32 xe_lrc_indirect_ring_ggtt_addr(struct xe_lrc *lrc);
u32 xe_lrc_ggtt_addr(struct xe_lrc *lrc);
u32 *xe_lrc_regs(struct xe_lrc *lrc);
+void xe_lrc_update_hwctx_regs_with_address(struct xe_lrc *lrc);
+void xe_default_lrc_update_memirq_regs_with_address(struct xe_hw_engine *hwe);
+void xe_lrc_update_memirq_regs_with_address(struct xe_lrc *lrc, struct xe_hw_engine *hwe,
+ u32 *regs);
u32 xe_lrc_read_ctx_reg(struct xe_lrc *lrc, int reg_nr);
void xe_lrc_write_ctx_reg(struct xe_lrc *lrc, int reg_nr, u32 val);
@@ -106,6 +112,7 @@ s32 xe_lrc_start_seqno(struct xe_lrc *lrc);
u32 xe_lrc_parallel_ggtt_addr(struct xe_lrc *lrc);
struct iosys_map xe_lrc_parallel_map(struct xe_lrc *lrc);
+size_t xe_lrc_reg_size(struct xe_device *xe);
size_t xe_lrc_skip_size(struct xe_device *xe);
void xe_lrc_dump_default(struct drm_printer *p,
@@ -124,6 +131,8 @@ u32 xe_lrc_ctx_timestamp_udw_ggtt_addr(struct xe_lrc *lrc);
u64 xe_lrc_ctx_timestamp(struct xe_lrc *lrc);
u32 xe_lrc_ctx_job_timestamp_ggtt_addr(struct xe_lrc *lrc);
u32 xe_lrc_ctx_job_timestamp(struct xe_lrc *lrc);
+int xe_lrc_setup_wa_bb_with_scratch(struct xe_lrc *lrc, struct xe_hw_engine *hwe,
+ u32 *scratch);
/**
* xe_lrc_update_timestamp - readout LRC timestamp and update cached value
diff --git a/drivers/gpu/drm/xe/xe_pci_sriov.c b/drivers/gpu/drm/xe/xe_pci_sriov.c
index 8813efdcafbb..447a7867eecb 100644
--- a/drivers/gpu/drm/xe/xe_pci_sriov.c
+++ b/drivers/gpu/drm/xe/xe_pci_sriov.c
@@ -12,6 +12,7 @@
#include "xe_pci_sriov.h"
#include "xe_pm.h"
#include "xe_sriov.h"
+#include "xe_sriov_pf.h"
#include "xe_sriov_pf_helpers.h"
#include "xe_sriov_printk.h"
@@ -138,6 +139,10 @@ static int pf_enable_vfs(struct xe_device *xe, int num_vfs)
xe_assert(xe, num_vfs <= total_vfs);
xe_sriov_dbg(xe, "enabling %u VF%s\n", num_vfs, str_plural(num_vfs));
+ err = xe_sriov_pf_wait_ready(xe);
+ if (err)
+ goto out;
+
/*
* We must hold additional reference to the runtime PM to keep PF in D0
* during VFs lifetime, as our VFs do not implement the PM capability.
@@ -169,7 +174,7 @@ static int pf_enable_vfs(struct xe_device *xe, int num_vfs)
failed:
pf_unprovision_vfs(xe, num_vfs);
xe_pm_runtime_put(xe);
-
+out:
xe_sriov_notice(xe, "Failed to enable %u VF%s (%pe)\n",
num_vfs, str_plural(num_vfs), ERR_PTR(err));
return err;
diff --git a/drivers/gpu/drm/xe/xe_sa.c b/drivers/gpu/drm/xe/xe_sa.c
index 1d43e183ca21..fedd017d6dd3 100644
--- a/drivers/gpu/drm/xe/xe_sa.c
+++ b/drivers/gpu/drm/xe/xe_sa.c
@@ -69,7 +69,6 @@ struct xe_sa_manager *__xe_sa_bo_manager_init(struct xe_tile *tile, u32 size, u3
}
sa_manager->bo = bo;
sa_manager->is_iomem = bo->vmap.is_iomem;
- sa_manager->gpu_addr = xe_bo_ggtt_addr(bo);
if (bo->vmap.is_iomem) {
sa_manager->cpu_ptr = kvzalloc(managed_size, GFP_KERNEL);
diff --git a/drivers/gpu/drm/xe/xe_sa.h b/drivers/gpu/drm/xe/xe_sa.h
index 1170ee5a81a8..99dbf0eea540 100644
--- a/drivers/gpu/drm/xe/xe_sa.h
+++ b/drivers/gpu/drm/xe/xe_sa.h
@@ -7,6 +7,8 @@
#include <linux/sizes.h>
#include <linux/types.h>
+
+#include "xe_bo.h"
#include "xe_sa_types.h"
struct dma_fence;
@@ -43,9 +45,20 @@ to_xe_sa_manager(struct drm_suballoc_manager *mng)
return container_of(mng, struct xe_sa_manager, base);
}
+/**
+ * xe_sa_manager_gpu_addr - Retrieve GPU address of a back storage BO
+ * within suballocator.
+ * @sa_manager: the &xe_sa_manager struct instance
+ * Return: GGTT address of the back storage BO.
+ */
+static inline u64 xe_sa_manager_gpu_addr(struct xe_sa_manager *sa_manager)
+{
+ return xe_bo_ggtt_addr(sa_manager->bo);
+}
+
static inline u64 xe_sa_bo_gpu_addr(struct drm_suballoc *sa)
{
- return to_xe_sa_manager(sa->manager)->gpu_addr +
+ return xe_sa_manager_gpu_addr(to_xe_sa_manager(sa->manager)) +
drm_suballoc_soffset(sa);
}
diff --git a/drivers/gpu/drm/xe/xe_sa_types.h b/drivers/gpu/drm/xe/xe_sa_types.h
index 2b070ff1292e..cb7238799dcb 100644
--- a/drivers/gpu/drm/xe/xe_sa_types.h
+++ b/drivers/gpu/drm/xe/xe_sa_types.h
@@ -12,7 +12,6 @@ struct xe_bo;
struct xe_sa_manager {
struct drm_suballoc_manager base;
struct xe_bo *bo;
- u64 gpu_addr;
void *cpu_ptr;
bool is_iomem;
};
diff --git a/drivers/gpu/drm/xe/xe_sriov_pf.c b/drivers/gpu/drm/xe/xe_sriov_pf.c
index afbdd894bd6e..27ddf3cc80e9 100644
--- a/drivers/gpu/drm/xe/xe_sriov_pf.c
+++ b/drivers/gpu/drm/xe/xe_sriov_pf.c
@@ -9,6 +9,7 @@
#include "xe_assert.h"
#include "xe_device.h"
+#include "xe_gt_sriov_pf.h"
#include "xe_module.h"
#include "xe_sriov.h"
#include "xe_sriov_pf.h"
@@ -103,6 +104,32 @@ int xe_sriov_pf_init_early(struct xe_device *xe)
}
/**
+ * xe_sriov_pf_wait_ready() - Wait until PF is ready to operate.
+ * @xe: the &xe_device to test
+ *
+ * This function can only be called on PF.
+ *
+ * Return: 0 on success or a negative error code on failure.
+ */
+int xe_sriov_pf_wait_ready(struct xe_device *xe)
+{
+ struct xe_gt *gt;
+ unsigned int id;
+ int err;
+
+ if (xe_device_wedged(xe))
+ return -ECANCELED;
+
+ for_each_gt(gt, xe, id) {
+ err = xe_gt_sriov_pf_wait_ready(gt);
+ if (err)
+ return err;
+ }
+
+ return 0;
+}
+
+/**
* xe_sriov_pf_print_vfs_summary - Print SR-IOV PF information.
* @xe: the &xe_device to print info from
* @p: the &drm_printer
diff --git a/drivers/gpu/drm/xe/xe_sriov_pf.h b/drivers/gpu/drm/xe/xe_sriov_pf.h
index c392c3fcf085..e3b34f8f5e04 100644
--- a/drivers/gpu/drm/xe/xe_sriov_pf.h
+++ b/drivers/gpu/drm/xe/xe_sriov_pf.h
@@ -15,6 +15,7 @@ struct xe_device;
#ifdef CONFIG_PCI_IOV
bool xe_sriov_pf_readiness(struct xe_device *xe);
int xe_sriov_pf_init_early(struct xe_device *xe);
+int xe_sriov_pf_wait_ready(struct xe_device *xe);
void xe_sriov_pf_debugfs_register(struct xe_device *xe, struct dentry *root);
void xe_sriov_pf_print_vfs_summary(struct xe_device *xe, struct drm_printer *p);
#else
diff --git a/drivers/gpu/drm/xe/xe_sriov_vf.c b/drivers/gpu/drm/xe/xe_sriov_vf.c
index 26e243c28994..5de81f213d83 100644
--- a/drivers/gpu/drm/xe/xe_sriov_vf.c
+++ b/drivers/gpu/drm/xe/xe_sriov_vf.c
@@ -11,6 +11,9 @@
#include "xe_gt_sriov_printk.h"
#include "xe_gt_sriov_vf.h"
#include "xe_guc_ct.h"
+#include "xe_guc_submit.h"
+#include "xe_irq.h"
+#include "xe_lrc.h"
#include "xe_pm.h"
#include "xe_sriov.h"
#include "xe_sriov_printk.h"
@@ -147,6 +150,56 @@ void xe_sriov_vf_init_early(struct xe_device *xe)
xe_sriov_info(xe, "migration not supported by this module version\n");
}
+/**
+ * vf_post_migration_shutdown - Stop the driver activities after VF migration.
+ * @xe: the &xe_device struct instance
+ *
+ * After this VM is migrated and assigned to a new VF, it is running on a new
+ * hardware, and therefore many hardware-dependent states and related structures
+ * require fixups. Without fixups, the hardware cannot do any work, and therefore
+ * all GPU pipelines are stalled.
+ * Stop some of kernel activities to make the fixup process faster.
+ */
+static void vf_post_migration_shutdown(struct xe_device *xe)
+{
+ struct xe_gt *gt;
+ unsigned int id;
+ int ret = 0;
+
+ for_each_gt(gt, xe, id) {
+ xe_guc_submit_pause(&gt->uc.guc);
+ ret |= xe_guc_submit_reset_block(&gt->uc.guc);
+ }
+
+ if (ret)
+ drm_info(&xe->drm, "migration recovery encountered ongoing reset\n");
+}
+
+/**
+ * vf_post_migration_kickstart - Re-start the driver activities under new hardware.
+ * @xe: the &xe_device struct instance
+ *
+ * After we have finished with all post-migration fixups, restart the driver
+ * activities to continue feeding the GPU with workloads.
+ */
+static void vf_post_migration_kickstart(struct xe_device *xe)
+{
+ struct xe_gt *gt;
+ unsigned int id;
+
+ /*
+ * Make sure interrupts on the new HW are properly set. The GuC IRQ
+ * must be working at this point, since the recovery did started,
+ * but the rest was not enabled using the procedure from spec.
+ */
+ xe_irq_resume(xe);
+
+ for_each_gt(gt, xe, id) {
+ xe_guc_submit_reset_unblock(&gt->uc.guc);
+ xe_guc_submit_unpause(&gt->uc.guc);
+ }
+}
+
static bool gt_vf_post_migration_needed(struct xe_gt *gt)
{
return test_bit(gt->info.id, &gt_to_xe(gt)->sriov.vf.migration.gt_flags);
@@ -192,6 +245,11 @@ static int vf_get_next_migrated_gt_id(struct xe_device *xe)
return -1;
}
+static size_t post_migration_scratch_size(struct xe_device *xe)
+{
+ return max(xe_lrc_reg_size(xe), LRC_WA_BB_SIZE);
+}
+
/**
* Perform post-migration fixups on a single GT.
*
@@ -208,19 +266,31 @@ static int vf_get_next_migrated_gt_id(struct xe_device *xe)
static int gt_vf_post_migration_fixups(struct xe_gt *gt)
{
s64 shift;
+ void *buf;
int err;
+ buf = kmalloc(post_migration_scratch_size(gt_to_xe(gt)), GFP_KERNEL);
+ if (!buf)
+ return -ENOMEM;
+
err = xe_gt_sriov_vf_query_config(gt);
if (err)
- return err;
+ goto out;
shift = xe_gt_sriov_vf_ggtt_shift(gt);
if (shift) {
xe_tile_sriov_vf_fixup_ggtt_nodes(gt_to_tile(gt), shift);
- /* FIXME: add the recovery steps */
+ xe_gt_sriov_vf_default_lrcs_hwsp_rebase(gt);
+ err = xe_guc_contexts_hwsp_rebase(&gt->uc.guc, buf);
+ if (err)
+ goto out;
+ xe_guc_jobs_ring_rebase(&gt->uc.guc);
xe_guc_ct_fixup_messages_with_ggtt(&gt->uc.guc.ct, shift);
}
- return 0;
+
+out:
+ kfree(buf);
+ return err;
}
static void vf_post_migration_recovery(struct xe_device *xe)
@@ -230,6 +300,7 @@ static void vf_post_migration_recovery(struct xe_device *xe)
drm_dbg(&xe->drm, "migration recovery in progress\n");
xe_pm_runtime_get(xe);
+ vf_post_migration_shutdown(xe);
if (!vf_migration_supported(xe)) {
xe_sriov_err(xe, "migration not supported by this module version\n");
@@ -247,6 +318,7 @@ static void vf_post_migration_recovery(struct xe_device *xe)
set_bit(id, &fixed_gts);
}
+ vf_post_migration_kickstart(xe);
err = vf_post_migration_notify_resfix_done(xe, fixed_gts);
if (err)
goto fail;
diff --git a/drivers/gpu/drm/xe/xe_sriov_vf_ccs.c b/drivers/gpu/drm/xe/xe_sriov_vf_ccs.c
index bf9fa1238462..f0ca2a9b2bb7 100644
--- a/drivers/gpu/drm/xe/xe_sriov_vf_ccs.c
+++ b/drivers/gpu/drm/xe/xe_sriov_vf_ccs.c
@@ -169,7 +169,7 @@ static int alloc_bb_pool(struct xe_tile *tile, struct xe_tile_vf_ccs *ctx)
static void ccs_rw_update_ring(struct xe_tile_vf_ccs *ctx)
{
struct xe_lrc *lrc = xe_migrate_lrc(ctx->migrate);
- u64 addr = ctx->mem.ccs_bb_pool->gpu_addr;
+ u64 addr = xe_sa_manager_gpu_addr(ctx->mem.ccs_bb_pool);
u32 dw[10], i = 0;
dw[i++] = MI_ARB_ON_OFF | MI_ARB_ENABLE;
@@ -271,8 +271,8 @@ int xe_sriov_vf_ccs_init(struct xe_device *xe)
ctx->ctx_id = ctx_id;
migrate = xe_migrate_alloc(tile);
- if (IS_ERR(migrate)) {
- err = PTR_ERR(migrate);
+ if (!migrate) {
+ err = -ENOMEM;
goto err_ret;
}
diff --git a/drivers/gpu/drm/xe/xe_wa.c b/drivers/gpu/drm/xe/xe_wa.c
index 22a98600fd8f..535067e7fb0c 100644
--- a/drivers/gpu/drm/xe/xe_wa.c
+++ b/drivers/gpu/drm/xe/xe_wa.c
@@ -538,6 +538,11 @@ static const struct xe_rtp_entry_sr engine_was[] = {
XE_RTP_RULES(GRAPHICS_VERSION(2004), ENGINE_CLASS(RENDER)),
XE_RTP_ACTIONS(SET(HALF_SLICE_CHICKEN7, CLEAR_OPTIMIZATION_DISABLE))
},
+ { XE_RTP_NAME("13012615864"),
+ XE_RTP_RULES(GRAPHICS_VERSION(2004),
+ FUNC(xe_rtp_match_first_render_or_compute)),
+ XE_RTP_ACTIONS(SET(TDL_TSL_CHICKEN, RES_CHK_SPR_DIS))
+ },
/* Xe2_HPG */
@@ -602,6 +607,11 @@ static const struct xe_rtp_entry_sr engine_was[] = {
FUNC(xe_rtp_match_first_render_or_compute)),
XE_RTP_ACTIONS(SET(TDL_TSL_CHICKEN, STK_ID_RESTRICT))
},
+ { XE_RTP_NAME("13012615864"),
+ XE_RTP_RULES(GRAPHICS_VERSION_RANGE(2001, 2002),
+ FUNC(xe_rtp_match_first_render_or_compute)),
+ XE_RTP_ACTIONS(SET(TDL_TSL_CHICKEN, RES_CHK_SPR_DIS))
+ },
/* Xe2_LPM */
@@ -647,7 +657,8 @@ static const struct xe_rtp_entry_sr engine_was[] = {
XE_RTP_ACTIONS(SET(TDL_CHICKEN, QID_WAIT_FOR_THREAD_NOT_RUN_DISABLE))
},
{ XE_RTP_NAME("13012615864"),
- XE_RTP_RULES(GRAPHICS_VERSION_RANGE(3000, 3001),
+ XE_RTP_RULES(GRAPHICS_VERSION_RANGE(3000, 3001), OR,
+ GRAPHICS_VERSION(3003),
FUNC(xe_rtp_match_first_render_or_compute)),
XE_RTP_ACTIONS(SET(TDL_TSL_CHICKEN, RES_CHK_SPR_DIS))
},
diff --git a/drivers/i2c/busses/Kconfig b/drivers/i2c/busses/Kconfig
index c8d115b58e44..070d014fdc5d 100644
--- a/drivers/i2c/busses/Kconfig
+++ b/drivers/i2c/busses/Kconfig
@@ -992,7 +992,6 @@ config I2C_APPLE
tristate "Apple SMBus platform driver"
depends on !I2C_PASEMI
depends on ARCH_APPLE || COMPILE_TEST
- default ARCH_APPLE
help
Say Y here if you want to use the I2C controller present on Apple
Silicon chips such as the M1.
diff --git a/drivers/i2c/i2c-core-acpi.c b/drivers/i2c/i2c-core-acpi.c
index 3445cc3b476b..ed90858a27b7 100644
--- a/drivers/i2c/i2c-core-acpi.c
+++ b/drivers/i2c/i2c-core-acpi.c
@@ -370,6 +370,7 @@ static const struct acpi_device_id i2c_acpi_force_100khz_device_ids[] = {
* the device works without issues on Windows at what is expected to be
* a 400KHz frequency. The root cause of the issue is not known.
*/
+ { "DLL0945", 0 },
{ "ELAN06FA", 0 },
{}
};
diff --git a/drivers/i2c/muxes/i2c-mux-mule.c b/drivers/i2c/muxes/i2c-mux-mule.c
index 284ff4afeeac..d3b32b794172 100644
--- a/drivers/i2c/muxes/i2c-mux-mule.c
+++ b/drivers/i2c/muxes/i2c-mux-mule.c
@@ -47,7 +47,6 @@ static int mule_i2c_mux_probe(struct platform_device *pdev)
struct mule_i2c_reg_mux *priv;
struct i2c_client *client;
struct i2c_mux_core *muxc;
- struct device_node *dev;
unsigned int readback;
int ndev, ret;
bool old_fw;
@@ -95,7 +94,7 @@ static int mule_i2c_mux_probe(struct platform_device *pdev)
"Failed to register mux remove\n");
/* Create device adapters */
- for_each_child_of_node(mux_dev->of_node, dev) {
+ for_each_child_of_node_scoped(mux_dev->of_node, dev) {
u32 reg;
ret = of_property_read_u32(dev, "reg", &reg);
diff --git a/drivers/iio/accel/sca3300.c b/drivers/iio/accel/sca3300.c
index bda370c0f660..8380b237831c 100644
--- a/drivers/iio/accel/sca3300.c
+++ b/drivers/iio/accel/sca3300.c
@@ -477,7 +477,7 @@ static irqreturn_t sca3300_trigger_handler(int irq, void *p)
struct iio_dev *indio_dev = pf->indio_dev;
struct sca3300_data *data = iio_priv(indio_dev);
int bit, ret, val, i = 0;
- IIO_DECLARE_BUFFER_WITH_TS(s16, channels, SCA3300_SCAN_MAX);
+ IIO_DECLARE_BUFFER_WITH_TS(s16, channels, SCA3300_SCAN_MAX) = { };
iio_for_each_active_channel(indio_dev, bit) {
ret = sca3300_read_reg(data, indio_dev->channels[bit].address, &val);
diff --git a/drivers/iio/adc/ad7124.c b/drivers/iio/adc/ad7124.c
index 9808df2e9242..4d8c6bafd1c3 100644
--- a/drivers/iio/adc/ad7124.c
+++ b/drivers/iio/adc/ad7124.c
@@ -849,7 +849,7 @@ enum {
static int ad7124_syscalib_locked(struct ad7124_state *st, const struct iio_chan_spec *chan)
{
struct device *dev = &st->sd.spi->dev;
- struct ad7124_channel *ch = &st->channels[chan->channel];
+ struct ad7124_channel *ch = &st->channels[chan->address];
int ret;
if (ch->syscalib_mode == AD7124_SYSCALIB_ZERO_SCALE) {
@@ -865,8 +865,8 @@ static int ad7124_syscalib_locked(struct ad7124_state *st, const struct iio_chan
if (ret < 0)
return ret;
- dev_dbg(dev, "offset for channel %d after zero-scale calibration: 0x%x\n",
- chan->channel, ch->cfg.calibration_offset);
+ dev_dbg(dev, "offset for channel %lu after zero-scale calibration: 0x%x\n",
+ chan->address, ch->cfg.calibration_offset);
} else {
ch->cfg.calibration_gain = st->gain_default;
@@ -880,8 +880,8 @@ static int ad7124_syscalib_locked(struct ad7124_state *st, const struct iio_chan
if (ret < 0)
return ret;
- dev_dbg(dev, "gain for channel %d after full-scale calibration: 0x%x\n",
- chan->channel, ch->cfg.calibration_gain);
+ dev_dbg(dev, "gain for channel %lu after full-scale calibration: 0x%x\n",
+ chan->address, ch->cfg.calibration_gain);
}
return 0;
@@ -924,7 +924,7 @@ static int ad7124_set_syscalib_mode(struct iio_dev *indio_dev,
{
struct ad7124_state *st = iio_priv(indio_dev);
- st->channels[chan->channel].syscalib_mode = mode;
+ st->channels[chan->address].syscalib_mode = mode;
return 0;
}
@@ -934,7 +934,7 @@ static int ad7124_get_syscalib_mode(struct iio_dev *indio_dev,
{
struct ad7124_state *st = iio_priv(indio_dev);
- return st->channels[chan->channel].syscalib_mode;
+ return st->channels[chan->address].syscalib_mode;
}
static const struct iio_enum ad7124_syscalib_mode_enum = {
diff --git a/drivers/iio/adc/ad7173.c b/drivers/iio/adc/ad7173.c
index 4413207be28f..683146e83ab2 100644
--- a/drivers/iio/adc/ad7173.c
+++ b/drivers/iio/adc/ad7173.c
@@ -200,7 +200,7 @@ struct ad7173_channel_config {
/*
* Following fields are used to compare equality. If you
* make adaptations in it, you most likely also have to adapt
- * ad7173_find_live_config(), too.
+ * ad7173_is_setup_equal(), too.
*/
struct_group(config_props,
bool bipolar;
@@ -561,12 +561,19 @@ static void ad7173_reset_usage_cnts(struct ad7173_state *st)
st->config_usage_counter = 0;
}
-static struct ad7173_channel_config *
-ad7173_find_live_config(struct ad7173_state *st, struct ad7173_channel_config *cfg)
+/**
+ * ad7173_is_setup_equal - Compare two channel setups
+ * @cfg1: First channel configuration
+ * @cfg2: Second channel configuration
+ *
+ * Compares all configuration options that affect the registers connected to
+ * SETUP_SEL, namely CONFIGx, FILTERx, GAINx and OFFSETx.
+ *
+ * Returns: true if the setups are identical, false otherwise
+ */
+static bool ad7173_is_setup_equal(const struct ad7173_channel_config *cfg1,
+ const struct ad7173_channel_config *cfg2)
{
- struct ad7173_channel_config *cfg_aux;
- int i;
-
/*
* This is just to make sure that the comparison is adapted after
* struct ad7173_channel_config was changed.
@@ -579,14 +586,22 @@ ad7173_find_live_config(struct ad7173_state *st, struct ad7173_channel_config *c
u8 ref_sel;
}));
+ return cfg1->bipolar == cfg2->bipolar &&
+ cfg1->input_buf == cfg2->input_buf &&
+ cfg1->odr == cfg2->odr &&
+ cfg1->ref_sel == cfg2->ref_sel;
+}
+
+static struct ad7173_channel_config *
+ad7173_find_live_config(struct ad7173_state *st, struct ad7173_channel_config *cfg)
+{
+ struct ad7173_channel_config *cfg_aux;
+ int i;
+
for (i = 0; i < st->num_channels; i++) {
cfg_aux = &st->channels[i].cfg;
- if (cfg_aux->live &&
- cfg->bipolar == cfg_aux->bipolar &&
- cfg->input_buf == cfg_aux->input_buf &&
- cfg->odr == cfg_aux->odr &&
- cfg->ref_sel == cfg_aux->ref_sel)
+ if (cfg_aux->live && ad7173_is_setup_equal(cfg, cfg_aux))
return cfg_aux;
}
return NULL;
@@ -1228,7 +1243,7 @@ static int ad7173_update_scan_mode(struct iio_dev *indio_dev,
const unsigned long *scan_mask)
{
struct ad7173_state *st = iio_priv(indio_dev);
- int i, ret;
+ int i, j, k, ret;
for (i = 0; i < indio_dev->num_channels; i++) {
if (test_bit(i, scan_mask))
@@ -1239,6 +1254,54 @@ static int ad7173_update_scan_mode(struct iio_dev *indio_dev,
return ret;
}
+ /*
+ * On some chips, there are more channels that setups, so if there were
+ * more unique setups requested than the number of available slots,
+ * ad7173_set_channel() will have written over some of the slots. We
+ * can detect this by making sure each assigned cfg_slot matches the
+ * requested configuration. If it doesn't, we know that the slot was
+ * overwritten by a different channel.
+ */
+ for_each_set_bit(i, scan_mask, indio_dev->num_channels) {
+ const struct ad7173_channel_config *cfg1, *cfg2;
+
+ cfg1 = &st->channels[i].cfg;
+
+ for_each_set_bit(j, scan_mask, indio_dev->num_channels) {
+ cfg2 = &st->channels[j].cfg;
+
+ /*
+ * Only compare configs that are assigned to the same
+ * SETUP_SEL slot and don't compare channel to itself.
+ */
+ if (i == j || cfg1->cfg_slot != cfg2->cfg_slot)
+ continue;
+
+ /*
+ * If we find two different configs trying to use the
+ * same SETUP_SEL slot, then we know that the that we
+ * have too many unique configurations requested for
+ * the available slots and at least one was overwritten.
+ */
+ if (!ad7173_is_setup_equal(cfg1, cfg2)) {
+ /*
+ * At this point, there isn't a way to tell
+ * which setups are actually programmed in the
+ * ADC anymore, so we could read them back to
+ * see, but it is simpler to just turn off all
+ * of the live flags so that everything gets
+ * reprogramed on the next attempt read a sample.
+ */
+ for (k = 0; k < st->num_channels; k++)
+ st->channels[k].cfg.live = false;
+
+ dev_err(&st->sd.spi->dev,
+ "Too many unique channel configurations requested for scan\n");
+ return -EINVAL;
+ }
+ }
+ }
+
return 0;
}
diff --git a/drivers/iio/proximity/isl29501.c b/drivers/iio/proximity/isl29501.c
index d1510fe24050..f69db6f2f380 100644
--- a/drivers/iio/proximity/isl29501.c
+++ b/drivers/iio/proximity/isl29501.c
@@ -938,12 +938,18 @@ static irqreturn_t isl29501_trigger_handler(int irq, void *p)
struct iio_dev *indio_dev = pf->indio_dev;
struct isl29501_private *isl29501 = iio_priv(indio_dev);
const unsigned long *active_mask = indio_dev->active_scan_mask;
- u32 buffer[4] __aligned(8) = {}; /* 1x16-bit + naturally aligned ts */
-
- if (test_bit(ISL29501_DISTANCE_SCAN_INDEX, active_mask))
- isl29501_register_read(isl29501, REG_DISTANCE, buffer);
+ u32 value;
+ struct {
+ u16 data;
+ aligned_s64 ts;
+ } scan = { };
+
+ if (test_bit(ISL29501_DISTANCE_SCAN_INDEX, active_mask)) {
+ isl29501_register_read(isl29501, REG_DISTANCE, &value);
+ scan.data = value;
+ }
- iio_push_to_buffers_with_timestamp(indio_dev, buffer, pf->timestamp);
+ iio_push_to_buffers_with_timestamp(indio_dev, &scan, pf->timestamp);
iio_trigger_notify_done(indio_dev->trig);
return IRQ_HANDLED;
diff --git a/drivers/iio/temperature/maxim_thermocouple.c b/drivers/iio/temperature/maxim_thermocouple.c
index cae8e84821d7..205939680fd4 100644
--- a/drivers/iio/temperature/maxim_thermocouple.c
+++ b/drivers/iio/temperature/maxim_thermocouple.c
@@ -11,6 +11,7 @@
#include <linux/module.h>
#include <linux/err.h>
#include <linux/spi/spi.h>
+#include <linux/types.h>
#include <linux/iio/iio.h>
#include <linux/iio/sysfs.h>
#include <linux/iio/trigger.h>
@@ -121,8 +122,15 @@ struct maxim_thermocouple_data {
struct spi_device *spi;
const struct maxim_thermocouple_chip *chip;
char tc_type;
-
- u8 buffer[16] __aligned(IIO_DMA_MINALIGN);
+ /* Buffer for reading up to 2 hardware channels. */
+ struct {
+ union {
+ __be16 raw16;
+ __be32 raw32;
+ __be16 raw[2];
+ };
+ aligned_s64 timestamp;
+ } buffer __aligned(IIO_DMA_MINALIGN);
};
static int maxim_thermocouple_read(struct maxim_thermocouple_data *data,
@@ -130,18 +138,16 @@ static int maxim_thermocouple_read(struct maxim_thermocouple_data *data,
{
unsigned int storage_bytes = data->chip->read_size;
unsigned int shift = chan->scan_type.shift + (chan->address * 8);
- __be16 buf16;
- __be32 buf32;
int ret;
switch (storage_bytes) {
case 2:
- ret = spi_read(data->spi, (void *)&buf16, storage_bytes);
- *val = be16_to_cpu(buf16);
+ ret = spi_read(data->spi, &data->buffer.raw16, storage_bytes);
+ *val = be16_to_cpu(data->buffer.raw16);
break;
case 4:
- ret = spi_read(data->spi, (void *)&buf32, storage_bytes);
- *val = be32_to_cpu(buf32);
+ ret = spi_read(data->spi, &data->buffer.raw32, storage_bytes);
+ *val = be32_to_cpu(data->buffer.raw32);
break;
default:
ret = -EINVAL;
@@ -166,9 +172,9 @@ static irqreturn_t maxim_thermocouple_trigger_handler(int irq, void *private)
struct maxim_thermocouple_data *data = iio_priv(indio_dev);
int ret;
- ret = spi_read(data->spi, data->buffer, data->chip->read_size);
+ ret = spi_read(data->spi, data->buffer.raw, data->chip->read_size);
if (!ret) {
- iio_push_to_buffers_with_ts(indio_dev, data->buffer,
+ iio_push_to_buffers_with_ts(indio_dev, &data->buffer,
sizeof(data->buffer),
iio_get_time_ns(indio_dev));
}
diff --git a/drivers/input/misc/max77693-haptic.c b/drivers/input/misc/max77693-haptic.c
index 1dfd7b95a4ce..5d45680d74a4 100644
--- a/drivers/input/misc/max77693-haptic.c
+++ b/drivers/input/misc/max77693-haptic.c
@@ -68,15 +68,16 @@ struct max77693_haptic {
static int max77693_haptic_set_duty_cycle(struct max77693_haptic *haptic)
{
- struct pwm_args pargs;
- int delta;
+ struct pwm_state state;
int error;
- pwm_get_args(haptic->pwm_dev, &pargs);
- delta = (pargs.period + haptic->pwm_duty) / 2;
- error = pwm_config(haptic->pwm_dev, delta, pargs.period);
+ pwm_init_state(haptic->pwm_dev, &state);
+ state.duty_cycle = (state.period + haptic->pwm_duty) / 2;
+
+ error = pwm_apply_might_sleep(haptic->pwm_dev, &state);
if (error) {
- dev_err(haptic->dev, "failed to configure pwm: %d\n", error);
+ dev_err(haptic->dev,
+ "failed to set pwm duty cycle: %d\n", error);
return error;
}
@@ -166,12 +167,17 @@ static int max77693_haptic_lowsys(struct max77693_haptic *haptic, bool enable)
static void max77693_haptic_enable(struct max77693_haptic *haptic)
{
+ struct pwm_state state;
int error;
if (haptic->enabled)
return;
- error = pwm_enable(haptic->pwm_dev);
+ pwm_init_state(haptic->pwm_dev, &state);
+ state.duty_cycle = (state.period + haptic->pwm_duty) / 2;
+ state.enabled = true;
+
+ error = pwm_apply_might_sleep(haptic->pwm_dev, &state);
if (error) {
dev_err(haptic->dev,
"failed to enable haptic pwm device: %d\n", error);
@@ -224,18 +230,13 @@ static void max77693_haptic_play_work(struct work_struct *work)
{
struct max77693_haptic *haptic =
container_of(work, struct max77693_haptic, work);
- int error;
-
- error = max77693_haptic_set_duty_cycle(haptic);
- if (error) {
- dev_err(haptic->dev, "failed to set duty cycle: %d\n", error);
- return;
- }
- if (haptic->magnitude)
- max77693_haptic_enable(haptic);
- else
+ if (!haptic->magnitude)
max77693_haptic_disable(haptic);
+ else if (haptic->enabled)
+ max77693_haptic_set_duty_cycle(haptic);
+ else
+ max77693_haptic_enable(haptic);
}
static int max77693_haptic_play_effect(struct input_dev *dev, void *data,
@@ -340,12 +341,6 @@ static int max77693_haptic_probe(struct platform_device *pdev)
return PTR_ERR(haptic->pwm_dev);
}
- /*
- * FIXME: pwm_apply_args() should be removed when switching to the
- * atomic PWM API.
- */
- pwm_apply_args(haptic->pwm_dev);
-
haptic->motor_reg = devm_regulator_get(&pdev->dev, "haptic");
if (IS_ERR(haptic->motor_reg)) {
dev_err(&pdev->dev, "failed to get regulator\n");
diff --git a/drivers/irqchip/irq-riscv-imsic-platform.c b/drivers/irqchip/irq-riscv-imsic-platform.c
index 74a2a28f9403..643c8e459611 100644
--- a/drivers/irqchip/irq-riscv-imsic-platform.c
+++ b/drivers/irqchip/irq-riscv-imsic-platform.c
@@ -308,7 +308,6 @@ static const struct msi_parent_ops imsic_msi_parent_ops = {
int imsic_irqdomain_init(void)
{
struct irq_domain_info info = {
- .fwnode = imsic->fwnode,
.ops = &imsic_base_domain_ops,
.host_data = imsic,
};
@@ -325,6 +324,7 @@ int imsic_irqdomain_init(void)
}
/* Create Base IRQ domain */
+ info.fwnode = imsic->fwnode,
imsic->base_domain = msi_create_parent_irq_domain(&info, &imsic_msi_parent_ops);
if (!imsic->base_domain) {
pr_err("%pfwP: failed to create IMSIC base domain\n", imsic->fwnode);
diff --git a/drivers/md/dm-raid.c b/drivers/md/dm-raid.c
index 15c538ee9537..79ea85d18e24 100644
--- a/drivers/md/dm-raid.c
+++ b/drivers/md/dm-raid.c
@@ -438,7 +438,7 @@ static bool rs_is_reshapable(struct raid_set *rs)
/* Return true, if raid set in @rs is recovering */
static bool rs_is_recovering(struct raid_set *rs)
{
- return rs->md.recovery_cp < rs->md.dev_sectors;
+ return rs->md.resync_offset < rs->md.dev_sectors;
}
/* Return true, if raid set in @rs is reshaping */
@@ -768,7 +768,7 @@ static struct raid_set *raid_set_alloc(struct dm_target *ti, struct raid_type *r
rs->md.layout = raid_type->algorithm;
rs->md.new_layout = rs->md.layout;
rs->md.delta_disks = 0;
- rs->md.recovery_cp = MaxSector;
+ rs->md.resync_offset = MaxSector;
for (i = 0; i < raid_devs; i++)
md_rdev_init(&rs->dev[i].rdev);
@@ -912,7 +912,7 @@ static int parse_dev_params(struct raid_set *rs, struct dm_arg_set *as)
rs->md.external = 0;
rs->md.persistent = 1;
rs->md.major_version = 2;
- } else if (rebuild && !rs->md.recovery_cp) {
+ } else if (rebuild && !rs->md.resync_offset) {
/*
* Without metadata, we will not be able to tell if the array
* is in-sync or not - we must assume it is not. Therefore,
@@ -1695,20 +1695,20 @@ static void rs_setup_recovery(struct raid_set *rs, sector_t dev_sectors)
{
/* raid0 does not recover */
if (rs_is_raid0(rs))
- rs->md.recovery_cp = MaxSector;
+ rs->md.resync_offset = MaxSector;
/*
* A raid6 set has to be recovered either
* completely or for the grown part to
* ensure proper parity and Q-Syndrome
*/
else if (rs_is_raid6(rs))
- rs->md.recovery_cp = dev_sectors;
+ rs->md.resync_offset = dev_sectors;
/*
* Other raid set types may skip recovery
* depending on the 'nosync' flag.
*/
else
- rs->md.recovery_cp = test_bit(__CTR_FLAG_NOSYNC, &rs->ctr_flags)
+ rs->md.resync_offset = test_bit(__CTR_FLAG_NOSYNC, &rs->ctr_flags)
? MaxSector : dev_sectors;
}
@@ -2143,7 +2143,7 @@ static void super_sync(struct mddev *mddev, struct md_rdev *rdev)
sb->events = cpu_to_le64(mddev->events);
sb->disk_recovery_offset = cpu_to_le64(rdev->recovery_offset);
- sb->array_resync_offset = cpu_to_le64(mddev->recovery_cp);
+ sb->array_resync_offset = cpu_to_le64(mddev->resync_offset);
sb->level = cpu_to_le32(mddev->level);
sb->layout = cpu_to_le32(mddev->layout);
@@ -2334,18 +2334,18 @@ static int super_init_validation(struct raid_set *rs, struct md_rdev *rdev)
}
if (!test_bit(__CTR_FLAG_NOSYNC, &rs->ctr_flags))
- mddev->recovery_cp = le64_to_cpu(sb->array_resync_offset);
+ mddev->resync_offset = le64_to_cpu(sb->array_resync_offset);
/*
* During load, we set FirstUse if a new superblock was written.
* There are two reasons we might not have a superblock:
* 1) The raid set is brand new - in which case, all of the
* devices must have their In_sync bit set. Also,
- * recovery_cp must be 0, unless forced.
+ * resync_offset must be 0, unless forced.
* 2) This is a new device being added to an old raid set
* and the new device needs to be rebuilt - in which
* case the In_sync bit will /not/ be set and
- * recovery_cp must be MaxSector.
+ * resync_offset must be MaxSector.
* 3) This is/are a new device(s) being added to an old
* raid set during takeover to a higher raid level
* to provide capacity for redundancy or during reshape
@@ -2390,8 +2390,8 @@ static int super_init_validation(struct raid_set *rs, struct md_rdev *rdev)
new_devs > 1 ? "s" : "");
return -EINVAL;
} else if (!test_bit(__CTR_FLAG_REBUILD, &rs->ctr_flags) && rs_is_recovering(rs)) {
- DMERR("'rebuild' specified while raid set is not in-sync (recovery_cp=%llu)",
- (unsigned long long) mddev->recovery_cp);
+ DMERR("'rebuild' specified while raid set is not in-sync (resync_offset=%llu)",
+ (unsigned long long) mddev->resync_offset);
return -EINVAL;
} else if (rs_is_reshaping(rs)) {
DMERR("'rebuild' specified while raid set is being reshaped (reshape_position=%llu)",
@@ -2700,11 +2700,11 @@ static int rs_adjust_data_offsets(struct raid_set *rs)
}
out:
/*
- * Raise recovery_cp in case data_offset != 0 to
+ * Raise resync_offset in case data_offset != 0 to
* avoid false recovery positives in the constructor.
*/
- if (rs->md.recovery_cp < rs->md.dev_sectors)
- rs->md.recovery_cp += rs->dev[0].rdev.data_offset;
+ if (rs->md.resync_offset < rs->md.dev_sectors)
+ rs->md.resync_offset += rs->dev[0].rdev.data_offset;
/* Adjust data offsets on all rdevs but on any raid4/5/6 journal device */
rdev_for_each(rdev, &rs->md) {
@@ -2759,7 +2759,7 @@ static int rs_setup_takeover(struct raid_set *rs)
}
clear_bit(MD_ARRAY_FIRST_USE, &mddev->flags);
- mddev->recovery_cp = MaxSector;
+ mddev->resync_offset = MaxSector;
while (d--) {
rdev = &rs->dev[d].rdev;
@@ -2767,7 +2767,7 @@ static int rs_setup_takeover(struct raid_set *rs)
if (test_bit(d, (void *) rs->rebuild_disks)) {
clear_bit(In_sync, &rdev->flags);
clear_bit(Faulty, &rdev->flags);
- mddev->recovery_cp = rdev->recovery_offset = 0;
+ mddev->resync_offset = rdev->recovery_offset = 0;
/* Bitmap has to be created when we do an "up" takeover */
set_bit(MD_ARRAY_FIRST_USE, &mddev->flags);
}
@@ -3225,7 +3225,7 @@ size_check:
if (r)
goto bad;
- rs_setup_recovery(rs, rs->md.recovery_cp < rs->md.dev_sectors ? rs->md.recovery_cp : rs->md.dev_sectors);
+ rs_setup_recovery(rs, rs->md.resync_offset < rs->md.dev_sectors ? rs->md.resync_offset : rs->md.dev_sectors);
} else {
/* This is no size change or it is shrinking, update size and record in superblocks */
r = rs_set_dev_and_array_sectors(rs, rs->ti->len, false);
@@ -3449,7 +3449,7 @@ static sector_t rs_get_progress(struct raid_set *rs, unsigned long recovery,
} else {
if (state == st_idle && !test_bit(MD_RECOVERY_INTR, &recovery))
- r = mddev->recovery_cp;
+ r = mddev->resync_offset;
else
r = mddev->curr_resync_completed;
@@ -4077,9 +4077,9 @@ static int raid_preresume(struct dm_target *ti)
}
/* Check for any resize/reshape on @rs and adjust/initiate */
- if (mddev->recovery_cp && mddev->recovery_cp < MaxSector) {
+ if (mddev->resync_offset && mddev->resync_offset < MaxSector) {
set_bit(MD_RECOVERY_REQUESTED, &mddev->recovery);
- mddev->resync_min = mddev->recovery_cp;
+ mddev->resync_min = mddev->resync_offset;
if (test_bit(RT_FLAG_RS_GROW, &rs->runtime_flags))
mddev->resync_max_sectors = mddev->dev_sectors;
}
diff --git a/drivers/md/md-bitmap.c b/drivers/md/md-bitmap.c
index 7f524a26cebc..334b71404930 100644
--- a/drivers/md/md-bitmap.c
+++ b/drivers/md/md-bitmap.c
@@ -1987,12 +1987,12 @@ static void bitmap_dirty_bits(struct mddev *mddev, unsigned long s,
md_bitmap_set_memory_bits(bitmap, sec, 1);
md_bitmap_file_set_bit(bitmap, sec);
- if (sec < bitmap->mddev->recovery_cp)
+ if (sec < bitmap->mddev->resync_offset)
/* We are asserting that the array is dirty,
- * so move the recovery_cp address back so
+ * so move the resync_offset address back so
* that it is obvious that it is dirty
*/
- bitmap->mddev->recovery_cp = sec;
+ bitmap->mddev->resync_offset = sec;
}
}
@@ -2258,7 +2258,7 @@ static int bitmap_load(struct mddev *mddev)
|| bitmap->events_cleared == mddev->events)
/* no need to keep dirty bits to optimise a
* re-add of a missing device */
- start = mddev->recovery_cp;
+ start = mddev->resync_offset;
mutex_lock(&mddev->bitmap_info.mutex);
err = md_bitmap_init_from_disk(bitmap, start);
diff --git a/drivers/md/md-cluster.c b/drivers/md/md-cluster.c
index 94221d964d4f..5497eaee96e7 100644
--- a/drivers/md/md-cluster.c
+++ b/drivers/md/md-cluster.c
@@ -337,11 +337,11 @@ static void recover_bitmaps(struct md_thread *thread)
md_wakeup_thread(mddev->sync_thread);
if (hi > 0) {
- if (lo < mddev->recovery_cp)
- mddev->recovery_cp = lo;
+ if (lo < mddev->resync_offset)
+ mddev->resync_offset = lo;
/* wake up thread to continue resync in case resync
* is not finished */
- if (mddev->recovery_cp != MaxSector) {
+ if (mddev->resync_offset != MaxSector) {
/*
* clear the REMOTE flag since we will launch
* resync thread in current node.
@@ -863,9 +863,9 @@ static int gather_all_resync_info(struct mddev *mddev, int total_slots)
lockres_free(bm_lockres);
continue;
}
- if ((hi > 0) && (lo < mddev->recovery_cp)) {
+ if ((hi > 0) && (lo < mddev->resync_offset)) {
set_bit(MD_RECOVERY_NEEDED, &mddev->recovery);
- mddev->recovery_cp = lo;
+ mddev->resync_offset = lo;
md_check_recovery(mddev);
}
@@ -1027,7 +1027,7 @@ static int leave(struct mddev *mddev)
* Also, we should send BITMAP_NEEDS_SYNC message in
* case reshaping is interrupted.
*/
- if ((cinfo->slot_number > 0 && mddev->recovery_cp != MaxSector) ||
+ if ((cinfo->slot_number > 0 && mddev->resync_offset != MaxSector) ||
(mddev->reshape_position != MaxSector &&
test_bit(MD_CLOSING, &mddev->flags)))
resync_bitmap(mddev);
@@ -1605,8 +1605,8 @@ static int gather_bitmaps(struct md_rdev *rdev)
pr_warn("md-cluster: Could not gather bitmaps from slot %d", sn);
goto out;
}
- if ((hi > 0) && (lo < mddev->recovery_cp))
- mddev->recovery_cp = lo;
+ if ((hi > 0) && (lo < mddev->resync_offset))
+ mddev->resync_offset = lo;
}
out:
return err;
diff --git a/drivers/md/md.c b/drivers/md/md.c
index 046fe85c76fe..ac85ec73a409 100644
--- a/drivers/md/md.c
+++ b/drivers/md/md.c
@@ -637,6 +637,12 @@ static void __mddev_put(struct mddev *mddev)
return;
/*
+ * If array is freed by stopping array, MD_DELETED is set by
+ * do_md_stop(), MD_DELETED is still set here in case mddev is freed
+ * directly by closing a mddev that is created by create_on_open.
+ */
+ set_bit(MD_DELETED, &mddev->flags);
+ /*
* Call queue_work inside the spinlock so that flush_workqueue() after
* mddev_find will succeed in waiting for the work to be done.
*/
@@ -1409,13 +1415,13 @@ static int super_90_validate(struct mddev *mddev, struct md_rdev *freshest, stru
mddev->layout = -1;
if (sb->state & (1<<MD_SB_CLEAN))
- mddev->recovery_cp = MaxSector;
+ mddev->resync_offset = MaxSector;
else {
if (sb->events_hi == sb->cp_events_hi &&
sb->events_lo == sb->cp_events_lo) {
- mddev->recovery_cp = sb->recovery_cp;
+ mddev->resync_offset = sb->resync_offset;
} else
- mddev->recovery_cp = 0;
+ mddev->resync_offset = 0;
}
memcpy(mddev->uuid+0, &sb->set_uuid0, 4);
@@ -1541,13 +1547,13 @@ static void super_90_sync(struct mddev *mddev, struct md_rdev *rdev)
mddev->minor_version = sb->minor_version;
if (mddev->in_sync)
{
- sb->recovery_cp = mddev->recovery_cp;
+ sb->resync_offset = mddev->resync_offset;
sb->cp_events_hi = (mddev->events>>32);
sb->cp_events_lo = (u32)mddev->events;
- if (mddev->recovery_cp == MaxSector)
+ if (mddev->resync_offset == MaxSector)
sb->state = (1<< MD_SB_CLEAN);
} else
- sb->recovery_cp = 0;
+ sb->resync_offset = 0;
sb->layout = mddev->layout;
sb->chunk_size = mddev->chunk_sectors << 9;
@@ -1895,7 +1901,7 @@ static int super_1_validate(struct mddev *mddev, struct md_rdev *freshest, struc
mddev->bitmap_info.default_space = (4096-1024) >> 9;
mddev->reshape_backwards = 0;
- mddev->recovery_cp = le64_to_cpu(sb->resync_offset);
+ mddev->resync_offset = le64_to_cpu(sb->resync_offset);
memcpy(mddev->uuid, sb->set_uuid, 16);
mddev->max_disks = (4096-256)/2;
@@ -2081,7 +2087,7 @@ static void super_1_sync(struct mddev *mddev, struct md_rdev *rdev)
sb->utime = cpu_to_le64((__u64)mddev->utime);
sb->events = cpu_to_le64(mddev->events);
if (mddev->in_sync)
- sb->resync_offset = cpu_to_le64(mddev->recovery_cp);
+ sb->resync_offset = cpu_to_le64(mddev->resync_offset);
else if (test_bit(MD_JOURNAL_CLEAN, &mddev->flags))
sb->resync_offset = cpu_to_le64(MaxSector);
else
@@ -2761,7 +2767,7 @@ repeat:
/* If this is just a dirty<->clean transition, and the array is clean
* and 'events' is odd, we can roll back to the previous clean state */
if (nospares
- && (mddev->in_sync && mddev->recovery_cp == MaxSector)
+ && (mddev->in_sync && mddev->resync_offset == MaxSector)
&& mddev->can_decrease_events
&& mddev->events != 1) {
mddev->events--;
@@ -4297,9 +4303,9 @@ __ATTR(chunk_size, S_IRUGO|S_IWUSR, chunk_size_show, chunk_size_store);
static ssize_t
resync_start_show(struct mddev *mddev, char *page)
{
- if (mddev->recovery_cp == MaxSector)
+ if (mddev->resync_offset == MaxSector)
return sprintf(page, "none\n");
- return sprintf(page, "%llu\n", (unsigned long long)mddev->recovery_cp);
+ return sprintf(page, "%llu\n", (unsigned long long)mddev->resync_offset);
}
static ssize_t
@@ -4325,7 +4331,7 @@ resync_start_store(struct mddev *mddev, const char *buf, size_t len)
err = -EBUSY;
if (!err) {
- mddev->recovery_cp = n;
+ mddev->resync_offset = n;
if (mddev->pers)
set_bit(MD_SB_CHANGE_CLEAN, &mddev->sb_flags);
}
@@ -6417,7 +6423,7 @@ static void md_clean(struct mddev *mddev)
mddev->external_size = 0;
mddev->dev_sectors = 0;
mddev->raid_disks = 0;
- mddev->recovery_cp = 0;
+ mddev->resync_offset = 0;
mddev->resync_min = 0;
mddev->resync_max = MaxSector;
mddev->reshape_position = MaxSector;
@@ -7362,9 +7368,9 @@ int md_set_array_info(struct mddev *mddev, struct mdu_array_info_s *info)
* openned
*/
if (info->state & (1<<MD_SB_CLEAN))
- mddev->recovery_cp = MaxSector;
+ mddev->resync_offset = MaxSector;
else
- mddev->recovery_cp = 0;
+ mddev->resync_offset = 0;
mddev->persistent = ! info->not_persistent;
mddev->external = 0;
@@ -8303,7 +8309,7 @@ static int status_resync(struct seq_file *seq, struct mddev *mddev)
seq_printf(seq, "\tresync=REMOTE");
return 1;
}
- if (mddev->recovery_cp < MaxSector) {
+ if (mddev->resync_offset < MaxSector) {
seq_printf(seq, "\tresync=PENDING");
return 1;
}
@@ -8946,7 +8952,7 @@ static sector_t md_sync_position(struct mddev *mddev, enum sync_action action)
return mddev->resync_min;
case ACTION_RESYNC:
if (!mddev->bitmap)
- return mddev->recovery_cp;
+ return mddev->resync_offset;
return 0;
case ACTION_RESHAPE:
/*
@@ -9184,8 +9190,8 @@ void md_do_sync(struct md_thread *thread)
atomic_read(&mddev->recovery_active) == 0);
mddev->curr_resync_completed = j;
if (test_bit(MD_RECOVERY_SYNC, &mddev->recovery) &&
- j > mddev->recovery_cp)
- mddev->recovery_cp = j;
+ j > mddev->resync_offset)
+ mddev->resync_offset = j;
update_time = jiffies;
set_bit(MD_SB_CHANGE_CLEAN, &mddev->sb_flags);
sysfs_notify_dirent_safe(mddev->sysfs_completed);
@@ -9305,19 +9311,19 @@ void md_do_sync(struct md_thread *thread)
mddev->curr_resync > MD_RESYNC_ACTIVE) {
if (test_bit(MD_RECOVERY_SYNC, &mddev->recovery)) {
if (test_bit(MD_RECOVERY_INTR, &mddev->recovery)) {
- if (mddev->curr_resync >= mddev->recovery_cp) {
+ if (mddev->curr_resync >= mddev->resync_offset) {
pr_debug("md: checkpointing %s of %s.\n",
desc, mdname(mddev));
if (test_bit(MD_RECOVERY_ERROR,
&mddev->recovery))
- mddev->recovery_cp =
+ mddev->resync_offset =
mddev->curr_resync_completed;
else
- mddev->recovery_cp =
+ mddev->resync_offset =
mddev->curr_resync;
}
} else
- mddev->recovery_cp = MaxSector;
+ mddev->resync_offset = MaxSector;
} else {
if (!test_bit(MD_RECOVERY_INTR, &mddev->recovery))
mddev->curr_resync = MaxSector;
@@ -9421,6 +9427,12 @@ static bool rdev_is_spare(struct md_rdev *rdev)
static bool rdev_addable(struct md_rdev *rdev)
{
+ struct mddev *mddev;
+
+ mddev = READ_ONCE(rdev->mddev);
+ if (!mddev)
+ return false;
+
/* rdev is already used, don't add it again. */
if (test_bit(Candidate, &rdev->flags) || rdev->raid_disk >= 0 ||
test_bit(Faulty, &rdev->flags))
@@ -9431,7 +9443,7 @@ static bool rdev_addable(struct md_rdev *rdev)
return true;
/* Allow to add if array is read-write. */
- if (md_is_rdwr(rdev->mddev))
+ if (md_is_rdwr(mddev))
return true;
/*
@@ -9533,7 +9545,7 @@ static bool md_choose_sync_action(struct mddev *mddev, int *spares)
}
/* Check if resync is in progress. */
- if (mddev->recovery_cp < MaxSector) {
+ if (mddev->resync_offset < MaxSector) {
remove_spares(mddev, NULL);
set_bit(MD_RECOVERY_SYNC, &mddev->recovery);
clear_bit(MD_RECOVERY_RECOVER, &mddev->recovery);
@@ -9714,7 +9726,7 @@ void md_check_recovery(struct mddev *mddev)
test_bit(MD_RECOVERY_DONE, &mddev->recovery) ||
(mddev->external == 0 && mddev->safemode == 1) ||
(mddev->safemode == 2
- && !mddev->in_sync && mddev->recovery_cp == MaxSector)
+ && !mddev->in_sync && mddev->resync_offset == MaxSector)
))
return;
@@ -9771,8 +9783,8 @@ void md_check_recovery(struct mddev *mddev)
* remove disk.
*/
rdev_for_each_safe(rdev, tmp, mddev) {
- if (test_and_clear_bit(ClusterRemove, &rdev->flags) &&
- rdev->raid_disk < 0)
+ if (rdev->raid_disk < 0 &&
+ test_and_clear_bit(ClusterRemove, &rdev->flags))
md_kick_rdev_from_array(rdev);
}
}
@@ -10078,8 +10090,11 @@ static void check_sb_changes(struct mddev *mddev, struct md_rdev *rdev)
/* Check for change of roles in the active devices */
rdev_for_each_safe(rdev2, tmp, mddev) {
- if (test_bit(Faulty, &rdev2->flags))
+ if (test_bit(Faulty, &rdev2->flags)) {
+ if (test_bit(ClusterRemove, &rdev2->flags))
+ set_bit(MD_RECOVERY_NEEDED, &mddev->recovery);
continue;
+ }
/* Check if the roles changed */
role = le16_to_cpu(sb->dev_roles[rdev2->desc_nr]);
diff --git a/drivers/md/md.h b/drivers/md/md.h
index 67b365621507..51af29a03079 100644
--- a/drivers/md/md.h
+++ b/drivers/md/md.h
@@ -523,7 +523,7 @@ struct mddev {
unsigned long normal_io_events; /* IO event timestamp */
atomic_t recovery_active; /* blocks scheduled, but not written */
wait_queue_head_t recovery_wait;
- sector_t recovery_cp;
+ sector_t resync_offset;
sector_t resync_min; /* user requested sync
* starts here */
sector_t resync_max; /* resync should pause
diff --git a/drivers/md/raid0.c b/drivers/md/raid0.c
index cbe2a9054cb9..f1d8811a542a 100644
--- a/drivers/md/raid0.c
+++ b/drivers/md/raid0.c
@@ -674,7 +674,7 @@ static void *raid0_takeover_raid45(struct mddev *mddev)
mddev->raid_disks--;
mddev->delta_disks = -1;
/* make sure it will be not marked as dirty */
- mddev->recovery_cp = MaxSector;
+ mddev->resync_offset = MaxSector;
mddev_clear_unsupported_flags(mddev, UNSUPPORTED_MDDEV_FLAGS);
create_strip_zones(mddev, &priv_conf);
@@ -717,7 +717,7 @@ static void *raid0_takeover_raid10(struct mddev *mddev)
mddev->raid_disks += mddev->delta_disks;
mddev->degraded = 0;
/* make sure it will be not marked as dirty */
- mddev->recovery_cp = MaxSector;
+ mddev->resync_offset = MaxSector;
mddev_clear_unsupported_flags(mddev, UNSUPPORTED_MDDEV_FLAGS);
create_strip_zones(mddev, &priv_conf);
@@ -760,7 +760,7 @@ static void *raid0_takeover_raid1(struct mddev *mddev)
mddev->delta_disks = 1 - mddev->raid_disks;
mddev->raid_disks = 1;
/* make sure it will be not marked as dirty */
- mddev->recovery_cp = MaxSector;
+ mddev->resync_offset = MaxSector;
mddev_clear_unsupported_flags(mddev, UNSUPPORTED_MDDEV_FLAGS);
create_strip_zones(mddev, &priv_conf);
diff --git a/drivers/md/raid1-10.c b/drivers/md/raid1-10.c
index b8b3a9069701..52881e6032da 100644
--- a/drivers/md/raid1-10.c
+++ b/drivers/md/raid1-10.c
@@ -283,7 +283,7 @@ static inline int raid1_check_read_range(struct md_rdev *rdev,
static inline bool raid1_should_read_first(struct mddev *mddev,
sector_t this_sector, int len)
{
- if ((mddev->recovery_cp < this_sector + len))
+ if ((mddev->resync_offset < this_sector + len))
return true;
if (mddev_is_clustered(mddev) &&
diff --git a/drivers/md/raid1.c b/drivers/md/raid1.c
index 64b8176907a9..408c26398321 100644
--- a/drivers/md/raid1.c
+++ b/drivers/md/raid1.c
@@ -127,10 +127,9 @@ static inline struct r1bio *get_resync_r1bio(struct bio *bio)
return get_resync_pages(bio)->raid_bio;
}
-static void * r1bio_pool_alloc(gfp_t gfp_flags, void *data)
+static void *r1bio_pool_alloc(gfp_t gfp_flags, struct r1conf *conf)
{
- struct pool_info *pi = data;
- int size = offsetof(struct r1bio, bios[pi->raid_disks]);
+ int size = offsetof(struct r1bio, bios[conf->raid_disks * 2]);
/* allocate a r1bio with room for raid_disks entries in the bios array */
return kzalloc(size, gfp_flags);
@@ -145,18 +144,18 @@ static void * r1bio_pool_alloc(gfp_t gfp_flags, void *data)
static void * r1buf_pool_alloc(gfp_t gfp_flags, void *data)
{
- struct pool_info *pi = data;
+ struct r1conf *conf = data;
struct r1bio *r1_bio;
struct bio *bio;
int need_pages;
int j;
struct resync_pages *rps;
- r1_bio = r1bio_pool_alloc(gfp_flags, pi);
+ r1_bio = r1bio_pool_alloc(gfp_flags, conf);
if (!r1_bio)
return NULL;
- rps = kmalloc_array(pi->raid_disks, sizeof(struct resync_pages),
+ rps = kmalloc_array(conf->raid_disks * 2, sizeof(struct resync_pages),
gfp_flags);
if (!rps)
goto out_free_r1bio;
@@ -164,7 +163,7 @@ static void * r1buf_pool_alloc(gfp_t gfp_flags, void *data)
/*
* Allocate bios : 1 for reading, n-1 for writing
*/
- for (j = pi->raid_disks ; j-- ; ) {
+ for (j = conf->raid_disks * 2; j-- ; ) {
bio = bio_kmalloc(RESYNC_PAGES, gfp_flags);
if (!bio)
goto out_free_bio;
@@ -177,11 +176,11 @@ static void * r1buf_pool_alloc(gfp_t gfp_flags, void *data)
* If this is a user-requested check/repair, allocate
* RESYNC_PAGES for each bio.
*/
- if (test_bit(MD_RECOVERY_REQUESTED, &pi->mddev->recovery))
- need_pages = pi->raid_disks;
+ if (test_bit(MD_RECOVERY_REQUESTED, &conf->mddev->recovery))
+ need_pages = conf->raid_disks * 2;
else
need_pages = 1;
- for (j = 0; j < pi->raid_disks; j++) {
+ for (j = 0; j < conf->raid_disks * 2; j++) {
struct resync_pages *rp = &rps[j];
bio = r1_bio->bios[j];
@@ -207,7 +206,7 @@ out_free_pages:
resync_free_pages(&rps[j]);
out_free_bio:
- while (++j < pi->raid_disks) {
+ while (++j < conf->raid_disks * 2) {
bio_uninit(r1_bio->bios[j]);
kfree(r1_bio->bios[j]);
}
@@ -220,12 +219,12 @@ out_free_r1bio:
static void r1buf_pool_free(void *__r1_bio, void *data)
{
- struct pool_info *pi = data;
+ struct r1conf *conf = data;
int i;
struct r1bio *r1bio = __r1_bio;
struct resync_pages *rp = NULL;
- for (i = pi->raid_disks; i--; ) {
+ for (i = conf->raid_disks * 2; i--; ) {
rp = get_resync_pages(r1bio->bios[i]);
resync_free_pages(rp);
bio_uninit(r1bio->bios[i]);
@@ -255,7 +254,7 @@ static void free_r1bio(struct r1bio *r1_bio)
struct r1conf *conf = r1_bio->mddev->private;
put_all_bios(conf, r1_bio);
- mempool_free(r1_bio, &conf->r1bio_pool);
+ mempool_free(r1_bio, conf->r1bio_pool);
}
static void put_buf(struct r1bio *r1_bio)
@@ -1305,9 +1304,8 @@ alloc_r1bio(struct mddev *mddev, struct bio *bio)
struct r1conf *conf = mddev->private;
struct r1bio *r1_bio;
- r1_bio = mempool_alloc(&conf->r1bio_pool, GFP_NOIO);
- /* Ensure no bio records IO_BLOCKED */
- memset(r1_bio->bios, 0, conf->raid_disks * sizeof(r1_bio->bios[0]));
+ r1_bio = mempool_alloc(conf->r1bio_pool, GFP_NOIO);
+ memset(r1_bio, 0, offsetof(struct r1bio, bios[conf->raid_disks * 2]));
init_r1bio(r1_bio, mddev, bio);
return r1_bio;
}
@@ -2747,7 +2745,7 @@ static int init_resync(struct r1conf *conf)
BUG_ON(mempool_initialized(&conf->r1buf_pool));
return mempool_init(&conf->r1buf_pool, buffs, r1buf_pool_alloc,
- r1buf_pool_free, conf->poolinfo);
+ r1buf_pool_free, conf);
}
static struct r1bio *raid1_alloc_init_r1buf(struct r1conf *conf)
@@ -2757,7 +2755,7 @@ static struct r1bio *raid1_alloc_init_r1buf(struct r1conf *conf)
struct bio *bio;
int i;
- for (i = conf->poolinfo->raid_disks; i--; ) {
+ for (i = conf->raid_disks * 2; i--; ) {
bio = r1bio->bios[i];
rps = bio->bi_private;
bio_reset(bio, NULL, 0);
@@ -2822,7 +2820,7 @@ static sector_t raid1_sync_request(struct mddev *mddev, sector_t sector_nr,
}
if (mddev->bitmap == NULL &&
- mddev->recovery_cp == MaxSector &&
+ mddev->resync_offset == MaxSector &&
!test_bit(MD_RECOVERY_REQUESTED, &mddev->recovery) &&
conf->fullsync == 0) {
*skipped = 1;
@@ -3085,6 +3083,7 @@ static struct r1conf *setup_conf(struct mddev *mddev)
int i;
struct raid1_info *disk;
struct md_rdev *rdev;
+ size_t r1bio_size;
int err = -ENOMEM;
conf = kzalloc(sizeof(struct r1conf), GFP_KERNEL);
@@ -3121,21 +3120,15 @@ static struct r1conf *setup_conf(struct mddev *mddev)
if (!conf->tmppage)
goto abort;
- conf->poolinfo = kzalloc(sizeof(*conf->poolinfo), GFP_KERNEL);
- if (!conf->poolinfo)
- goto abort;
- conf->poolinfo->raid_disks = mddev->raid_disks * 2;
- err = mempool_init(&conf->r1bio_pool, NR_RAID_BIOS, r1bio_pool_alloc,
- rbio_pool_free, conf->poolinfo);
- if (err)
+ r1bio_size = offsetof(struct r1bio, bios[mddev->raid_disks * 2]);
+ conf->r1bio_pool = mempool_create_kmalloc_pool(NR_RAID_BIOS, r1bio_size);
+ if (!conf->r1bio_pool)
goto abort;
err = bioset_init(&conf->bio_split, BIO_POOL_SIZE, 0, 0);
if (err)
goto abort;
- conf->poolinfo->mddev = mddev;
-
err = -EINVAL;
spin_lock_init(&conf->device_lock);
conf->raid_disks = mddev->raid_disks;
@@ -3198,10 +3191,9 @@ static struct r1conf *setup_conf(struct mddev *mddev)
abort:
if (conf) {
- mempool_exit(&conf->r1bio_pool);
+ mempool_destroy(conf->r1bio_pool);
kfree(conf->mirrors);
safe_put_page(conf->tmppage);
- kfree(conf->poolinfo);
kfree(conf->nr_pending);
kfree(conf->nr_waiting);
kfree(conf->nr_queued);
@@ -3282,9 +3274,9 @@ static int raid1_run(struct mddev *mddev)
}
if (conf->raid_disks - mddev->degraded == 1)
- mddev->recovery_cp = MaxSector;
+ mddev->resync_offset = MaxSector;
- if (mddev->recovery_cp != MaxSector)
+ if (mddev->resync_offset != MaxSector)
pr_info("md/raid1:%s: not clean -- starting background reconstruction\n",
mdname(mddev));
pr_info("md/raid1:%s: active with %d out of %d mirrors\n",
@@ -3311,10 +3303,9 @@ static void raid1_free(struct mddev *mddev, void *priv)
{
struct r1conf *conf = priv;
- mempool_exit(&conf->r1bio_pool);
+ mempool_destroy(conf->r1bio_pool);
kfree(conf->mirrors);
safe_put_page(conf->tmppage);
- kfree(conf->poolinfo);
kfree(conf->nr_pending);
kfree(conf->nr_waiting);
kfree(conf->nr_queued);
@@ -3345,8 +3336,8 @@ static int raid1_resize(struct mddev *mddev, sector_t sectors)
md_set_array_sectors(mddev, newsize);
if (sectors > mddev->dev_sectors &&
- mddev->recovery_cp > mddev->dev_sectors) {
- mddev->recovery_cp = mddev->dev_sectors;
+ mddev->resync_offset > mddev->dev_sectors) {
+ mddev->resync_offset = mddev->dev_sectors;
set_bit(MD_RECOVERY_NEEDED, &mddev->recovery);
}
mddev->dev_sectors = sectors;
@@ -3367,17 +3358,13 @@ static int raid1_reshape(struct mddev *mddev)
* At the same time, we "pack" the devices so that all the missing
* devices have the higher raid_disk numbers.
*/
- mempool_t newpool, oldpool;
- struct pool_info *newpoolinfo;
+ mempool_t *newpool, *oldpool;
+ size_t new_r1bio_size;
struct raid1_info *newmirrors;
struct r1conf *conf = mddev->private;
int cnt, raid_disks;
unsigned long flags;
int d, d2;
- int ret;
-
- memset(&newpool, 0, sizeof(newpool));
- memset(&oldpool, 0, sizeof(oldpool));
/* Cannot change chunk_size, layout, or level */
if (mddev->chunk_sectors != mddev->new_chunk_sectors ||
@@ -3403,24 +3390,16 @@ static int raid1_reshape(struct mddev *mddev)
return -EBUSY;
}
- newpoolinfo = kmalloc(sizeof(*newpoolinfo), GFP_KERNEL);
- if (!newpoolinfo)
+ new_r1bio_size = offsetof(struct r1bio, bios[raid_disks * 2]);
+ newpool = mempool_create_kmalloc_pool(NR_RAID_BIOS, new_r1bio_size);
+ if (!newpool) {
return -ENOMEM;
- newpoolinfo->mddev = mddev;
- newpoolinfo->raid_disks = raid_disks * 2;
-
- ret = mempool_init(&newpool, NR_RAID_BIOS, r1bio_pool_alloc,
- rbio_pool_free, newpoolinfo);
- if (ret) {
- kfree(newpoolinfo);
- return ret;
}
newmirrors = kzalloc(array3_size(sizeof(struct raid1_info),
raid_disks, 2),
GFP_KERNEL);
if (!newmirrors) {
- kfree(newpoolinfo);
- mempool_exit(&newpool);
+ mempool_destroy(newpool);
return -ENOMEM;
}
@@ -3429,7 +3408,6 @@ static int raid1_reshape(struct mddev *mddev)
/* ok, everything is stopped */
oldpool = conf->r1bio_pool;
conf->r1bio_pool = newpool;
- init_waitqueue_head(&conf->r1bio_pool.wait);
for (d = d2 = 0; d < conf->raid_disks; d++) {
struct md_rdev *rdev = conf->mirrors[d].rdev;
@@ -3446,8 +3424,6 @@ static int raid1_reshape(struct mddev *mddev)
}
kfree(conf->mirrors);
conf->mirrors = newmirrors;
- kfree(conf->poolinfo);
- conf->poolinfo = newpoolinfo;
spin_lock_irqsave(&conf->device_lock, flags);
mddev->degraded += (raid_disks - conf->raid_disks);
@@ -3461,7 +3437,7 @@ static int raid1_reshape(struct mddev *mddev)
set_bit(MD_RECOVERY_NEEDED, &mddev->recovery);
md_wakeup_thread(mddev->thread);
- mempool_exit(&oldpool);
+ mempool_destroy(oldpool);
return 0;
}
diff --git a/drivers/md/raid1.h b/drivers/md/raid1.h
index 33f318fcc268..d236ef179cfb 100644
--- a/drivers/md/raid1.h
+++ b/drivers/md/raid1.h
@@ -49,22 +49,6 @@ struct raid1_info {
sector_t seq_start;
};
-/*
- * memory pools need a pointer to the mddev, so they can force an unplug
- * when memory is tight, and a count of the number of drives that the
- * pool was allocated for, so they know how much to allocate and free.
- * mddev->raid_disks cannot be used, as it can change while a pool is active
- * These two datums are stored in a kmalloced struct.
- * The 'raid_disks' here is twice the raid_disks in r1conf.
- * This allows space for each 'real' device can have a replacement in the
- * second half of the array.
- */
-
-struct pool_info {
- struct mddev *mddev;
- int raid_disks;
-};
-
struct r1conf {
struct mddev *mddev;
struct raid1_info *mirrors; /* twice 'raid_disks' to
@@ -114,11 +98,7 @@ struct r1conf {
*/
int recovery_disabled;
- /* poolinfo contains information about the content of the
- * mempools - it changes when the array grows or shrinks
- */
- struct pool_info *poolinfo;
- mempool_t r1bio_pool;
+ mempool_t *r1bio_pool;
mempool_t r1buf_pool;
struct bio_set bio_split;
diff --git a/drivers/md/raid10.c b/drivers/md/raid10.c
index 95dc354a86a0..b60c30bfb6c7 100644
--- a/drivers/md/raid10.c
+++ b/drivers/md/raid10.c
@@ -2117,7 +2117,7 @@ static int raid10_add_disk(struct mddev *mddev, struct md_rdev *rdev)
int last = conf->geo.raid_disks - 1;
struct raid10_info *p;
- if (mddev->recovery_cp < MaxSector)
+ if (mddev->resync_offset < MaxSector)
/* only hot-add to in-sync arrays, as recovery is
* very different from resync
*/
@@ -3185,7 +3185,7 @@ static sector_t raid10_sync_request(struct mddev *mddev, sector_t sector_nr,
* of a clean array, like RAID1 does.
*/
if (mddev->bitmap == NULL &&
- mddev->recovery_cp == MaxSector &&
+ mddev->resync_offset == MaxSector &&
mddev->reshape_position == MaxSector &&
!test_bit(MD_RECOVERY_SYNC, &mddev->recovery) &&
!test_bit(MD_RECOVERY_REQUESTED, &mddev->recovery) &&
@@ -4145,7 +4145,7 @@ static int raid10_run(struct mddev *mddev)
disk->recovery_disabled = mddev->recovery_disabled - 1;
}
- if (mddev->recovery_cp != MaxSector)
+ if (mddev->resync_offset != MaxSector)
pr_notice("md/raid10:%s: not clean -- starting background reconstruction\n",
mdname(mddev));
pr_info("md/raid10:%s: active with %d out of %d devices\n",
@@ -4245,8 +4245,8 @@ static int raid10_resize(struct mddev *mddev, sector_t sectors)
md_set_array_sectors(mddev, size);
if (sectors > mddev->dev_sectors &&
- mddev->recovery_cp > oldsize) {
- mddev->recovery_cp = oldsize;
+ mddev->resync_offset > oldsize) {
+ mddev->resync_offset = oldsize;
set_bit(MD_RECOVERY_NEEDED, &mddev->recovery);
}
calc_sectors(conf, sectors);
@@ -4275,7 +4275,7 @@ static void *raid10_takeover_raid0(struct mddev *mddev, sector_t size, int devs)
mddev->delta_disks = mddev->raid_disks;
mddev->raid_disks *= 2;
/* make sure it will be not marked as dirty */
- mddev->recovery_cp = MaxSector;
+ mddev->resync_offset = MaxSector;
mddev->dev_sectors = size;
conf = setup_conf(mddev);
@@ -5087,8 +5087,8 @@ static void raid10_finish_reshape(struct mddev *mddev)
return;
if (mddev->delta_disks > 0) {
- if (mddev->recovery_cp > mddev->resync_max_sectors) {
- mddev->recovery_cp = mddev->resync_max_sectors;
+ if (mddev->resync_offset > mddev->resync_max_sectors) {
+ mddev->resync_offset = mddev->resync_max_sectors;
set_bit(MD_RECOVERY_NEEDED, &mddev->recovery);
}
mddev->resync_max_sectors = mddev->array_sectors;
diff --git a/drivers/md/raid5-ppl.c b/drivers/md/raid5-ppl.c
index c0fb335311aa..56b234683ee6 100644
--- a/drivers/md/raid5-ppl.c
+++ b/drivers/md/raid5-ppl.c
@@ -1163,7 +1163,7 @@ static int ppl_load_distributed(struct ppl_log *log)
le64_to_cpu(pplhdr->generation));
/* attempt to recover from log if we are starting a dirty array */
- if (pplhdr && !mddev->pers && mddev->recovery_cp != MaxSector)
+ if (pplhdr && !mddev->pers && mddev->resync_offset != MaxSector)
ret = ppl_recover(log, pplhdr, pplhdr_offset);
/* write empty header if we are starting the array */
@@ -1422,14 +1422,14 @@ int ppl_init_log(struct r5conf *conf)
if (ret) {
goto err;
- } else if (!mddev->pers && mddev->recovery_cp == 0 &&
+ } else if (!mddev->pers && mddev->resync_offset == 0 &&
ppl_conf->recovered_entries > 0 &&
ppl_conf->mismatch_count == 0) {
/*
* If we are starting a dirty array and the recovery succeeds
* without any issues, set the array as clean.
*/
- mddev->recovery_cp = MaxSector;
+ mddev->resync_offset = MaxSector;
set_bit(MD_SB_CHANGE_CLEAN, &mddev->sb_flags);
} else if (mddev->pers && ppl_conf->mismatch_count > 0) {
/* no mismatch allowed when enabling PPL for a running array */
diff --git a/drivers/md/raid5.c b/drivers/md/raid5.c
index 7ec61ee7b218..023649fe2476 100644
--- a/drivers/md/raid5.c
+++ b/drivers/md/raid5.c
@@ -3740,7 +3740,7 @@ static int want_replace(struct stripe_head *sh, int disk_idx)
&& !test_bit(Faulty, &rdev->flags)
&& !test_bit(In_sync, &rdev->flags)
&& (rdev->recovery_offset <= sh->sector
- || rdev->mddev->recovery_cp <= sh->sector))
+ || rdev->mddev->resync_offset <= sh->sector))
rv = 1;
return rv;
}
@@ -3832,7 +3832,7 @@ static int need_this_block(struct stripe_head *sh, struct stripe_head_state *s,
* is missing/faulty, then we need to read everything we can.
*/
if (!force_rcw &&
- sh->sector < sh->raid_conf->mddev->recovery_cp)
+ sh->sector < sh->raid_conf->mddev->resync_offset)
/* reconstruct-write isn't being forced */
return 0;
for (i = 0; i < s->failed && i < 2; i++) {
@@ -4097,7 +4097,7 @@ static int handle_stripe_dirtying(struct r5conf *conf,
int disks)
{
int rmw = 0, rcw = 0, i;
- sector_t recovery_cp = conf->mddev->recovery_cp;
+ sector_t resync_offset = conf->mddev->resync_offset;
/* Check whether resync is now happening or should start.
* If yes, then the array is dirty (after unclean shutdown or
@@ -4107,14 +4107,14 @@ static int handle_stripe_dirtying(struct r5conf *conf,
* generate correct data from the parity.
*/
if (conf->rmw_level == PARITY_DISABLE_RMW ||
- (recovery_cp < MaxSector && sh->sector >= recovery_cp &&
+ (resync_offset < MaxSector && sh->sector >= resync_offset &&
s->failed == 0)) {
/* Calculate the real rcw later - for now make it
* look like rcw is cheaper
*/
rcw = 1; rmw = 2;
- pr_debug("force RCW rmw_level=%u, recovery_cp=%llu sh->sector=%llu\n",
- conf->rmw_level, (unsigned long long)recovery_cp,
+ pr_debug("force RCW rmw_level=%u, resync_offset=%llu sh->sector=%llu\n",
+ conf->rmw_level, (unsigned long long)resync_offset,
(unsigned long long)sh->sector);
} else for (i = disks; i--; ) {
/* would I have to read this buffer for read_modify_write */
@@ -4770,14 +4770,14 @@ static void analyse_stripe(struct stripe_head *sh, struct stripe_head_state *s)
if (test_bit(STRIPE_SYNCING, &sh->state)) {
/* If there is a failed device being replaced,
* we must be recovering.
- * else if we are after recovery_cp, we must be syncing
+ * else if we are after resync_offset, we must be syncing
* else if MD_RECOVERY_REQUESTED is set, we also are syncing.
* else we can only be replacing
* sync and recovery both need to read all devices, and so
* use the same flag.
*/
if (do_recovery ||
- sh->sector >= conf->mddev->recovery_cp ||
+ sh->sector >= conf->mddev->resync_offset ||
test_bit(MD_RECOVERY_REQUESTED, &(conf->mddev->recovery)))
s->syncing = 1;
else
@@ -7780,7 +7780,7 @@ static int raid5_run(struct mddev *mddev)
int first = 1;
int ret = -EIO;
- if (mddev->recovery_cp != MaxSector)
+ if (mddev->resync_offset != MaxSector)
pr_notice("md/raid:%s: not clean -- starting background reconstruction\n",
mdname(mddev));
@@ -7921,7 +7921,7 @@ static int raid5_run(struct mddev *mddev)
mdname(mddev));
mddev->ro = 1;
set_disk_ro(mddev->gendisk, 1);
- } else if (mddev->recovery_cp == MaxSector)
+ } else if (mddev->resync_offset == MaxSector)
set_bit(MD_JOURNAL_CLEAN, &mddev->flags);
}
@@ -7988,7 +7988,7 @@ static int raid5_run(struct mddev *mddev)
mddev->resync_max_sectors = mddev->dev_sectors;
if (mddev->degraded > dirty_parity_disks &&
- mddev->recovery_cp != MaxSector) {
+ mddev->resync_offset != MaxSector) {
if (test_bit(MD_HAS_PPL, &mddev->flags))
pr_crit("md/raid:%s: starting dirty degraded array with PPL.\n",
mdname(mddev));
@@ -8328,8 +8328,8 @@ static int raid5_resize(struct mddev *mddev, sector_t sectors)
md_set_array_sectors(mddev, newsize);
if (sectors > mddev->dev_sectors &&
- mddev->recovery_cp > mddev->dev_sectors) {
- mddev->recovery_cp = mddev->dev_sectors;
+ mddev->resync_offset > mddev->dev_sectors) {
+ mddev->resync_offset = mddev->dev_sectors;
set_bit(MD_RECOVERY_NEEDED, &mddev->recovery);
}
mddev->dev_sectors = sectors;
@@ -8423,7 +8423,7 @@ static int raid5_start_reshape(struct mddev *mddev)
return -EINVAL;
/* raid5 can't handle concurrent reshape and recovery */
- if (mddev->recovery_cp < MaxSector)
+ if (mddev->resync_offset < MaxSector)
return -EBUSY;
for (i = 0; i < conf->raid_disks; i++)
if (conf->disks[i].replacement)
@@ -8648,7 +8648,7 @@ static void *raid45_takeover_raid0(struct mddev *mddev, int level)
mddev->raid_disks += 1;
mddev->delta_disks = 1;
/* make sure it will be not marked as dirty */
- mddev->recovery_cp = MaxSector;
+ mddev->resync_offset = MaxSector;
return setup_conf(mddev);
}
diff --git a/drivers/media/Kconfig b/drivers/media/Kconfig
index 12bbb169c0b0..6abc9302cd84 100644
--- a/drivers/media/Kconfig
+++ b/drivers/media/Kconfig
@@ -230,19 +230,6 @@ source "drivers/media/platform/Kconfig"
source "drivers/media/mmc/Kconfig"
endif
-config MEDIA_VIRTIO
- tristate "Virtio-media Driver"
- depends on VIRTIO && VIDEO_DEV && 64BIT && (X86 || (ARM && CPU_LITTLE_ENDIAN))
- select VIDEOBUF2_CORE
- select VIDEOBUF2_MEMOPS
- help
- Enables the virtio-media driver.
-
- This driver is used to virtualize media devices such as cameras or
- decoders from a host into a guest using the V4L2 protocol.
-
- If unsure, say N.
-
if MEDIA_TEST_SUPPORT
source "drivers/media/test-drivers/Kconfig"
endif
diff --git a/drivers/media/Makefile b/drivers/media/Makefile
index 7a1377661919..20fac24e4f0f 100644
--- a/drivers/media/Makefile
+++ b/drivers/media/Makefile
@@ -25,8 +25,6 @@ obj-y += rc/
obj-$(CONFIG_CEC_CORE) += cec/
-obj-$(CONFIG_MEDIA_VIRTIO) += virtio/
-
#
# Finally, merge the drivers that require the core
#
diff --git a/drivers/media/virtio/Makefile b/drivers/media/virtio/Makefile
deleted file mode 100644
index 16f91304420d..000000000000
--- a/drivers/media/virtio/Makefile
+++ /dev/null
@@ -1,9 +0,0 @@
-# SPDX-License-Identifier: GPL-2.0
-#
-# Makefile for the virtio-media device driver.
-
-virtio-media-objs := scatterlist_builder.o virtio_media_ioctls.o \
- virtio_media_driver.o
-
-obj-$(CONFIG_MEDIA_VIRTIO) += virtio-media.o
-
diff --git a/drivers/media/virtio/protocol.h b/drivers/media/virtio/protocol.h
deleted file mode 100644
index a22758cda5aa..000000000000
--- a/drivers/media/virtio/protocol.h
+++ /dev/null
@@ -1,288 +0,0 @@
-/* SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0+ */
-
-/*
- * Definitions of virtio-media protocol structures.
- *
- * Copyright (c) 2024-2025 Google LLC.
- */
-
-#ifndef __VIRTIO_MEDIA_PROTOCOL_H
-#define __VIRTIO_MEDIA_PROTOCOL_H
-
-#include <linux/videodev2.h>
-
-/*
- * Virtio protocol definition.
- */
-
-/**
- * struct virtio_media_cmd_header - Header for all virtio-media commands.
- * @cmd: one of VIRTIO_MEDIA_CMD_*.
- * @__reserved: must be set to zero by the driver.
- *
- * This header starts all commands from the driver to the device on the
- * commandq.
- */
-struct virtio_media_cmd_header {
- u32 cmd;
- u32 __reserved;
-};
-
-/**
- * struct virtio_media_resp_header - Header for all virtio-media responses.
- * @status: 0 if the command was successful, or one of the standard Linux error
- * codes.
- * @__reserved: must be set to zero by the device.
- *
- * This header starts all responses from the device to the driver on the
- * commandq.
- */
-struct virtio_media_resp_header {
- u32 status;
- u32 __reserved;
-};
-
-/**
- * VIRTIO_MEDIA_CMD_OPEN - Command for creating a new session.
- *
- * This is the equivalent of calling `open` on a V4L2 device node. Upon
- * success, a session id is returned which can be used to perform other
- * commands on the session, notably ioctls.
- */
-#define VIRTIO_MEDIA_CMD_OPEN 1
-
-/**
- * struct virtio_media_cmd_open - Driver command for VIRTIO_MEDIA_CMD_OPEN.
- * @hdr: header with cmd member set to VIRTIO_MEDIA_CMD_OPEN.
- */
-struct virtio_media_cmd_open {
- struct virtio_media_cmd_header hdr;
-};
-
-/**
- * struct virtio_media_resp_open - Device response for VIRTIO_MEDIA_CMD_OPEN.
- * @hdr: header containing the status of the command.
- * @session_id: if hdr.status == 0, contains the id of the newly created session.
- * @__reserved: must be set to zero by the device.
- */
-struct virtio_media_resp_open {
- struct virtio_media_resp_header hdr;
- u32 session_id;
- u32 __reserved;
-};
-
-/**
- * VIRTIO_MEDIA_CMD_CLOSE - Command for closing an active session.
- *
- * This is the equivalent of calling `close` on a previously opened V4L2
- * session. All resources associated with this session will be freed and the
- * session ID shall not be used again after queueing this command.
- *
- * This command does not require a response from the device.
- */
-#define VIRTIO_MEDIA_CMD_CLOSE 2
-
-/**
- * struct virtio_media_cmd_close - Driver command for VIRTIO_MEDIA_CMD_CLOSE.
- * @hdr: header with cmd member set to VIRTIO_MEDIA_CMD_CLOSE.
- * @session_id: id of the session to close.
- * @__reserved: must be set to zero by the driver.
- */
-struct virtio_media_cmd_close {
- struct virtio_media_cmd_header hdr;
- u32 session_id;
- u32 __reserved;
-};
-
-/**
- * VIRTIO_MEDIA_CMD_IOCTL - Driver command for executing an ioctl.
- *
- * This command asks the device to run one of the `VIDIOC_*` ioctls on the
- * active session.
- *
- * The code of the ioctl is extracted from the VIDIOC_* definitions in
- * `videodev2.h`, and consists of the second argument of the `_IO*` macro.
- *
- * Each ioctl has a payload, which is defined by the third argument of the
- * `_IO*` macro defining it. It can be writable by the driver (`_IOW`), the
- * device (`_IOR`), or both (`_IOWR`).
- *
- * If an ioctl is writable by the driver, it must be followed by a
- * driver-writable descriptor containing the payload.
- *
- * If an ioctl is writable by the device, it must be followed by a
- * device-writable descriptor of the size of the payload that the device will
- * write into.
- *
- */
-#define VIRTIO_MEDIA_CMD_IOCTL 3
-
-/**
- * struct virtio_media_cmd_ioctl - Driver command for VIRTIO_MEDIA_CMD_IOCTL.
- * @hdr: header with cmd member set to VIRTIO_MEDIA_CMD_IOCTL.
- * @session_id: id of the session to run the ioctl on.
- * @code: code of the ioctl to run.
- */
-struct virtio_media_cmd_ioctl {
- struct virtio_media_cmd_header hdr;
- u32 session_id;
- u32 code;
-};
-
-/**
- * struct virtio_media_resp_ioctl - Device response for VIRTIO_MEDIA_CMD_IOCTL.
- * @hdr: header containing the status of the ioctl.
- */
-struct virtio_media_resp_ioctl {
- struct virtio_media_resp_header hdr;
-};
-
-/**
- * struct virtio_media_sg_entry - Description of part of a scattered guest memory.
- * @start: start guest address of the memory segment.
- * @len: length of this memory segment.
- * @__reserved: must be set to zero by the driver.
- */
-struct virtio_media_sg_entry {
- u64 start;
- u32 len;
- u32 __reserved;
-};
-
-/**
- * enum virtio_media_memory - Memory types supported by virtio-media.
- * @VIRTIO_MEDIA_MMAP: memory allocated and managed by device. Can be mapped
- * into the guest using VIRTIO_MEDIA_CMD_MMAP.
- * @VIRTIO_MEDIA_SHARED_PAGES: memory allocated by the driver. Passed to the
- * device using virtio_media_sg_entry.
- * @VIRTIO_MEDIA_OBJECT: memory backed by a virtio object.
- */
-enum virtio_media_memory {
- VIRTIO_MEDIA_MMAP = V4L2_MEMORY_MMAP,
- VIRTIO_MEDIA_SHARED_PAGES = V4L2_MEMORY_USERPTR,
- VIRTIO_MEDIA_OBJECT = V4L2_MEMORY_DMABUF,
-};
-
-#define VIRTIO_MEDIA_MMAP_FLAG_RW (1 << 0)
-
-/**
- * VIRTIO_MEDIA_CMD_MMAP - Command for mapping a MMAP buffer into the driver's
- * address space.
- *
- */
-#define VIRTIO_MEDIA_CMD_MMAP 4
-
-/**
- * struct virtio_media_cmd_mmap - Driver command for VIRTIO_MEDIA_CMD_MMAP.
- * @hdr: header with cmd member set to VIRTIO_MEDIA_CMD_MMAP.
- * @session_id: ID of the session we are mapping for.
- * @flags: combination of VIRTIO_MEDIA_MMAP_FLAG_*.
- * @offset: mem_offset field of the plane to map, as returned by VIDIOC_QUERYBUF.
- */
-struct virtio_media_cmd_mmap {
- struct virtio_media_cmd_header hdr;
- u32 session_id;
- u32 flags;
- u32 offset;
-};
-
-/**
- * struct virtio_media_resp_mmap - Device response for VIRTIO_MEDIA_CMD_MMAP.
- * @hdr: header containing the status of the command.
- * @driver_addr: offset into SHM region 0 of the start of the mapping.
- * @len: length of the mapping.
- */
-struct virtio_media_resp_mmap {
- struct virtio_media_resp_header hdr;
- u64 driver_addr;
- u64 len;
-};
-
-/**
- * VIRTIO_MEDIA_CMD_MUNMAP - Unmap a MMAP buffer previously mapped using
- * VIRTIO_MEDIA_CMD_MMAP.
- */
-#define VIRTIO_MEDIA_CMD_MUNMAP 5
-
-/**
- * struct virtio_media_cmd_munmap - Driver command for VIRTIO_MEDIA_CMD_MUNMAP.
- * @hdr: header with cmd member set to VIRTIO_MEDIA_CMD_MUNMAP.
- * @driver_addr: offset into SHM region 0 at which the buffer has been previously
- * mapped.
- */
-struct virtio_media_cmd_munmap {
- struct virtio_media_cmd_header hdr;
- u64 driver_addr;
-};
-
-/**
- * struct virtio_media_resp_munmap - Device response for VIRTIO_MEDIA_CMD_MUNMAP.
- * @hdr: header containing the status of the command.
- */
-struct virtio_media_resp_munmap {
- struct virtio_media_resp_header hdr;
-};
-
-#define VIRTIO_MEDIA_EVT_ERROR 0
-#define VIRTIO_MEDIA_EVT_DQBUF 1
-#define VIRTIO_MEDIA_EVT_EVENT 2
-
-/**
- * struct virtio_media_event_header - Header for events on the eventq.
- * @event: one of VIRTIO_MEDIA_EVT_*
- * @session_id: ID of the session the event applies to.
- */
-struct virtio_media_event_header {
- u32 event;
- u32 session_id;
-};
-
-/**
- * struct virtio_media_event_error - Unrecoverable device-side error.
- * @hdr: header for the event.
- * @errno: error code describing the kind of error that occurred.
- * @__reserved: must to set to zero by the device.
- *
- * Upon receiving this event, the session mentioned in the header is considered
- * corrupted and closed.
- *
- */
-struct virtio_media_event_error {
- struct virtio_media_event_header hdr;
- u32 errno;
- u32 __reserved;
-};
-
-#define VIRTIO_MEDIA_MAX_PLANES VIDEO_MAX_PLANES
-
-/**
- * struct virtio_media_event_dqbuf - Dequeued buffer event.
- * @hdr: header for the event.
- * @buffer: struct v4l2_buffer describing the buffer that has been dequeued.
- * @planes: plane information for the dequeued buffer.
- *
- * This event is used to signal that a buffer is not being used anymore by the
- * device and is returned to the driver.
- */
-struct virtio_media_event_dqbuf {
- struct virtio_media_event_header hdr;
- struct v4l2_buffer buffer;
- struct v4l2_plane planes[VIRTIO_MEDIA_MAX_PLANES];
-};
-
-/**
- * struct virtio_media_event_event - V4L2 event.
- * @hdr: header for the event.
- * @event: description of the event that occurred.
- *
- * This event signals that a V4L2 event has been emitted for a session.
- */
-struct virtio_media_event_event {
- struct virtio_media_event_header hdr;
- struct v4l2_event event;
-};
-
-/* Maximum size of an event. We will queue descriptors of this size on the eventq. */
-#define VIRTIO_MEDIA_EVENT_MAX_SIZE sizeof(struct virtio_media_event_dqbuf)
-
-#endif // __VIRTIO_MEDIA_PROTOCOL_H
diff --git a/drivers/media/virtio/scatterlist_builder.c b/drivers/media/virtio/scatterlist_builder.c
deleted file mode 100644
index 2837689f385e..000000000000
--- a/drivers/media/virtio/scatterlist_builder.c
+++ /dev/null
@@ -1,563 +0,0 @@
-// SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0+
-
-/*
- * Scatterlist builder helpers for virtio-media.
- *
- * Copyright (c) 2024-2025 Google LLC.
- */
-
-#include <linux/moduleparam.h>
-#include <linux/scatterlist.h>
-#include <linux/videodev2.h>
-#include <media/videobuf2-memops.h>
-
-#include "protocol.h"
-#include "scatterlist_builder.h"
-#include "session.h"
-
-/*
- * If set to ``true``, then the driver will always copy the data passed to the
- * host into the shadow buffer (instead of trying to map the source memory into
- * the SG table directly when possible).
- */
-static bool always_use_shadow_buffer;
-module_param(always_use_shadow_buffer, bool, 0660);
-
-/* Convert a V4L2 IOCTL into the IOCTL code we can give to the host */
-#define VIRTIO_MEDIA_IOCTL_CODE(IOCTL) ((IOCTL >> _IOC_NRSHIFT) & _IOC_NRMASK)
-
-/**
- * scatterlist_builder_add_descriptor() - Add a descriptor to the chain.
- * @builder: builder to use.
- * @desc_index: index of the descriptor to add.
- *
- * Returns ``-ENOSPC`` if ``sgs`` is already full.
- */
-int scatterlist_builder_add_descriptor(struct scatterlist_builder *builder,
- size_t desc_index)
-{
- if (builder->cur_sg >= builder->num_sgs)
- return -ENOSPC;
- builder->sgs[builder->cur_sg++] = &builder->descs[desc_index];
-
- return 0;
-}
-
-/**
- * scatterlist_builder_add_data() - Append arbitrary data to the descriptor chain.
- * @builder: builder to use.
- * @data: pointer to the data to add to the descriptor chain.
- * @len: length of the data to add.
- *
- * @data will either be directly referenced, or copied into the shadow buffer
- * to be referenced from there.
- */
-int scatterlist_builder_add_data(struct scatterlist_builder *builder,
- void *data, size_t len)
-{
- const size_t cur_desc = builder->cur_desc;
-
- if (len == 0)
- return 0;
-
- if (builder->cur_desc >= builder->num_descs)
- return -ENOSPC;
-
- if (!always_use_shadow_buffer && virt_addr_valid(data + len)) {
- /*
- * If "data" is in the 1:1 physical memory mapping then we can
- * use a single SG entry and avoid copying.
- */
- struct page *page = virt_to_page(data);
- size_t offset = (((size_t)data) & ~PAGE_MASK);
- struct scatterlist *next_desc =
- &builder->descs[builder->cur_desc];
-
- memset(next_desc, 0, sizeof(*next_desc));
- sg_set_page(next_desc, page, len, offset);
- builder->cur_desc++;
- } else if (!always_use_shadow_buffer && is_vmalloc_addr(data)) {
- int prev_pfn = -2;
-
- /*
- * If "data" has been vmalloc'ed, we need at most one entry per
- * memory page but can avoid copying.
- */
- while (len > 0) {
- struct page *page = vmalloc_to_page(data);
- int cur_pfn = page_to_pfn(page);
- /* All pages but the first will start at offset 0. */
- unsigned long offset =
- (((unsigned long)data) & ~PAGE_MASK);
- size_t len_in_page = min(PAGE_SIZE - offset, len);
- struct scatterlist *next_desc =
- &builder->descs[builder->cur_desc];
-
- if (builder->cur_desc >= builder->num_descs)
- return -ENOSPC;
-
- /* Optimize contiguous pages */
- if (cur_pfn == prev_pfn + 1) {
- (next_desc - 1)->length += len_in_page;
- } else {
- memset(next_desc, 0, sizeof(*next_desc));
- sg_set_page(next_desc, page, len_in_page,
- offset);
- builder->cur_desc++;
- }
- data += len_in_page;
- len -= len_in_page;
- prev_pfn = cur_pfn;
- }
- } else {
- /*
- * As a last resort, copy into the shadow buffer and reference
- * it with a single SG entry. Calling
- * `scatterlist_builder_retrieve_data` will be necessary to copy
- * the data written by the device back into @data.
- */
- void *shadow_buffer =
- builder->shadow_buffer + builder->shadow_buffer_pos;
- struct page *page = virt_to_page(shadow_buffer);
- unsigned long offset =
- (((unsigned long)shadow_buffer) & ~PAGE_MASK);
- struct scatterlist *next_desc =
- &builder->descs[builder->cur_desc];
-
- if (len >
- builder->shadow_buffer_size - builder->shadow_buffer_pos)
- return -ENOSPC;
-
- memcpy(shadow_buffer, data, len);
- memset(next_desc, 0, sizeof(*next_desc));
- sg_set_page(next_desc, page, len, offset);
- builder->cur_desc++;
- builder->shadow_buffer_pos += len;
- }
-
- sg_mark_end(&builder->descs[builder->cur_desc - 1]);
- return scatterlist_builder_add_descriptor(builder, cur_desc);
-}
-
-/**
- * scatterlist_builder_retrieve_data() - Retrieve a response written by the
- * device on the shadow buffer.
- * @builder: builder to use.
- * @sg_index: index of the descriptor to read from.
- * @data: destination for the shadowed data.
- *
- * If the shadow buffer is pointed to by the descriptor at index @sg_index of
- * the chain, then ``sg->length`` bytes are copied back from it into @data.
- * Otherwise nothing is done since the device has written into @data directly.
- *
- * @data must have originally been added by ``scatterlist_builder_add_data`` as
- * the same size as passed to ``scatterlist_builder_add_data`` will be copied
- * back.
- */
-int scatterlist_builder_retrieve_data(struct scatterlist_builder *builder,
- size_t sg_index, void *data)
-{
- void *shadow_buf = builder->shadow_buffer;
- struct scatterlist *sg;
- void *kaddr;
-
- /* We can only retrieve from the range of sgs currently set. */
- if (sg_index >= builder->cur_sg)
- return -ERANGE;
-
- sg = builder->sgs[sg_index];
- kaddr = pfn_to_kaddr(page_to_pfn(sg_page(sg))) + sg->offset;
-
- if (kaddr >= shadow_buf &&
- kaddr < shadow_buf + VIRTIO_SHADOW_BUF_SIZE) {
- if (kaddr + sg->length >= shadow_buf + VIRTIO_SHADOW_BUF_SIZE)
- return -EINVAL;
-
- memcpy(data, kaddr, sg->length);
- }
-
- return 0;
-}
-
-/**
- * scatterlist_builder_add_ioctl_cmd() - Add an ioctl command to the descriptor
- * chain.
- * @builder: builder to use.
- * @session: session on behalf of which the ioctl command is added.
- * @ioctl_code: code of the ioctl to add (i.e. ``VIDIOC_*``).
- */
-int scatterlist_builder_add_ioctl_cmd(struct scatterlist_builder *builder,
- struct virtio_media_session *session,
- u32 ioctl_code)
-{
- struct virtio_media_cmd_ioctl *cmd_ioctl = &session->cmd.ioctl;
-
- cmd_ioctl->hdr.cmd = VIRTIO_MEDIA_CMD_IOCTL;
- cmd_ioctl->session_id = session->id;
- cmd_ioctl->code = VIRTIO_MEDIA_IOCTL_CODE(ioctl_code);
-
- return scatterlist_builder_add_data(builder, cmd_ioctl,
- sizeof(*cmd_ioctl));
-}
-
-/**
- * scatterlist_builder_add_ioctl_resp() - Add storage to receive an ioctl
- * response to the descriptor chain.
- * @builder: builder to use.
- * @session: session on behalf of which the ioctl response is added.
- */
-int scatterlist_builder_add_ioctl_resp(struct scatterlist_builder *builder,
- struct virtio_media_session *session)
-{
- struct virtio_media_resp_ioctl *resp_ioctl = &session->resp.ioctl;
-
- return scatterlist_builder_add_data(builder, resp_ioctl,
- sizeof(*resp_ioctl));
-}
-
-/**
- * __scatterlist_builder_add_userptr() - Add user pages to @builder.
- * @builder: builder to use.
- * @userptr: pointer to userspace memory that we want to add.
- * @length: length of the data to add.
- * @sg_list: output parameter. Upon success, points to the area of the shadow
- * buffer containing the array of SG entries to be added to the descriptor
- * chain.
- * @nents: output parameter. Upon success, contains the number of entries
- * pointed to by @sg_list.
- *
- * Data referenced by userspace pointers can be potentially large and very
- * scattered, which could overwhelm the descriptor chain if added as-is. For
- * these, we instead build an array of ``struct virtio_media_sg_entry`` in the
- * shadow buffer and reference it using a single descriptor.
- *
- * This function is a helper to perform that. Callers should then add the
- * descriptor to the chain properly.
- *
- * Returns -EFAULT if @userptr is not a valid user address, which is a case the
- * driver should consider as "normal" operation. All other failures signal a
- * problem with the driver.
- */
-static int
-__scatterlist_builder_add_userptr(struct scatterlist_builder *builder,
- unsigned long userptr, unsigned long length,
- struct virtio_media_sg_entry **sg_list,
- int *nents)
-{
- struct sg_table sg_table = {};
- struct frame_vector *framevec;
- struct scatterlist *sg_iter;
- struct page **pages;
- const unsigned int offset = userptr & ~PAGE_MASK;
- unsigned int pages_count;
- size_t entries_size;
- int i;
- int ret;
-
- framevec = vb2_create_framevec(userptr, length, true);
- if (IS_ERR(framevec)) {
- if (PTR_ERR(framevec) != -EFAULT) {
- pr_warn("error %ld creating frame vector for userptr 0x%lx, length 0x%lx\n",
- PTR_ERR(framevec), userptr, length);
- } else {
- /* -EINVAL is expected in case of invalid userptr. */
- framevec = ERR_PTR(-EINVAL);
- }
- return PTR_ERR(framevec);
- }
-
- pages = frame_vector_pages(framevec);
- if (IS_ERR(pages)) {
- pr_warn("error getting vector pages\n");
- ret = PTR_ERR(pages);
- goto done;
- }
- pages_count = frame_vector_count(framevec);
- ret = sg_alloc_table_from_pages(&sg_table, pages, pages_count, offset,
- length, 0);
- if (ret) {
- pr_warn("error creating sg table\n");
- goto done;
- }
-
- /* Allocate our actual SG in the shadow buffer. */
- *nents = sg_nents(sg_table.sgl);
- entries_size = sizeof(**sg_list) * *nents;
- if (builder->shadow_buffer_pos + entries_size >
- builder->shadow_buffer_size) {
- ret = -ENOMEM;
- goto free_sg;
- }
-
- *sg_list = builder->shadow_buffer + builder->shadow_buffer_pos;
- builder->shadow_buffer_pos += entries_size;
-
- for_each_sgtable_sg(&sg_table, sg_iter, i) {
- struct virtio_media_sg_entry *sg_entry = &(*sg_list)[i];
-
- sg_entry->start = sg_phys(sg_iter);
- sg_entry->len = sg_iter->length;
- }
-
-free_sg:
- sg_free_table(&sg_table);
-
-done:
- vb2_destroy_framevec(framevec);
- return ret;
-}
-
-/**
- * scatterlist_builder_add_userptr() - Add a user-memory buffer using an array
- * of ``struct virtio_media_sg_entry``.
- * @builder: builder to use.
- * @userptr: pointer to userspace memory that we want to add.
- * @length: length of the data to add.
- *
- * Upon success, an array of ``struct virtio_media_sg_entry`` referencing
- * @userptr has been built into the shadow buffer, and that array added to the
- * descriptor chain.
- */
-static int scatterlist_builder_add_userptr(struct scatterlist_builder *builder,
- unsigned long userptr,
- unsigned long length)
-{
- int ret;
- int nents;
- struct virtio_media_sg_entry *sg_list;
-
- ret = __scatterlist_builder_add_userptr(builder, userptr, length,
- &sg_list, &nents);
- if (ret)
- return ret;
-
- ret = scatterlist_builder_add_data(builder, sg_list,
- sizeof(*sg_list) * nents);
- if (ret)
- return ret;
-
- return 0;
-}
-
-/**
- * scatterlist_builder_add_buffer() - Add a ``v4l2_buffer`` and its planes to
- * the descriptor chain.
- * @builder: builder to use.
- * @b: ``v4l2_buffer`` to add.
- */
-int scatterlist_builder_add_buffer(struct scatterlist_builder *builder,
- struct v4l2_buffer *b)
-{
- int i;
- int ret;
-
- /* Fixup: plane length must be zero if userptr is NULL */
- if (!V4L2_TYPE_IS_MULTIPLANAR(b->type) &&
- b->memory == V4L2_MEMORY_USERPTR && b->m.userptr == 0)
- b->length = 0;
-
- /* v4l2_buffer */
- ret = scatterlist_builder_add_data(builder, b, sizeof(*b));
- if (ret)
- return ret;
-
- if (V4L2_TYPE_IS_MULTIPLANAR(b->type) && b->length > 0) {
- /* Fixup: plane length must be zero if userptr is NULL */
- if (b->memory == V4L2_MEMORY_USERPTR) {
- for (i = 0; i < b->length; i++) {
- struct v4l2_plane *plane = &b->m.planes[i];
-
- if (plane->m.userptr == 0)
- plane->length = 0;
- }
- }
-
- /* Array of v4l2_planes */
- ret = scatterlist_builder_add_data(builder, b->m.planes,
- sizeof(struct v4l2_plane) *
- b->length);
- if (ret)
- return ret;
- }
-
- return 0;
-}
-
-/**
- * scatterlist_builder_add_buffer_userptr() - Add the payload of a ``USERTPR``
- * v4l2_buffer to the descriptor chain.
- * @builder: builder to use.
- * @b: ``v4l2_buffer`` which ``USERPTR`` payload we want to add.
- *
- * Add an array of ``virtio_media_sg_entry`` pointing to a ``USERPTR`` buffer's
- * contents. Does nothing if the buffer is not of type ``USERPTR``. This is
- * split out of :ref:`scatterlist_builder_add_buffer` because we only want to
- * add these to the device-readable part of the descriptor chain.
- */
-int scatterlist_builder_add_buffer_userptr(struct scatterlist_builder *builder,
- struct v4l2_buffer *b)
-{
- int i;
- int ret;
-
- if (b->memory != V4L2_MEMORY_USERPTR)
- return 0;
-
- if (V4L2_TYPE_IS_MULTIPLANAR(b->type)) {
- for (i = 0; i < b->length; i++) {
- struct v4l2_plane *plane = &b->m.planes[i];
-
- if (b->memory == V4L2_MEMORY_USERPTR &&
- plane->length > 0) {
- ret = scatterlist_builder_add_userptr(
- builder, plane->m.userptr,
- plane->length);
- if (ret)
- return ret;
- }
- }
- } else if (b->length > 0) {
- ret = scatterlist_builder_add_userptr(builder, b->m.userptr,
- b->length);
- if (ret)
- return ret;
- }
-
- return 0;
-}
-
-/**
- * scatterlist_builder_retrieve_buffer() - Retrieve a v4l2_buffer written by
- * the device on the shadow buffer, if needed.
- * @builder: builder to use.
- * @sg_index: index of the first SG entry of the buffer in the builder's
- * descriptor chain.
- * @b: v4l2_buffer to copy shadow buffer data into.
- * @orig_planes: the original ``planes`` pointer, to be restored if the buffer
- * is multi-planar.
- *
- * If the v4l2_buffer pointed by @buffer_sgs was copied into the shadow buffer,
- * then its updated content is copied back into @b. Otherwise nothing is done
- * as the device has written into @b directly.
- *
- * @orig_planes is used to restore the original ``planes`` pointer in case it
- * gets modified by the host. The specification stipulates that the host should
- * not modify it, but we enforce this for additional safety.
- */
-int scatterlist_builder_retrieve_buffer(struct scatterlist_builder *builder,
- size_t sg_index, struct v4l2_buffer *b,
- struct v4l2_plane *orig_planes)
-{
- int ret;
-
- ret = scatterlist_builder_retrieve_data(builder, sg_index++, b);
- if (ret)
- return ret;
-
- if (V4L2_TYPE_IS_MULTIPLANAR(b->type)) {
- b->m.planes = orig_planes;
-
- if (orig_planes != NULL) {
- ret = scatterlist_builder_retrieve_data(
- builder, sg_index++, b->m.planes);
- if (ret)
- return ret;
- }
- }
-
- return 0;
-}
-
-/**
- * scatterlist_builder_add_ext_ctrls() - Add a v4l2_ext_controls and its
- * controls to @builder.
- * @builder: builder to use.
- * @ctrls: ``struct v4l2_ext_controls`` to add.
- *
- * Add @ctrls and its array of `struct v4l2_ext_control` to the descriptor chain.
- */
-int scatterlist_builder_add_ext_ctrls(struct scatterlist_builder *builder,
- struct v4l2_ext_controls *ctrls)
-{
- int ret;
-
- /* v4l2_ext_controls */
- ret = scatterlist_builder_add_data(builder, ctrls, sizeof(*ctrls));
- if (ret)
- return ret;
-
- if (ctrls->count > 0) {
- /* array of v4l2_controls */
- ret = scatterlist_builder_add_data(builder, ctrls->controls,
- sizeof(ctrls->controls[0]) *
- ctrls->count);
- if (ret)
- return ret;
- }
-
- return 0;
-}
-
-/**
- * scatterlist_builder_add_ext_ctrls_userptrs() - Add the userspace payloads of
- * a ``struct v4l2_ext_controls`` to the descriptor chain.
- * @builder: builder to use.
- * @ctrls: ``struct v4l2_ext_controls`` from which we want to add the userspace payload of.
- *
- * Add the userspace payloads of @ctrls to the descriptor chain. This is split
- * out of :ref:`scatterlist_builder_add_ext_ctrls` because we only want to add
- * these to the device-readable part of the descriptor chain.
- */
-int scatterlist_builder_add_ext_ctrls_userptrs(
- struct scatterlist_builder *builder, struct v4l2_ext_controls *ctrls)
-{
- int i;
- int ret;
-
- /* Pointers to user memory in individual controls */
- for (i = 0; i < ctrls->count; i++) {
- struct v4l2_ext_control *ctrl = &ctrls->controls[i];
-
- if (ctrl->size > 0) {
- ret = scatterlist_builder_add_userptr(
- builder, (unsigned long)ctrl->ptr, ctrl->size);
- if (ret)
- return ret;
- }
- }
-
- return 0;
-}
-
-/**
- * scatterlist_builder_retrieve_ext_ctrls() - Retrieve controls written by the
- * device on the shadow buffer, if needed.
- * @builder: builder to use.
- * @sg_index: index of the first SG entry of the controls in the builder's
- * descriptor chain.
- * @ctrls: ``struct v4l2_ext_controls`` to copy shadow buffer data into.
- *
- * If the shadow buffer is pointed to by @sg, copy its content back into @ctrls.
- */
-int scatterlist_builder_retrieve_ext_ctrls(struct scatterlist_builder *builder,
- size_t sg_index,
- struct v4l2_ext_controls *ctrls)
-{
- struct v4l2_ext_control *controls_backup = ctrls->controls;
- int ret;
-
- ret = scatterlist_builder_retrieve_data(builder, sg_index++, ctrls);
- if (ret)
- return ret;
-
- ctrls->controls = controls_backup;
-
- if (ctrls->count > 0 && ctrls->controls) {
- ret = scatterlist_builder_retrieve_data(builder, sg_index++,
- ctrls->controls);
- if (ret)
- return ret;
- }
-
- return 0;
-}
diff --git a/drivers/media/virtio/scatterlist_builder.h b/drivers/media/virtio/scatterlist_builder.h
deleted file mode 100644
index c8323c31ac21..000000000000
--- a/drivers/media/virtio/scatterlist_builder.h
+++ /dev/null
@@ -1,111 +0,0 @@
-/* SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0+ */
-
-/*
- * Scatterlist builder helpers for virtio-media.
- *
- * Copyright (c) 2024-2025 Google LLC.
- */
-
-#ifndef __VIRTIO_MEDIA_SCATTERLIST_BUILDER_H
-#define __VIRTIO_MEDIA_SCATTERLIST_BUILDER_H
-
-#include <linux/scatterlist.h>
-
-#include "session.h"
-
-/**
- * struct scatterlist_builder - helper to build a scatterlist from data.
- * @descs: pool of descriptors to use.
- * @num_descs: number of entries in descs.
- * @cur_desc: next descriptor to be used in @descs.
- * @shadow_buffer: pointer to a shadow buffer where elements that cannot be
- * mapped directly into the scatterlist get copied.
- * @shadow_buffer_size: size of @shadow_buffer.
- * @shadow_buffer_pos: current position in @shadow_buffer.
- * @sgs: descriptor chain to eventually pass to virtio functions.
- * @num_sgs: total number of entries in @sgs.
- * @cur_sg: next entry in @sgs to be used.
- *
- * Virtio passes data from the driver to the device (through e.g.
- * ``virtqueue_add_sgs``) via a scatterlist that the device interprets as a
- * linear view over scattered driver memory.
- *
- * In virtio-media, the payload of ioctls from user-space can for the most part
- * be passed as-is, or after slight modification, which makes it tempting to
- * just forward the ioctl payload received from user-space as-is instead of
- * doing another copy into a dedicated buffer. This structure helps with this.
- *
- * virtio-media descriptor chains are typically made of the following parts:
- *
- * Device-readable:
- * - A command structure, i.e. ``virtio_media_cmd_*``,
- * - An ioctl payload (one of the regular ioctl parameters),
- * - (optionally) arrays of ``virtio_media_sg_entry`` describing the content of
- * buffers in guest memory.
- *
- * Device-writable:
- * - A response structure, i.e. ``virtio_media_resp_*``,
- * - An ioctl payload, that the device will write to.
- *
- * This structure helps laying out the descriptor chain into its @sgs member in
- * an optimal way, by building a scatterlist adapted to the originating memory
- * of the data we want to pass to the device while avoiding copies when
- * possible.
- *
- * It is made of a pool of ``struct scatterlist`` (@descs) that is used to
- * build the final descriptor chain @sgs, and a @shadow_buffer where data that
- * cannot (or should not) be mapped directly by the host can be temporarily
- * copied.
- */
-struct scatterlist_builder {
- struct scatterlist *descs;
- size_t num_descs;
- size_t cur_desc;
-
- void *shadow_buffer;
- size_t shadow_buffer_size;
- size_t shadow_buffer_pos;
-
- struct scatterlist **sgs;
- size_t num_sgs;
- size_t cur_sg;
-};
-
-int scatterlist_builder_add_descriptor(struct scatterlist_builder *builder,
- size_t desc_index);
-
-int scatterlist_builder_add_data(struct scatterlist_builder *builder,
- void *data, size_t len);
-
-int scatterlist_builder_retrieve_data(struct scatterlist_builder *builder,
- size_t sg_index, void *data);
-
-int scatterlist_builder_add_ioctl_cmd(struct scatterlist_builder *builder,
- struct virtio_media_session *session,
- u32 ioctl_code);
-
-int scatterlist_builder_add_ioctl_resp(struct scatterlist_builder *builder,
- struct virtio_media_session *session);
-
-int scatterlist_builder_add_buffer(struct scatterlist_builder *builder,
- struct v4l2_buffer *buffer);
-
-int scatterlist_builder_add_buffer_userptr(struct scatterlist_builder *builder,
- struct v4l2_buffer *b);
-
-int scatterlist_builder_retrieve_buffer(struct scatterlist_builder *builder,
- size_t sg_index,
- struct v4l2_buffer *buffer,
- struct v4l2_plane *orig_planes);
-
-int scatterlist_builder_add_ext_ctrls(struct scatterlist_builder *builder,
- struct v4l2_ext_controls *ctrls);
-
-int scatterlist_builder_add_ext_ctrls_userptrs(
- struct scatterlist_builder *builder, struct v4l2_ext_controls *ctrls);
-
-int scatterlist_builder_retrieve_ext_ctrls(struct scatterlist_builder *builder,
- size_t sg_index,
- struct v4l2_ext_controls *ctrls);
-
-#endif // __VIRTIO_MEDIA_SCATTERLIST_BUILDER_H
diff --git a/drivers/media/virtio/session.h b/drivers/media/virtio/session.h
deleted file mode 100644
index b643d0d95047..000000000000
--- a/drivers/media/virtio/session.h
+++ /dev/null
@@ -1,109 +0,0 @@
-/* SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0+ */
-
-/*
- * Definitions of virtio-media session related structures.
- *
- * Copyright (c) 2024-2025 Google LLC.
- */
-
-#ifndef __VIRTIO_MEDIA_SESSION_H
-#define __VIRTIO_MEDIA_SESSION_H
-
-#include <linux/scatterlist.h>
-#include <media/v4l2-fh.h>
-
-#include "protocol.h"
-
-#define VIRTIO_MEDIA_LAST_QUEUE (V4L2_BUF_TYPE_META_OUTPUT)
-
-/*
- * Size of the per-session virtio shadow and event buffers. 16K should be
- * enough to contain everything we need.
- */
-#define VIRTIO_SHADOW_BUF_SIZE 0x4000
-
-/**
- * struct virtio_media_buffer - Current state of a buffer.
- * @buffer: ``struct v4l2_buffer`` with current information about the buffer.
- * @planes: backing planes array for @buffer.
- * @list: link into the list of buffers pending dequeue.
- */
-struct virtio_media_buffer {
- struct v4l2_buffer buffer;
- struct v4l2_plane planes[VIDEO_MAX_PLANES];
- struct list_head list;
-};
-
-/**
- * struct virtio_media_queue_state - Represents the state of a V4L2 queue.
- * @streaming: Whether the queue is currently streaming.
- * @allocated_bufs: How many buffers are currently allocated.
- * @is_capture_last: set to true when the last buffer has been received on a
- * capture queue, so we can return -EPIPE on subsequent DQBUF requests.
- * @buffers: Buffer state array of size @allocated_bufs.
- * @queued_bufs: How many buffers are currently queued on the device.
- * @pending_dqbufs: Buffers that are available for being dequeued.
- */
-struct virtio_media_queue_state {
- bool streaming;
- size_t allocated_bufs;
- bool is_capture_last;
-
- struct virtio_media_buffer *buffers;
- size_t queued_bufs;
- struct list_head pending_dqbufs;
-};
-
-/**
- * struct virtio_media_session - A session on a virtio_media device.
- * @fh: file handler for the session.
- * @id: session ID used to communicate with the device.
- * @nonblocking_dequeue: whether dequeue should block or not (nonblocking if
- * file opened with O_NONBLOCK).
- * @uses_mplane: whether the queues for this session use the MPLANE API or not.
- * @cmd: union of session-related commands. A session can have one command currently running.
- * @resp: union of session-related responses. A session can wait on one command only.
- * @shadow_buf: shadow buffer where data to be added to the descriptor chain can
- * be staged before being sent to the device.
- * @command_sgs: SG table gathering descriptors for a given command and its response.
- * @queues: state of all the queues for this session.
- * @queues_lock: protects all members fo the queues for this session.
- * virtio_media_queue_state`.
- * @dqbuf_wait: waitqueue for dequeued buffers, if ``VIDIOC_DQBUF`` needs to
- * block or when polling.
- * @list: link into the list of sessions for the device.
- */
-struct virtio_media_session {
- struct v4l2_fh fh;
- u32 id;
- bool nonblocking_dequeue;
- bool uses_mplane;
-
- union {
- struct virtio_media_cmd_close close;
- struct virtio_media_cmd_ioctl ioctl;
- struct virtio_media_cmd_mmap mmap;
- } cmd;
-
- union {
- struct virtio_media_resp_ioctl ioctl;
- struct virtio_media_resp_mmap mmap;
- } resp;
-
- void *shadow_buf;
-
- struct sg_table command_sgs;
-
- struct virtio_media_queue_state queues[VIRTIO_MEDIA_LAST_QUEUE + 1];
- struct mutex queues_lock;
- wait_queue_head_t dqbuf_wait;
-
- struct list_head list;
-};
-
-static inline struct virtio_media_session *fh_to_session(struct v4l2_fh *fh)
-{
- return container_of(fh, struct virtio_media_session, fh);
-}
-
-#endif // __VIRTIO_MEDIA_SESSION_H
diff --git a/drivers/media/virtio/virtio_media.h b/drivers/media/virtio/virtio_media.h
deleted file mode 100644
index 0aa503defdd6..000000000000
--- a/drivers/media/virtio/virtio_media.h
+++ /dev/null
@@ -1,93 +0,0 @@
-/* SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0+ */
-
-/*
- * Virtio-media structures & functions declarations.
- *
- * Copyright (c) 2024-2025 Google LLC.
- */
-
-#ifndef __VIRTIO_MEDIA_H
-#define __VIRTIO_MEDIA_H
-
-#include <linux/virtio_config.h>
-#include <media/v4l2-device.h>
-
-#include "protocol.h"
-
-#define DESC_CHAIN_MAX_LEN SG_MAX_SINGLE_ALLOC
-
-#define VIRTIO_MEDIA_DEFAULT_DRIVER_NAME "virtio-media"
-
-extern char *virtio_media_driver_name;
-extern bool virtio_media_allow_userptr;
-
-/**
- * struct virtio_media - Virtio-media device.
- * @v4l2_dev: v4l2_device for the media device.
- * @video_dev: video_device for the media device.
- * @virtio_dev: virtio device for the media device.
- * @commandq: virtio command queue.
- * @eventq: virtio event queue.
- * @eventq_work: work to run when events are received on @eventq.
- * @mmap_region: region into which MMAP buffers are mapped by the host.
- * @event_buffer: buffer for event descriptors.
- * @sessions: list of active sessions on the device.
- * @sessions_lock: protects @sessions and ``virtio_media_session::list``.
- * @events_lock: prevents concurrent processing of events.
- * @cmd: union of device-related commands.
- * @resp: union of device-related responses.
- * @vlock: serializes access to the command queue.
- * @wq: waitqueue for host responses on the command queue.
- */
-struct virtio_media {
- struct v4l2_device v4l2_dev;
- struct video_device video_dev;
-
- struct virtio_device *virtio_dev;
- struct virtqueue *commandq;
- struct virtqueue *eventq;
- struct work_struct eventq_work;
-
- struct virtio_shm_region mmap_region;
-
- void *event_buffer;
-
- struct list_head sessions;
- struct mutex sessions_lock;
-
- struct mutex events_lock;
-
- union {
- struct virtio_media_cmd_open open;
- struct virtio_media_cmd_munmap munmap;
- } cmd;
-
- union {
- struct virtio_media_resp_open open;
- struct virtio_media_resp_munmap munmap;
- } resp;
-
- struct mutex vlock;
- wait_queue_head_t wq;
-};
-
-static inline struct virtio_media *
-to_virtio_media(struct video_device *video_dev)
-{
- return container_of(video_dev, struct virtio_media, video_dev);
-}
-
-/* virtio_media_driver.c */
-
-int virtio_media_send_command(struct virtio_media *vv, struct scatterlist **sgs,
- const size_t out_sgs, const size_t in_sgs,
- size_t minimum_resp_len, size_t *resp_len);
-void virtio_media_process_events(struct virtio_media *vv);
-
-/* virtio_media_ioctls.c */
-
-long virtio_media_device_ioctl(struct file *file, unsigned int cmd,
- unsigned long arg);
-extern const struct v4l2_ioctl_ops virtio_media_ioctl_ops;
-
-#endif // __VIRTIO_MEDIA_H
diff --git a/drivers/media/virtio/virtio_media_driver.c b/drivers/media/virtio/virtio_media_driver.c
deleted file mode 100644
index e8d6dc453f22..000000000000
--- a/drivers/media/virtio/virtio_media_driver.c
+++ /dev/null
@@ -1,959 +0,0 @@
-// SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0+
-
-/*
- * Virtio-media driver.
- *
- * Copyright (c) 2024-2025 Google LLC.
- */
-
-#include <linux/delay.h>
-#include <linux/device.h>
-#include <linux/dev_printk.h>
-#include <linux/mm.h>
-#include <linux/mutex.h>
-#include <linux/scatterlist.h>
-#include <linux/types.h>
-#include <linux/videodev2.h>
-#include <linux/vmalloc.h>
-#include <linux/wait.h>
-#include <linux/workqueue.h>
-#include <linux/module.h>
-#include <linux/moduleparam.h>
-#include <linux/virtio.h>
-#include <linux/virtio_config.h>
-#include <linux/virtio_ids.h>
-
-#include <media/frame_vector.h>
-#include <media/v4l2-dev.h>
-#include <media/v4l2-event.h>
-#include <media/videobuf2-memops.h>
-#include <media/v4l2-device.h>
-#include <media/v4l2-ioctl.h>
-
-#include "protocol.h"
-#include "session.h"
-#include "virtio_media.h"
-
-#define VIRTIO_MEDIA_NUM_EVENT_BUFS 16
-
-/* ID of the SHM region into which MMAP buffer will be mapped. */
-#define VIRTIO_MEDIA_SHM_MMAP 0
-
-/*
- * Name of the driver to expose to user-space.
- *
- * This is configurable because v4l2-compliance has workarounds specific to
- * some drivers. When proxying these directly from the host, this allows it to
- * apply them as needed.
- */
-char *virtio_media_driver_name;
-module_param_named(driver_name, virtio_media_driver_name, charp, 0660);
-
-/*
- * Whether USERPTR buffers are allowed.
- *
- * This is disabled by default as USERPTR buffers are dangerous, but the option
- * is left to enable them if desired.
- */
-bool virtio_media_allow_userptr;
-module_param_named(allow_userptr, virtio_media_allow_userptr, bool, 0660);
-
-/**
- * virtio_media_session_alloc - Allocate a new session.
- * @vv: virtio-media device the session belongs to.
- * @id: ID of the session.
- * @nonblocking_dequeue: whether dequeuing of buffers should be blocking or
- * not.
- *
- * The ``id`` and ``list`` fields must still be set by the caller.
- */
-static struct virtio_media_session *
-virtio_media_session_alloc(struct virtio_media *vv, u32 id,
- bool nonblocking_dequeue)
-{
- struct virtio_media_session *session;
- int i;
- int ret;
-
- session = kzalloc(sizeof(*session), GFP_KERNEL);
- if (!session)
- goto err_session;
-
- session->shadow_buf = kzalloc(VIRTIO_SHADOW_BUF_SIZE, GFP_KERNEL);
- if (!session->shadow_buf)
- goto err_shadow_buf;
-
- ret = sg_alloc_table(&session->command_sgs, DESC_CHAIN_MAX_LEN,
- GFP_KERNEL);
- if (ret)
- goto err_payload_sgs;
-
- session->id = id;
- session->nonblocking_dequeue = nonblocking_dequeue;
-
- INIT_LIST_HEAD(&session->list);
- v4l2_fh_init(&session->fh, &vv->video_dev);
- v4l2_fh_add(&session->fh);
-
- for (i = 0; i <= VIRTIO_MEDIA_LAST_QUEUE; i++)
- INIT_LIST_HEAD(&session->queues[i].pending_dqbufs);
- mutex_init(&session->queues_lock);
-
- init_waitqueue_head(&session->dqbuf_wait);
-
- mutex_lock(&vv->sessions_lock);
- list_add_tail(&session->list, &vv->sessions);
- mutex_unlock(&vv->sessions_lock);
-
- return session;
-
-err_payload_sgs:
- kfree(session->shadow_buf);
-err_shadow_buf:
- kfree(session);
-err_session:
- return ERR_PTR(-ENOMEM);
-}
-
-/**
- * virtio_media_session_free - Free all resources of a session.
- * @vv: virtio-media device the session belongs to.
- * @session: session to destroy.
- *
- * All the resources of @sesssion, as well as the backing memory of @session
- * itself, are freed.
- */
-static void virtio_media_session_free(struct virtio_media *vv,
- struct virtio_media_session *session)
-{
- int i;
-
- mutex_lock(&vv->sessions_lock);
- list_del(&session->list);
- mutex_unlock(&vv->sessions_lock);
-
- v4l2_fh_del(&session->fh);
- v4l2_fh_exit(&session->fh);
-
- sg_free_table(&session->command_sgs);
-
- for (i = 0; i <= VIRTIO_MEDIA_LAST_QUEUE; i++)
- vfree(session->queues[i].buffers);
-
- kfree(session->shadow_buf);
- kfree(session);
-}
-
-/**
- * virtio_media_session_close - Close and free a session.
- * @vv: virtio-media device the session belongs to.
- * @session: session to close and destroy.
- *
- * This send the ``VIRTIO_MEDIA_CMD_CLOSE`` command to the device, and frees
- * all resources used by @session.
- */
-static int virtio_media_session_close(struct virtio_media *vv,
- struct virtio_media_session *session)
-{
- struct virtio_media_cmd_close *cmd_close = &session->cmd.close;
- struct scatterlist cmd_sg = {};
- struct scatterlist *sgs[1] = { &cmd_sg };
- int ret;
-
- mutex_lock(&vv->vlock);
-
- cmd_close->hdr.cmd = VIRTIO_MEDIA_CMD_CLOSE;
- cmd_close->session_id = session->id;
-
- sg_set_buf(&cmd_sg, cmd_close, sizeof(*cmd_close));
- sg_mark_end(&cmd_sg);
-
- ret = virtio_media_send_command(vv, sgs, 1, 0, 0, NULL);
- mutex_unlock(&vv->vlock);
- if (ret < 0)
- return ret;
-
- virtio_media_session_free(vv, session);
-
- return 0;
-}
-
-/**
- * virtio_media_find_session - Lookup for the session with a given ID.
- * @vv: virtio-media device to lookup the session from.
- * @id: ID of the session to lookup.
- */
-static struct virtio_media_session *
-virtio_media_find_session(struct virtio_media *vv, u32 id)
-{
- struct list_head *p;
- struct virtio_media_session *session = NULL;
-
- mutex_lock(&vv->sessions_lock);
- list_for_each(p, &vv->sessions) {
- struct virtio_media_session *s =
- list_entry(p, struct virtio_media_session, list);
- if (s->id == id) {
- session = s;
- break;
- }
- }
- mutex_unlock(&vv->sessions_lock);
-
- return session;
-}
-
-/**
- * struct virtio_media_cmd_callback_param - Callback parameters to the virtio command queue.
- * @vv: virtio-media device in use.
- * @done: flag to be switched once the command is completed.
- * @resp_len: length of the received response from the command. Only valid
- * after @done_flag has switched to ``true``.
- */
-struct virtio_media_cmd_callback_param {
- struct virtio_media *vv;
- bool done;
- size_t resp_len;
-};
-
-/**
- * commandq_callback: Callback for the command queue.
- * @queue: command virtqueue.
- *
- * This just wakes up the thread that was waiting on the command to complete.
- */
-static void commandq_callback(struct virtqueue *queue)
-{
- unsigned int len;
- struct virtio_media_cmd_callback_param *param;
-
-process_bufs:
- while ((param = virtqueue_get_buf(queue, &len))) {
- param->done = true;
- param->resp_len = len;
- wake_up(&param->vv->wq);
- }
-
- if (!virtqueue_enable_cb(queue)) {
- virtqueue_disable_cb(queue);
- goto process_bufs;
- }
-}
-
-/**
- * virtio_media_kick_command - send a command to the commandq.
- * @vv: virtio-media device in use.
- * @sgs: descriptor chain to send.
- * @out_sgs: number of device-readable descriptors in @sgs.
- * @in_sgs: number of device-writable descriptors in @sgs.
- * @resp_len: output parameter. Upon success, contains the size of the response
- * in bytes.
- *
- */
-static int virtio_media_kick_command(struct virtio_media *vv,
- struct scatterlist **sgs,
- const size_t out_sgs, const size_t in_sgs,
- size_t *resp_len)
-{
- struct virtio_media_cmd_callback_param cb_param = {
- .vv = vv,
- .done = false,
- .resp_len = 0,
- };
- struct virtio_media_resp_header *resp_header;
- int ret;
-
- ret = virtqueue_add_sgs(vv->commandq, sgs, out_sgs, in_sgs, &cb_param,
- GFP_ATOMIC);
- if (ret) {
- v4l2_err(&vv->v4l2_dev,
- "failed to add sgs to command virtqueue\n");
- return ret;
- }
-
- if (!virtqueue_kick(vv->commandq)) {
- v4l2_err(&vv->v4l2_dev, "failed to kick command virtqueue\n");
- return -EINVAL;
- }
-
- /* Wait for the response. */
- ret = wait_event_timeout(vv->wq, cb_param.done, 5 * HZ);
- if (ret == 0) {
- v4l2_err(&vv->v4l2_dev,
- "timed out waiting for response to command\n");
- return -ETIMEDOUT;
- }
-
- if (resp_len)
- *resp_len = cb_param.resp_len;
-
- if (in_sgs > 0) {
- /*
- * If we expect a response, make sure we have at least a
- * response header - anything shorter is invalid.
- */
- if (cb_param.resp_len < sizeof(*resp_header)) {
- v4l2_err(&vv->v4l2_dev,
- "received response header is too short\n");
- return -EINVAL;
- }
-
- resp_header = sg_virt(sgs[out_sgs]);
- if (resp_header->status)
- /* Host returns a positive error code. */
- return -resp_header->status;
- }
-
- return 0;
-}
-
-/**
- * virtio_media_send_command - Send a command to the device and wait for its
- * response.
- * @vv: virtio-media device in use.
- * @sgs: descriptor chain to send.
- * @out_sgs: number of device-readable descriptors in @sgs.
- * @in_sgs: number of device-writable descriptors in @sgs.
- * @minimum_resp_len: minimum length of the response expected by the caller
- * when the command is successful. Anything shorter than that will result in
- * ``-EINVAL`` being returned.
- * @resp_len: output parameter. Upon success, contains the size of the response
- * in bytes.
- */
-int virtio_media_send_command(struct virtio_media *vv, struct scatterlist **sgs,
- const size_t out_sgs, const size_t in_sgs,
- size_t minimum_resp_len, size_t *resp_len)
-{
- size_t local_resp_len = resp_len ? *resp_len : 0;
- int ret = virtio_media_kick_command(vv, sgs, out_sgs, in_sgs,
- &local_resp_len);
- if (resp_len)
- *resp_len = local_resp_len;
-
- /* If the host could not process the command, there is no valid response */
- if (ret < 0)
- return ret;
-
- /* Make sure the host wrote a complete reply. */
- if (local_resp_len < minimum_resp_len) {
- v4l2_err(
- &vv->v4l2_dev,
- "received response is too short: received %zu, expected at least %zu\n",
- local_resp_len, minimum_resp_len);
- return -EINVAL;
- }
-
- return 0;
-}
-
-/**
- * virtio_media_send_event_buffer() - Sends an event buffer to the host so it
- * can return it with an event.
- * @vv: virtio-media device in use.
- * @event_buffer: pointer to the event buffer to send to the device.
- */
-static int virtio_media_send_event_buffer(struct virtio_media *vv,
- void *event_buffer)
-{
- struct scatterlist *sgs[1], vresp;
- int ret;
-
- sg_init_one(&vresp, event_buffer, VIRTIO_MEDIA_EVENT_MAX_SIZE);
- sgs[0] = &vresp;
-
- ret = virtqueue_add_sgs(vv->eventq, sgs, 0, 1, event_buffer,
- GFP_ATOMIC);
- if (ret) {
- v4l2_err(&vv->v4l2_dev,
- "failed to add sgs to event virtqueue\n");
- return ret;
- }
-
- if (!virtqueue_kick(vv->eventq)) {
- v4l2_err(&vv->v4l2_dev, "failed to kick event virtqueue\n");
- return -EINVAL;
- }
-
- return 0;
-}
-
-/**
- * eventq_callback() - Callback for the event queue.
- * @queue: event virtqueue.
- *
- * This just schedules for event work to be run.
- */
-static void eventq_callback(struct virtqueue *queue)
-{
- struct virtio_media *vv = queue->vdev->priv;
-
- schedule_work(&vv->eventq_work);
-}
-
-/**
- * virtio_media_process_dqbuf_event() - Process a dequeued event for a session.
- * @vv: virtio-media device in use.
- * @session: session the event is addressed to.
- * @dqbuf_evt: the dequeued event to process.
- *
- * Invalid events are ignored with an error log.
- */
-static void
-virtio_media_process_dqbuf_event(struct virtio_media *vv,
- struct virtio_media_session *session,
- struct virtio_media_event_dqbuf *dqbuf_evt)
-{
- struct virtio_media_buffer *dqbuf;
- const enum v4l2_buf_type queue_type = dqbuf_evt->buffer.type;
- struct virtio_media_queue_state *queue;
- typeof(dqbuf->buffer.m) buffer_m;
- typeof(dqbuf->buffer.m.planes[0].m) plane_m;
- int i;
-
- if (queue_type >= ARRAY_SIZE(session->queues)) {
- v4l2_err(&vv->v4l2_dev,
- "unmanaged queue %d passed to dqbuf event",
- dqbuf_evt->buffer.type);
- return;
- }
- queue = &session->queues[queue_type];
-
- if (dqbuf_evt->buffer.index >= queue->allocated_bufs) {
- v4l2_err(&vv->v4l2_dev,
- "invalid buffer ID %d for queue %d in dqbuf event",
- dqbuf_evt->buffer.index, dqbuf_evt->buffer.type);
- return;
- }
-
- dqbuf = &queue->buffers[dqbuf_evt->buffer.index];
-
- /*
- * Preserve the 'm' union that was passed to us during QBUF so userspace
- * gets back the information it submitted.
- */
- buffer_m = dqbuf->buffer.m;
- memcpy(&dqbuf->buffer, &dqbuf_evt->buffer, sizeof(dqbuf->buffer));
- dqbuf->buffer.m = buffer_m;
- if (V4L2_TYPE_IS_MULTIPLANAR(dqbuf->buffer.type)) {
- if (dqbuf->buffer.length > VIDEO_MAX_PLANES) {
- v4l2_err(
- &vv->v4l2_dev,
- "invalid number of planes received from host for a multiplanar buffer\n");
- return;
- }
- for (i = 0; i < dqbuf->buffer.length; i++) {
- plane_m = dqbuf->planes[i].m;
- memcpy(&dqbuf->planes[i], &dqbuf_evt->planes[i],
- sizeof(struct v4l2_plane));
- dqbuf->planes[i].m = plane_m;
- }
- }
-
- /* Set the DONE flag as the buffer is waiting for being dequeued. */
- dqbuf->buffer.flags |= V4L2_BUF_FLAG_DONE;
-
- mutex_lock(&session->queues_lock);
- list_add_tail(&dqbuf->list, &queue->pending_dqbufs);
- queue->queued_bufs -= 1;
- mutex_unlock(&session->queues_lock);
-
- wake_up(&session->dqbuf_wait);
-}
-
-/**
- * virtio_media_process_events() - Process all pending events on a device.
- * @vv: device which pending events we want to process.
- *
- * Retrieves all pending events on @vv's event queue and dispatch them to their
- * corresponding session.
- *
- * Invalid events are ignored with an error log.
- */
-void virtio_media_process_events(struct virtio_media *vv)
-{
- struct virtio_media_event_error *error_evt;
- struct virtio_media_event_dqbuf *dqbuf_evt;
- struct virtio_media_event_event *event_evt;
- struct virtio_media_session *session;
- struct virtio_media_event_header *evt;
- unsigned int len;
-
- mutex_lock(&vv->events_lock);
-
-process_bufs:
- while ((evt = virtqueue_get_buf(vv->eventq, &len))) {
- /* Make sure we received enough data */
- if (len < sizeof(*evt)) {
- v4l2_err(
- &vv->v4l2_dev,
- "event is too short: got %u, expected at least %zu\n",
- len, sizeof(*evt));
- goto end_of_event;
- }
-
- session = virtio_media_find_session(vv, evt->session_id);
- if (!session) {
- v4l2_err(&vv->v4l2_dev, "cannot find session %d\n",
- evt->session_id);
- goto end_of_event;
- }
-
- switch (evt->event) {
- case VIRTIO_MEDIA_EVT_ERROR:
- if (len < sizeof(*error_evt)) {
- v4l2_err(
- &vv->v4l2_dev,
- "error event is too short: got %u, expected %zu\n",
- len, sizeof(*error_evt));
- break;
- }
- error_evt = (struct virtio_media_event_error *)evt;
- v4l2_err(&vv->v4l2_dev,
- "received error %d for session %d",
- error_evt->errno, error_evt->hdr.session_id);
- virtio_media_session_close(vv, session);
- break;
-
- /*
- * Dequeued buffer: put it into the right queue so user-space can dequeue
- * it.
- */
- case VIRTIO_MEDIA_EVT_DQBUF:
- if (len < sizeof(*dqbuf_evt)) {
- v4l2_err(
- &vv->v4l2_dev,
- "dqbuf event is too short: got %u, expected %zu\n",
- len, sizeof(*dqbuf_evt));
- break;
- }
- dqbuf_evt = (struct virtio_media_event_dqbuf *)evt;
- virtio_media_process_dqbuf_event(vv, session,
- dqbuf_evt);
- break;
-
- case VIRTIO_MEDIA_EVT_EVENT:
- if (len < sizeof(*event_evt)) {
- v4l2_err(
- &vv->v4l2_dev,
- "session event is too short: got %u expected %zu\n",
- len, sizeof(*event_evt));
- break;
- }
-
- event_evt = (struct virtio_media_event_event *)evt;
- v4l2_event_queue_fh(&session->fh, &event_evt->event);
- break;
-
- default:
- v4l2_err(&vv->v4l2_dev, "unknown event type %d\n",
- evt->event);
- break;
- }
-
-end_of_event:
- virtio_media_send_event_buffer(vv, evt);
- }
-
- if (!virtqueue_enable_cb(vv->eventq)) {
- virtqueue_disable_cb(vv->eventq);
- goto process_bufs;
- }
-
- mutex_unlock(&vv->events_lock);
-}
-
-static void virtio_media_event_work(struct work_struct *work)
-{
- struct virtio_media *vv =
- container_of(work, struct virtio_media, eventq_work);
-
- virtio_media_process_events(vv);
-}
-
-/**
- * virtio_media_device_open() - Create a new session from an opened file.
- * @file: opened file for the session.
- */
-static int virtio_media_device_open(struct file *file)
-{
- struct video_device *video_dev = video_devdata(file);
- struct virtio_media *vv = to_virtio_media(video_dev);
- struct virtio_media_cmd_open *cmd_open = &vv->cmd.open;
- struct virtio_media_resp_open *resp_open = &vv->resp.open;
- struct scatterlist cmd_sg = {}, resp_sg = {};
- struct scatterlist *sgs[2] = { &cmd_sg, &resp_sg };
- struct virtio_media_session *session;
- u32 session_id;
- int ret;
-
- mutex_lock(&vv->vlock);
-
- sg_set_buf(&cmd_sg, cmd_open, sizeof(*cmd_open));
- sg_mark_end(&cmd_sg);
-
- sg_set_buf(&resp_sg, resp_open, sizeof(*resp_open));
- sg_mark_end(&resp_sg);
-
- cmd_open->hdr.cmd = VIRTIO_MEDIA_CMD_OPEN;
- ret = virtio_media_send_command(vv, sgs, 1, 1, sizeof(*resp_open),
- NULL);
- session_id = resp_open->session_id;
- mutex_unlock(&vv->vlock);
- if (ret < 0)
- return ret;
-
- session = virtio_media_session_alloc(vv, session_id,
- (file->f_flags & O_NONBLOCK));
- if (IS_ERR(session))
- return PTR_ERR(session);
-
- file->private_data = &session->fh;
-
- return 0;
-}
-
-/**
- * virtio_media_device_close() - Close a previously opened session.
- * @file: file of the session to close.
- *
- * This sends to ``VIRTIO_MEDIA_CMD_CLOSE`` command to the device, and close
- * the session on the driver side.
- */
-static int virtio_media_device_close(struct file *file)
-{
- struct video_device *video_dev = video_devdata(file);
- struct virtio_media *vv = to_virtio_media(video_dev);
- struct virtio_media_session *session =
- fh_to_session(file->private_data);
-
- return virtio_media_session_close(vv, session);
-}
-
-/**
- * virtio_media_device_poll() - Poll logic for a virtio-media device.
- * @file: file of the session to poll.
- * @wait: poll table to wait on.
- */
-static __poll_t virtio_media_device_poll(struct file *file, poll_table *wait)
-{
- struct virtio_media_session *session =
- fh_to_session(file->private_data);
- enum v4l2_buf_type capture_type =
- session->uses_mplane ? V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE :
- V4L2_BUF_TYPE_VIDEO_CAPTURE;
- enum v4l2_buf_type output_type =
- session->uses_mplane ? V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE :
- V4L2_BUF_TYPE_VIDEO_OUTPUT;
- struct virtio_media_queue_state *capture_queue =
- &session->queues[capture_type];
- struct virtio_media_queue_state *output_queue =
- &session->queues[output_type];
- __poll_t req_events = poll_requested_events(wait);
- __poll_t rc = 0;
-
- poll_wait(file, &session->dqbuf_wait, wait);
- poll_wait(file, &session->fh.wait, wait);
-
- mutex_lock(&session->queues_lock);
- if (req_events & (EPOLLIN | EPOLLRDNORM)) {
- if (!capture_queue->streaming ||
- (capture_queue->queued_bufs == 0 &&
- list_empty(&capture_queue->pending_dqbufs)))
- rc |= EPOLLERR;
- else if (!list_empty(&capture_queue->pending_dqbufs))
- rc |= EPOLLIN | EPOLLRDNORM;
- }
- if (req_events & (EPOLLOUT | EPOLLWRNORM)) {
- if (!output_queue->streaming)
- rc |= EPOLLERR;
- else if (output_queue->queued_bufs <
- output_queue->allocated_bufs)
- rc |= EPOLLOUT | EPOLLWRNORM;
- }
- mutex_unlock(&session->queues_lock);
-
- if (v4l2_event_pending(&session->fh))
- rc |= EPOLLPRI;
-
- return rc;
-}
-
-static void virtio_media_vma_close_locked(struct vm_area_struct *vma)
-{
- struct virtio_media *vv = vma->vm_private_data;
- struct virtio_media_cmd_munmap *cmd_munmap = &vv->cmd.munmap;
- struct virtio_media_resp_munmap *resp_munmap = &vv->resp.munmap;
- struct scatterlist cmd_sg = {}, resp_sg = {};
- struct scatterlist *sgs[2] = { &cmd_sg, &resp_sg };
- int ret;
-
- sg_set_buf(&cmd_sg, cmd_munmap, sizeof(*cmd_munmap));
- sg_mark_end(&cmd_sg);
-
- sg_set_buf(&resp_sg, resp_munmap, sizeof(*resp_munmap));
- sg_mark_end(&resp_sg);
-
- cmd_munmap->hdr.cmd = VIRTIO_MEDIA_CMD_MUNMAP;
- cmd_munmap->driver_addr =
- (vma->vm_pgoff << PAGE_SHIFT) - vv->mmap_region.addr;
- ret = virtio_media_send_command(vv, sgs, 1, 1, sizeof(*resp_munmap),
- NULL);
- if (ret < 0) {
- v4l2_err(&vv->v4l2_dev, "host failed to unmap buffer: %d\n",
- ret);
- }
-}
-
-/**
- * virtio_media_vma_close() - Close a MMAP buffer mapping.
- * @vma: VMA of the mapping to close.
- *
- * Inform the host that a previously created MMAP mapping is no longer needed
- * and can be removed.
- */
-static void virtio_media_vma_close(struct vm_area_struct *vma)
-{
- struct virtio_media *vv = vma->vm_private_data;
-
- mutex_lock(&vv->vlock);
- virtio_media_vma_close_locked(vma);
- mutex_unlock(&vv->vlock);
-}
-
-static const struct vm_operations_struct virtio_media_vm_ops = {
- .close = virtio_media_vma_close,
-};
-
-/**
- * virtio_media_device_mmap - Perform a mmap request from userspace.
- * @file: opened file of the session to map for.
- * @vma: VM area struct describing the desired mapping.
- *
- * This requests the host to map a MMAP buffer for us, so we can then make that
- * mapping visible into user-space address space.
- */
-static int virtio_media_device_mmap(struct file *file,
- struct vm_area_struct *vma)
-{
- struct video_device *video_dev = video_devdata(file);
- struct virtio_media *vv = to_virtio_media(video_dev);
- struct virtio_media_session *session =
- fh_to_session(file->private_data);
- struct virtio_media_cmd_mmap *cmd_mmap = &session->cmd.mmap;
- struct virtio_media_resp_mmap *resp_mmap = &session->resp.mmap;
- struct scatterlist cmd_sg = {}, resp_sg = {};
- struct scatterlist *sgs[2] = { &cmd_sg, &resp_sg };
- int ret;
-
- if (!(vma->vm_flags & VM_SHARED))
- return -EINVAL;
- if (!(vma->vm_flags & (VM_READ | VM_WRITE)))
- return -EINVAL;
-
- mutex_lock(&vv->vlock);
-
- cmd_mmap->hdr.cmd = VIRTIO_MEDIA_CMD_MMAP;
- cmd_mmap->session_id = session->id;
- cmd_mmap->flags =
- (vma->vm_flags & VM_WRITE) ? VIRTIO_MEDIA_MMAP_FLAG_RW : 0;
- cmd_mmap->offset = vma->vm_pgoff << PAGE_SHIFT;
-
- sg_set_buf(&cmd_sg, cmd_mmap, sizeof(*cmd_mmap));
- sg_mark_end(&cmd_sg);
-
- sg_set_buf(&resp_sg, resp_mmap, sizeof(*resp_mmap));
- sg_mark_end(&resp_sg);
-
- /*
- * The host performs reference counting and is smart enough to return the
- * same guest physical address if this is called several times on the same
- * buffer.
- */
- ret = virtio_media_send_command(vv, sgs, 1, 1, sizeof(*resp_mmap),
- NULL);
- if (ret < 0)
- goto end;
-
- vma->vm_private_data = vv;
- /*
- * Keep the guest address at which the buffer is mapped since we will
- * use that to unmap.
- */
- vma->vm_pgoff = (resp_mmap->driver_addr + vv->mmap_region.addr) >>
- PAGE_SHIFT;
-
- /*
- * We cannot let the mapping be larger than the buffer.
- */
- if (vma->vm_end - vma->vm_start > PAGE_ALIGN(resp_mmap->len)) {
- dev_dbg(&video_dev->dev,
- "invalid MMAP, as it would overflow buffer length\n");
- virtio_media_vma_close_locked(vma);
- ret = -EINVAL;
- goto end;
- }
-
- ret = io_remap_pfn_range(vma, vma->vm_start, vma->vm_pgoff,
- vma->vm_end - vma->vm_start,
- vma->vm_page_prot);
- if (ret)
- goto end;
-
- vma->vm_ops = &virtio_media_vm_ops;
-
-end:
- mutex_unlock(&vv->vlock);
- return ret;
-}
-
-static const struct v4l2_file_operations virtio_media_fops = {
- .owner = THIS_MODULE,
- .open = virtio_media_device_open,
- .release = virtio_media_device_close,
- .poll = virtio_media_device_poll,
- .unlocked_ioctl = virtio_media_device_ioctl,
- .mmap = virtio_media_device_mmap,
-};
-
-static int virtio_media_probe(struct virtio_device *virtio_dev)
-{
- struct device *dev = &virtio_dev->dev;
- struct virtqueue *vqs[2];
- static struct virtqueue_info vq_info[2] = {
- {
- .name = "command",
- .callback = commandq_callback,
- },
- {
- .name = "event",
- .callback = eventq_callback,
- },
- };
- struct virtio_media *vv;
- struct video_device *vd;
- int i;
- int ret;
-
- vv = devm_kzalloc(dev, sizeof(*vv), GFP_KERNEL);
- if (!vv)
- return -ENOMEM;
-
- vv->event_buffer = devm_kzalloc(
- dev, VIRTIO_MEDIA_EVENT_MAX_SIZE * VIRTIO_MEDIA_NUM_EVENT_BUFS,
- GFP_KERNEL);
- if (!vv->event_buffer)
- return -ENOMEM;
-
- INIT_LIST_HEAD(&vv->sessions);
- mutex_init(&vv->sessions_lock);
- mutex_init(&vv->events_lock);
- mutex_init(&vv->vlock);
-
- vv->virtio_dev = virtio_dev;
- virtio_dev->priv = vv;
-
- init_waitqueue_head(&vv->wq);
-
- ret = v4l2_device_register(dev, &vv->v4l2_dev);
- if (ret)
- return ret;
-
- ret = virtio_find_vqs(virtio_dev, 2, vqs, vq_info, NULL);
- if (ret)
- goto err_find_vqs;
-
- vv->commandq = vqs[0];
- vv->eventq = vqs[1];
- INIT_WORK(&vv->eventq_work, virtio_media_event_work);
-
- /* Get MMAP buffer mapping SHM region */
- virtio_get_shm_region(virtio_dev, &vv->mmap_region,
- VIRTIO_MEDIA_SHM_MMAP);
-
- vd = &vv->video_dev;
-
- vd->v4l2_dev = &vv->v4l2_dev;
- vd->vfl_type = VFL_TYPE_VIDEO;
- vd->ioctl_ops = &virtio_media_ioctl_ops;
- vd->fops = &virtio_media_fops;
- vd->device_caps = virtio_cread32(virtio_dev, 0);
- if (vd->device_caps & (V4L2_CAP_VIDEO_M2M | V4L2_CAP_VIDEO_M2M_MPLANE))
- vd->vfl_dir = VFL_DIR_M2M;
- else if (vd->device_caps &
- (V4L2_CAP_VIDEO_OUTPUT | V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE))
- vd->vfl_dir = VFL_DIR_TX;
- else
- vd->vfl_dir = VFL_DIR_RX;
- vd->release = video_device_release_empty;
- strscpy(vd->name, "virtio-media", sizeof(vd->name));
-
- video_set_drvdata(vd, vv);
-
- ret = video_register_device(vd, virtio_cread32(virtio_dev, 4), 0);
- if (ret)
- goto err_register_device;
-
- for (i = 0; i < VIRTIO_MEDIA_NUM_EVENT_BUFS; i++) {
- ret = virtio_media_send_event_buffer(
- vv, vv->event_buffer + VIRTIO_MEDIA_EVENT_MAX_SIZE * i);
- if (ret)
- goto err_send_event_buffer;
- }
-
- virtio_device_ready(virtio_dev);
-
- return 0;
-
-err_send_event_buffer:
- video_unregister_device(&vv->video_dev);
-err_register_device:
- virtio_dev->config->del_vqs(virtio_dev);
-err_find_vqs:
- v4l2_device_unregister(&vv->v4l2_dev);
-
- return ret;
-}
-
-static void virtio_media_remove(struct virtio_device *virtio_dev)
-{
- struct virtio_media *vv = virtio_dev->priv;
- struct list_head *p, *n;
-
- cancel_work_sync(&vv->eventq_work);
- virtio_reset_device(virtio_dev);
-
- v4l2_device_unregister(&vv->v4l2_dev);
- virtio_dev->config->del_vqs(virtio_dev);
- video_unregister_device(&vv->video_dev);
-
- list_for_each_safe(p, n, &vv->sessions) {
- struct virtio_media_session *s =
- list_entry(p, struct virtio_media_session, list);
-
- virtio_media_session_free(vv, s);
- }
-}
-
-static struct virtio_device_id id_table[] = {
- { VIRTIO_ID_MEDIA, VIRTIO_DEV_ANY_ID },
- { 0 },
-};
-
-static unsigned int features[] = {};
-
-static struct virtio_driver virtio_media_driver = {
- .feature_table = features,
- .feature_table_size = ARRAY_SIZE(features),
- .driver.name = VIRTIO_MEDIA_DEFAULT_DRIVER_NAME,
- .driver.owner = THIS_MODULE,
- .id_table = id_table,
- .probe = virtio_media_probe,
- .remove = virtio_media_remove,
-};
-
-module_virtio_driver(virtio_media_driver);
-
-MODULE_DEVICE_TABLE(virtio, id_table);
-MODULE_DESCRIPTION("virtio media driver");
-MODULE_AUTHOR("Alexandre Courbot <gnurou@gmail.com>");
-MODULE_LICENSE("Dual BSD/GPL");
diff --git a/drivers/media/virtio/virtio_media_ioctls.c b/drivers/media/virtio/virtio_media_ioctls.c
deleted file mode 100644
index 863cdfbaaadc..000000000000
--- a/drivers/media/virtio/virtio_media_ioctls.c
+++ /dev/null
@@ -1,1297 +0,0 @@
-// SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0+
-
-/*
- * Ioctls implementations for the virtio-media driver.
- *
- * Copyright (c) 2024-2025 Google LLC.
- */
-
-#include <linux/mutex.h>
-#include <linux/videodev2.h>
-#include <linux/virtio_config.h>
-#include <linux/vmalloc.h>
-#include <media/v4l2-event.h>
-#include <media/v4l2-ioctl.h>
-
-#include "scatterlist_builder.h"
-#include "virtio_media.h"
-
-/**
- * virtio_media_send_r_ioctl() - Send a read-only ioctl to the device.
- * @fh: file handler of the session doing the ioctl.
- * @ioctl: ``VIDIOC_*`` ioctl code.
- * @ioctl_data: pointer to the ioctl payload.
- * @ioctl_data_len: length in bytes of the ioctl payload.
- *
- * Send an ioctl that has no driver payload, but expects a response from the
- * host (i.e. an ioctl specified with ``_IOR``).
- */
-static int virtio_media_send_r_ioctl(struct v4l2_fh *fh, u32 ioctl,
- void *ioctl_data, size_t ioctl_data_len)
-{
- struct video_device *video_dev = fh->vdev;
- struct virtio_media *vv = to_virtio_media(video_dev);
- struct virtio_media_session *session = fh_to_session(fh);
- struct scatterlist *sgs[3];
- struct scatterlist_builder builder = {
- .descs = session->command_sgs.sgl,
- .num_descs = DESC_CHAIN_MAX_LEN,
- .cur_desc = 0,
- .shadow_buffer = session->shadow_buf,
- .shadow_buffer_size = VIRTIO_SHADOW_BUF_SIZE,
- .shadow_buffer_pos = 0,
- .sgs = sgs,
- .num_sgs = ARRAY_SIZE(sgs),
- .cur_sg = 0,
- };
- int ret;
-
- /* Command descriptor */
- ret = scatterlist_builder_add_ioctl_cmd(&builder, session, ioctl);
- if (ret)
- return ret;
-
- /* Response descriptor */
- ret = scatterlist_builder_add_ioctl_resp(&builder, session);
- if (ret)
- return ret;
-
- /* Response payload */
- ret = scatterlist_builder_add_data(&builder, ioctl_data,
- ioctl_data_len);
- if (ret) {
- v4l2_err(&vv->v4l2_dev,
- "failed to prepare command descriptor chain\n");
- return ret;
- }
-
- ret = virtio_media_send_command(
- vv, sgs, 1, 2,
- sizeof(struct virtio_media_resp_ioctl) + ioctl_data_len, NULL);
- if (ret < 0)
- return ret;
-
- ret = scatterlist_builder_retrieve_data(&builder, 2, ioctl_data);
- if (ret) {
- v4l2_err(&vv->v4l2_dev,
- "failed to retrieve response descriptor chain\n");
- return ret;
- }
-
- return 0;
-}
-
-/**
- * virtio_media_send_w_ioctl() - Send a write-only ioctl to the device.
- * @fh: file handler of the session doing the ioctl.
- * @ioctl: ``VIDIOC_*`` ioctl code.
- * @ioctl_data: pointer to the ioctl payload.
- * @ioctl_data_len: length in bytes of the ioctl payload.
- *
- * Send an ioctl that does not expect a reply beyond an error status (i.e. an
- * ioctl specified with ``_IOW``) to the host.
- */
-static int virtio_media_send_w_ioctl(struct v4l2_fh *fh, u32 ioctl,
- const void *ioctl_data,
- size_t ioctl_data_len)
-{
- struct video_device *video_dev = fh->vdev;
- struct virtio_media *vv = to_virtio_media(video_dev);
- struct virtio_media_session *session = fh_to_session(fh);
- struct scatterlist *sgs[3];
- struct scatterlist_builder builder = {
- .descs = session->command_sgs.sgl,
- .num_descs = DESC_CHAIN_MAX_LEN,
- .cur_desc = 0,
- .shadow_buffer = session->shadow_buf,
- .shadow_buffer_size = VIRTIO_SHADOW_BUF_SIZE,
- .shadow_buffer_pos = 0,
- .sgs = sgs,
- .num_sgs = ARRAY_SIZE(sgs),
- .cur_sg = 0,
- };
- int ret;
-
- /* Command descriptor */
- ret = scatterlist_builder_add_ioctl_cmd(&builder, session, ioctl);
- if (ret)
- return ret;
-
- /* Command payload */
- ret = scatterlist_builder_add_data(&builder, (void *)ioctl_data,
- ioctl_data_len);
- if (ret) {
- v4l2_err(&vv->v4l2_dev,
- "failed to prepare command descriptor chain\n");
- return ret;
- }
-
- /* Response descriptor */
- ret = scatterlist_builder_add_ioctl_resp(&builder, session);
- if (ret)
- return ret;
-
- ret = virtio_media_send_command(
- vv, sgs, 2, 1, sizeof(struct virtio_media_resp_ioctl), NULL);
- if (ret < 0)
- return ret;
-
- return 0;
-}
-
-/**
- * virtio_media_send_wr_ioctl() - Send a read-write ioctl to the device.
- * @fh: file handler of the session doing the ioctl.
- * @ioctl: ``VIDIOC_*`` ioctl code.
- * @ioctl_data: pointer to the ioctl payload.
- * @ioctl_data_len: length in bytes of the ioctl payload.
- * @minimum_resp_payload: minimum expected length of the response's payload.
- *
- * Sends an ioctl that expects a response of exactly the same size as the
- * input (i.e. an ioctl specified with ``_IOWR``) to the host.
- *
- * This corresponds to what most V4L2 ioctls do. For instance
- * ``VIDIOC_ENUM_FMT`` takes a partially-initialized ``struct v4l2_fmtdesc``
- * and returns its filled version.
- */
-static int virtio_media_send_wr_ioctl(struct v4l2_fh *fh, u32 ioctl,
- void *ioctl_data, size_t ioctl_data_len,
- size_t minimum_resp_payload)
-{
- struct video_device *video_dev = fh->vdev;
- struct virtio_media *vv = to_virtio_media(video_dev);
- struct virtio_media_session *session = fh_to_session(fh);
- struct scatterlist *sgs[4];
- struct scatterlist_builder builder = {
- .descs = session->command_sgs.sgl,
- .num_descs = DESC_CHAIN_MAX_LEN,
- .cur_desc = 0,
- .shadow_buffer = session->shadow_buf,
- .shadow_buffer_size = VIRTIO_SHADOW_BUF_SIZE,
- .shadow_buffer_pos = 0,
- .sgs = sgs,
- .num_sgs = ARRAY_SIZE(sgs),
- .cur_sg = 0,
- };
- int ret;
-
- /* Command descriptor */
- ret = scatterlist_builder_add_ioctl_cmd(&builder, session, ioctl);
- if (ret)
- return ret;
-
- /* Command payload */
- ret = scatterlist_builder_add_data(&builder, ioctl_data,
- ioctl_data_len);
- if (ret) {
- v4l2_err(&vv->v4l2_dev,
- "failed to prepare command descriptor chain\n");
- return ret;
- }
-
- /* Response descriptor */
- ret = scatterlist_builder_add_ioctl_resp(&builder, session);
- if (ret)
- return ret;
-
- /* Response payload, same as command */
- ret = scatterlist_builder_add_descriptor(&builder, 1);
- if (ret)
- return ret;
-
- ret = virtio_media_send_command(vv, sgs, 2, 2,
- sizeof(struct virtio_media_resp_ioctl) +
- minimum_resp_payload,
- NULL);
- if (ret < 0)
- return ret;
-
- ret = scatterlist_builder_retrieve_data(&builder, 3, ioctl_data);
- if (ret) {
- v4l2_err(&vv->v4l2_dev,
- "failed to retrieve response descriptor chain\n");
- return ret;
- }
-
- return 0;
-}
-
-/**
- * virtio_media_send_buffer_ioctl() - Send an ioctl taking a buffer as
- * parameter to the device.
- * @fh: file handler of the session doing the ioctl.
- * @ioctl: ``VIDIOC_*`` ioctl code.
- * @b: ``v4l2_buffer`` to be sent as the ioctl payload.
- *
- * Buffers can require an additional descriptor to send their planes array, and
- * can have pointers to userspace memory hence this dedicated function.
- */
-static int virtio_media_send_buffer_ioctl(struct v4l2_fh *fh, u32 ioctl,
- struct v4l2_buffer *b)
-{
- struct video_device *video_dev = fh->vdev;
- struct virtio_media *vv = to_virtio_media(video_dev);
- struct virtio_media_session *session = fh_to_session(fh);
- struct v4l2_plane *orig_planes = NULL;
- struct scatterlist *sgs[64];
- /* End of the device-readable buffer SGs, to reuse in device-writable section. */
- size_t num_cmd_sgs;
- size_t end_buf_sg;
- struct scatterlist_builder builder = {
- .descs = session->command_sgs.sgl,
- .num_descs = DESC_CHAIN_MAX_LEN,
- .cur_desc = 0,
- .shadow_buffer = session->shadow_buf,
- .shadow_buffer_size = VIRTIO_SHADOW_BUF_SIZE,
- .shadow_buffer_pos = 0,
- .sgs = sgs,
- .num_sgs = ARRAY_SIZE(sgs),
- .cur_sg = 0,
- };
- size_t resp_len;
- int ret;
- int i;
-
- if (b->type > VIRTIO_MEDIA_LAST_QUEUE)
- return -EINVAL;
-
- if (V4L2_TYPE_IS_MULTIPLANAR(b->type))
- orig_planes = b->m.planes;
-
- /* Command descriptor */
- ret = scatterlist_builder_add_ioctl_cmd(&builder, session, ioctl);
- if (ret)
- return ret;
-
- /* Command payload (struct v4l2_buffer) */
- ret = scatterlist_builder_add_buffer(&builder, b);
- if (ret < 0)
- return ret;
-
- end_buf_sg = builder.cur_sg;
-
- /* Payload of SHARED_PAGES buffers, if relevant */
- ret = scatterlist_builder_add_buffer_userptr(&builder, b);
- if (ret < 0)
- return ret;
-
- num_cmd_sgs = builder.cur_sg;
-
- /* Response descriptor */
- ret = scatterlist_builder_add_ioctl_resp(&builder, session);
- if (ret)
- return ret;
-
- /* Response payload (same as input, but no userptr mapping) */
- for (i = 1; i < end_buf_sg; i++) {
- ret = scatterlist_builder_add_descriptor(&builder, i);
- if (ret < 0)
- return ret;
- }
-
- ret = virtio_media_send_command(
- vv, builder.sgs, num_cmd_sgs, builder.cur_sg - num_cmd_sgs,
- sizeof(struct virtio_media_resp_ioctl) + sizeof(*b), &resp_len);
- if (ret < 0)
- return ret;
-
- resp_len -= sizeof(struct virtio_media_resp_ioctl);
-
- /* Make sure that the reply length covers our v4l2_buffer */
- if (resp_len < sizeof(*b))
- return -EINVAL;
-
- ret = scatterlist_builder_retrieve_buffer(&builder, num_cmd_sgs + 1, b,
- orig_planes);
- if (ret) {
- v4l2_err(&vv->v4l2_dev,
- "failed to retrieve response descriptor chain\n");
- return ret;
- }
-
- return 0;
-}
-
-/**
- * virtio_media_send_ext_controls_ioctl() - Send an ioctl taking extended
- * controls as parameters to the device.
- * @fh: file handler of the session doing the ioctl.
- * @ioctl: ``VIDIOC_*`` ioctl code.
- * @ctrls: ``v4l2_ext_controls`` to be sent as the ioctl payload.
- *
- * Queues an ioctl that sends a ``v4l2_ext_controls`` to the host and receives
- * an updated version.
- *
- * ``v4l2_ext_controls`` has a pointer to an array of ``v4l2_ext_control``, and
- * also potentially pointers to user-space memory that we need to map properly,
- * hence the dedicated function.
- */
-static int virtio_media_send_ext_controls_ioctl(struct v4l2_fh *fh, u32 ioctl,
- struct v4l2_ext_controls *ctrls)
-{
- struct video_device *video_dev = fh->vdev;
- struct virtio_media *vv = to_virtio_media(video_dev);
- struct virtio_media_session *session = fh_to_session(fh);
- size_t num_cmd_sgs;
- size_t end_ctrls_sg;
- struct v4l2_ext_control *controls_backup = ctrls->controls;
- const u32 num_ctrls = ctrls->count;
- struct scatterlist *sgs[64];
- struct scatterlist_builder builder = {
- .descs = session->command_sgs.sgl,
- .num_descs = DESC_CHAIN_MAX_LEN,
- .cur_desc = 0,
- .shadow_buffer = session->shadow_buf,
- .shadow_buffer_size = VIRTIO_SHADOW_BUF_SIZE,
- .shadow_buffer_pos = 0,
- .sgs = sgs,
- .num_sgs = ARRAY_SIZE(sgs),
- .cur_sg = 0,
- };
- size_t resp_len = 0;
- int ret;
- int i;
-
- /* Command descriptor */
- ret = scatterlist_builder_add_ioctl_cmd(&builder, session, ioctl);
- if (ret)
- return ret;
-
- /* v4l2_controls */
- ret = scatterlist_builder_add_ext_ctrls(&builder, ctrls);
- if (ret)
- return ret;
-
- end_ctrls_sg = builder.cur_sg;
-
- ret = scatterlist_builder_add_ext_ctrls_userptrs(&builder, ctrls);
- if (ret)
- return ret;
-
- num_cmd_sgs = builder.cur_sg;
-
- /* Response descriptor */
- ret = scatterlist_builder_add_ioctl_resp(&builder, session);
- if (ret)
- return ret;
-
- /* Response payload (same as input but without userptrs) */
- for (i = 1; i < end_ctrls_sg; i++) {
- ret = scatterlist_builder_add_descriptor(&builder, i);
- if (ret < 0)
- return ret;
- }
-
- ret = virtio_media_send_command(
- vv, builder.sgs, num_cmd_sgs, builder.cur_sg - num_cmd_sgs,
- sizeof(struct virtio_media_resp_ioctl) + sizeof(*ctrls),
- &resp_len);
-
- /* Just in case the host touched these. */
- ctrls->controls = controls_backup;
- if (ctrls->count != num_ctrls) {
- v4l2_err(
- &vv->v4l2_dev,
- "device returned a number of controls different than the one submitted\n");
- }
- if (ctrls->count > num_ctrls)
- return -ENOSPC;
-
- /* Event if we have received an error, we may need to read our payload back */
- if (ret < 0 && resp_len >= sizeof(struct virtio_media_resp_ioctl) +
- sizeof(*ctrls)) {
- /* Deliberately ignore the error here as we want to return the previous one */
- scatterlist_builder_retrieve_ext_ctrls(&builder,
- num_cmd_sgs + 1, ctrls);
- return ret;
- }
-
- resp_len -= sizeof(struct virtio_media_resp_ioctl);
-
- /* Make sure that the reply's length covers our v4l2_ext_controls */
- if (resp_len < sizeof(*ctrls))
- return -EINVAL;
-
- ret = scatterlist_builder_retrieve_ext_ctrls(&builder, num_cmd_sgs + 1,
- ctrls);
- if (ret)
- return ret;
-
- return 0;
-}
-
-/**
- * virtio_media_clear_queue() - clear all pending buffers on a streamed-off queue.
- * @session: session which the queue to clear belongs to.
- * @queue: state of the queue to clear.
- *
- * Helper function to clear the list of buffers waiting to be dequeued on a
- * queue that has just been streamed off.
- */
-static void virtio_media_clear_queue(struct virtio_media_session *session,
- struct virtio_media_queue_state *queue)
-{
- struct list_head *p, *n;
- int i;
-
- mutex_lock(&session->queues_lock);
-
- list_for_each_safe(p, n, &queue->pending_dqbufs) {
- struct virtio_media_buffer *dqbuf =
- list_entry(p, struct virtio_media_buffer, list);
-
- list_del(&dqbuf->list);
- }
-
- /* All buffers are now dequeued. */
- for (i = 0; i < queue->allocated_bufs; i++)
- queue->buffers[i].buffer.flags = 0;
-
- queue->queued_bufs = 0;
- queue->streaming = false;
- queue->is_capture_last = false;
-
- mutex_unlock(&session->queues_lock);
-}
-
-/*
- * Macros suitable for defining ioctls with a constant size payload.
- */
-
-#define SIMPLE_WR_IOCTL(name, ioctl, payload_t) \
- static int virtio_media_##name(struct file *file, void *fh, \
- payload_t *payload) \
- { \
- return virtio_media_send_wr_ioctl(fh, ioctl, payload, \
- sizeof(*payload), \
- sizeof(*payload)); \
- }
-#define SIMPLE_R_IOCTL(name, ioctl, payload_t) \
- static int virtio_media_##name(struct file *file, void *fh, \
- payload_t *payload) \
- { \
- return virtio_media_send_r_ioctl(fh, ioctl, payload, \
- sizeof(*payload)); \
- }
-#define SIMPLE_W_IOCTL(name, ioctl, payload_t) \
- static int virtio_media_##name(struct file *file, void *fh, \
- payload_t *payload) \
- { \
- return virtio_media_send_w_ioctl(fh, ioctl, payload, \
- sizeof(*payload)); \
- }
-
-/*
- * V4L2 ioctl handlers.
- *
- * Most of these functions just forward the ioctl to the host, for these we can
- * use one of the SIMPLE_*_IOCTL macros. Exceptions that have their own
- * standalone function follow.
- */
-
-SIMPLE_WR_IOCTL(enum_fmt, VIDIOC_ENUM_FMT, struct v4l2_fmtdesc)
-SIMPLE_WR_IOCTL(g_fmt, VIDIOC_G_FMT, struct v4l2_format)
-SIMPLE_WR_IOCTL(s_fmt, VIDIOC_S_FMT, struct v4l2_format)
-SIMPLE_WR_IOCTL(try_fmt, VIDIOC_TRY_FMT, struct v4l2_format)
-SIMPLE_WR_IOCTL(enum_framesizes, VIDIOC_ENUM_FRAMESIZES,
- struct v4l2_frmsizeenum)
-SIMPLE_WR_IOCTL(enum_frameintervals, VIDIOC_ENUM_FRAMEINTERVALS,
- struct v4l2_frmivalenum)
-SIMPLE_WR_IOCTL(query_ext_ctrl, VIDIOC_QUERY_EXT_CTRL,
- struct v4l2_query_ext_ctrl)
-SIMPLE_WR_IOCTL(s_dv_timings, VIDIOC_S_DV_TIMINGS, struct v4l2_dv_timings)
-SIMPLE_WR_IOCTL(g_dv_timings, VIDIOC_G_DV_TIMINGS, struct v4l2_dv_timings)
-SIMPLE_R_IOCTL(query_dv_timings, VIDIOC_QUERY_DV_TIMINGS,
- struct v4l2_dv_timings)
-SIMPLE_WR_IOCTL(enum_dv_timings, VIDIOC_ENUM_DV_TIMINGS,
- struct v4l2_enum_dv_timings)
-SIMPLE_WR_IOCTL(dv_timings_cap, VIDIOC_DV_TIMINGS_CAP,
- struct v4l2_dv_timings_cap)
-SIMPLE_WR_IOCTL(enuminput, VIDIOC_ENUMINPUT, struct v4l2_input)
-SIMPLE_WR_IOCTL(querymenu, VIDIOC_QUERYMENU, struct v4l2_querymenu)
-SIMPLE_WR_IOCTL(enumoutput, VIDIOC_ENUMOUTPUT, struct v4l2_output)
-SIMPLE_WR_IOCTL(enumaudio, VIDIOC_ENUMAUDIO, struct v4l2_audio)
-SIMPLE_R_IOCTL(g_audio, VIDIOC_G_AUDIO, struct v4l2_audio)
-SIMPLE_W_IOCTL(s_audio, VIDIOC_S_AUDIO, const struct v4l2_audio)
-SIMPLE_WR_IOCTL(enumaudout, VIDIOC_ENUMAUDOUT, struct v4l2_audioout)
-SIMPLE_R_IOCTL(g_audout, VIDIOC_G_AUDOUT, struct v4l2_audioout)
-SIMPLE_W_IOCTL(s_audout, VIDIOC_S_AUDOUT, const struct v4l2_audioout)
-SIMPLE_WR_IOCTL(g_modulator, VIDIOC_G_MODULATOR, struct v4l2_modulator)
-SIMPLE_W_IOCTL(s_modulator, VIDIOC_S_MODULATOR, const struct v4l2_modulator)
-SIMPLE_WR_IOCTL(g_selection, VIDIOC_G_SELECTION, struct v4l2_selection)
-SIMPLE_WR_IOCTL(s_selection, VIDIOC_S_SELECTION, struct v4l2_selection)
-SIMPLE_R_IOCTL(g_enc_index, VIDIOC_G_ENC_INDEX, struct v4l2_enc_idx)
-SIMPLE_WR_IOCTL(encoder_cmd, VIDIOC_ENCODER_CMD, struct v4l2_encoder_cmd)
-SIMPLE_WR_IOCTL(try_encoder_cmd, VIDIOC_TRY_ENCODER_CMD,
- struct v4l2_encoder_cmd)
-SIMPLE_WR_IOCTL(try_decoder_cmd, VIDIOC_TRY_DECODER_CMD,
- struct v4l2_decoder_cmd)
-SIMPLE_WR_IOCTL(g_parm, VIDIOC_G_PARM, struct v4l2_streamparm)
-SIMPLE_WR_IOCTL(s_parm, VIDIOC_S_PARM, struct v4l2_streamparm)
-SIMPLE_R_IOCTL(g_std, VIDIOC_G_STD, v4l2_std_id)
-SIMPLE_R_IOCTL(querystd, VIDIOC_QUERYSTD, v4l2_std_id)
-SIMPLE_WR_IOCTL(enumstd, VIDIOC_ENUMSTD, struct v4l2_standard)
-SIMPLE_WR_IOCTL(g_tuner, VIDIOC_G_TUNER, struct v4l2_tuner)
-SIMPLE_W_IOCTL(s_tuner, VIDIOC_S_TUNER, const struct v4l2_tuner)
-SIMPLE_WR_IOCTL(g_frequency, VIDIOC_G_FREQUENCY, struct v4l2_frequency)
-SIMPLE_W_IOCTL(s_frequency, VIDIOC_S_FREQUENCY, const struct v4l2_frequency)
-SIMPLE_WR_IOCTL(enum_freq_bands, VIDIOC_ENUM_FREQ_BANDS,
- struct v4l2_frequency_band)
-SIMPLE_WR_IOCTL(g_sliced_vbi_cap, VIDIOC_G_SLICED_VBI_CAP,
- struct v4l2_sliced_vbi_cap)
-SIMPLE_W_IOCTL(s_hw_freq_seek, VIDIOC_S_HW_FREQ_SEEK,
- const struct v4l2_hw_freq_seek)
-
-/*
- * QUERYCAP is handled by reading the configuration area.
- *
- */
-
-static int virtio_media_querycap(struct file *file, void *fh,
- struct v4l2_capability *cap)
-{
- struct video_device *video_dev = video_devdata(file);
- struct virtio_media *vv = to_virtio_media(video_dev);
-
- strscpy(cap->bus_info, "platform:virtio-media");
-
- if (!virtio_media_driver_name)
- strscpy(cap->driver, VIRTIO_MEDIA_DEFAULT_DRIVER_NAME);
- else
- strscpy(cap->driver, virtio_media_driver_name);
-
- virtio_cread_bytes(vv->virtio_dev, 8, cap->card, sizeof(cap->card));
-
- cap->capabilities = video_dev->device_caps | V4L2_CAP_DEVICE_CAPS;
- cap->device_caps = video_dev->device_caps;
-
- return 0;
-}
-
-/*
- * Extended control ioctls are handled mostly identically.
- */
-
-static int virtio_media_g_ext_ctrls(struct file *file, void *fh,
- struct v4l2_ext_controls *ctrls)
-{
- return virtio_media_send_ext_controls_ioctl(fh, VIDIOC_G_EXT_CTRLS,
- ctrls);
-}
-
-static int virtio_media_s_ext_ctrls(struct file *file, void *fh,
- struct v4l2_ext_controls *ctrls)
-{
- return virtio_media_send_ext_controls_ioctl(fh, VIDIOC_S_EXT_CTRLS,
- ctrls);
-}
-
-static int virtio_media_try_ext_ctrls(struct file *file, void *fh,
- struct v4l2_ext_controls *ctrls)
-{
- return virtio_media_send_ext_controls_ioctl(fh, VIDIOC_TRY_EXT_CTRLS,
- ctrls);
-}
-
-/*
- * Subscribe/unsubscribe from an event.
- */
-
-static int
-virtio_media_subscribe_event(struct v4l2_fh *fh,
- const struct v4l2_event_subscription *sub)
-{
- struct video_device *video_dev = fh->vdev;
- struct virtio_media *vv = to_virtio_media(video_dev);
- int ret;
-
- /* First subscribe to the event in the guest. */
- switch (sub->type) {
- case V4L2_EVENT_SOURCE_CHANGE:
- ret = v4l2_src_change_event_subscribe(fh, sub);
- break;
- default:
- ret = v4l2_event_subscribe(fh, sub, 1, NULL);
- break;
- }
- if (ret)
- return ret;
-
- /* Then ask the host to signal us these events. */
- ret = virtio_media_send_w_ioctl(fh, VIDIOC_SUBSCRIBE_EVENT, sub,
- sizeof(*sub));
- if (ret < 0) {
- v4l2_event_unsubscribe(fh, sub);
- return ret;
- }
-
- /*
- * Subscribing to an event may result in that event being signaled
- * immediately. Process all pending events to make sure we don't miss it.
- */
- if (sub->flags & V4L2_EVENT_SUB_FL_SEND_INITIAL)
- virtio_media_process_events(vv);
-
- return 0;
-}
-
-static int
-virtio_media_unsubscribe_event(struct v4l2_fh *fh,
- const struct v4l2_event_subscription *sub)
-{
- int ret;
-
- ret = virtio_media_send_w_ioctl(fh, VIDIOC_UNSUBSCRIBE_EVENT, sub,
- sizeof(*sub));
- if (ret < 0)
- return ret;
-
- ret = v4l2_event_unsubscribe(fh, sub);
- if (ret)
- return ret;
-
- return 0;
-}
-
-/*
- * Streamon/off affect the local queue state.
- */
-
-static int virtio_media_streamon(struct file *file, void *fh,
- enum v4l2_buf_type i)
-{
- struct virtio_media_session *session = fh_to_session(fh);
- int ret;
-
- if (i > VIRTIO_MEDIA_LAST_QUEUE)
- return -EINVAL;
-
- ret = virtio_media_send_w_ioctl(fh, VIDIOC_STREAMON, &i, sizeof(i));
- if (ret < 0)
- return ret;
-
- session->queues[i].streaming = true;
-
- return 0;
-}
-
-static int virtio_media_streamoff(struct file *file, void *fh,
- enum v4l2_buf_type i)
-{
- struct virtio_media_session *session = fh_to_session(fh);
- int ret;
-
- if (i > VIRTIO_MEDIA_LAST_QUEUE)
- return -EINVAL;
-
- ret = virtio_media_send_w_ioctl(fh, VIDIOC_STREAMOFF, &i, sizeof(i));
- if (ret < 0)
- return ret;
-
- virtio_media_clear_queue(session, &session->queues[i]);
-
- return 0;
-}
-
-/*
- * Buffer creation/queuing functions deal with the local driver state.
- */
-
-static int virtio_media_reqbufs(struct file *file, void *fh,
- struct v4l2_requestbuffers *b)
-{
- struct virtio_media_session *session = fh_to_session(fh);
- struct virtio_media_queue_state *queue;
- int ret;
-
- if (b->type > VIRTIO_MEDIA_LAST_QUEUE)
- return -EINVAL;
-
- if (b->memory == V4L2_MEMORY_USERPTR && !virtio_media_allow_userptr)
- return -EINVAL;
-
- ret = virtio_media_send_wr_ioctl(fh, VIDIOC_REQBUFS, b, sizeof(*b),
- sizeof(*b));
- if (ret)
- return ret;
-
- queue = &session->queues[b->type];
-
- /* REQBUFS(0) is an implicit STREAMOFF. */
- if (b->count == 0)
- virtio_media_clear_queue(session, queue);
-
- vfree(queue->buffers);
- queue->buffers = NULL;
-
- if (b->count > 0) {
- queue->buffers =
- vzalloc(sizeof(struct virtio_media_buffer) * b->count);
- if (!queue->buffers)
- return -ENOMEM;
- }
-
- queue->allocated_bufs = b->count;
-
- /*
- * If a multiplanar queue is successfully used here, this means
- * we are using the multiplanar interface.
- */
- if (V4L2_TYPE_IS_MULTIPLANAR(b->type))
- session->uses_mplane = true;
-
- if (!virtio_media_allow_userptr)
- b->capabilities &= ~V4L2_BUF_CAP_SUPPORTS_USERPTR;
-
- /* We do not support DMABUF yet. */
- b->capabilities &= ~V4L2_BUF_CAP_SUPPORTS_DMABUF;
-
- return 0;
-}
-
-static int virtio_media_querybuf(struct file *file, void *fh,
- struct v4l2_buffer *b)
-{
- struct virtio_media_session *session = fh_to_session(fh);
- struct virtio_media_queue_state *queue;
- struct virtio_media_buffer *buffer;
- int ret;
-
- ret = virtio_media_send_buffer_ioctl(fh, VIDIOC_QUERYBUF, b);
- if (ret)
- return ret;
-
- if (b->type > VIRTIO_MEDIA_LAST_QUEUE)
- return -EINVAL;
-
- queue = &session->queues[b->type];
- if (b->index >= queue->allocated_bufs)
- return -EINVAL;
-
- buffer = &queue->buffers[b->index];
- /* Set the DONE flag if the buffer is waiting in our own dequeue queue. */
- b->flags |= (buffer->buffer.flags & V4L2_BUF_FLAG_DONE);
-
- return 0;
-}
-
-static int virtio_media_create_bufs(struct file *file, void *fh,
- struct v4l2_create_buffers *b)
-{
- struct virtio_media_session *session = fh_to_session(fh);
- struct virtio_media_queue_state *queue;
- struct virtio_media_buffer *buffers;
- u32 type = b->format.type;
- int ret;
-
- if (type > VIRTIO_MEDIA_LAST_QUEUE)
- return -EINVAL;
-
- queue = &session->queues[type];
-
- ret = virtio_media_send_wr_ioctl(fh, VIDIOC_CREATE_BUFS, b, sizeof(*b),
- sizeof(*b));
- if (ret)
- return ret;
-
- /* If count is zero, we were just checking for format. */
- if (b->count == 0)
- return 0;
-
- buffers = queue->buffers;
-
- queue->buffers =
- vzalloc(sizeof(*queue->buffers) * (b->index + b->count));
- if (!queue->buffers) {
- queue->buffers = buffers;
- return -ENOMEM;
- }
-
- memcpy(queue->buffers, buffers,
- sizeof(*buffers) * queue->allocated_bufs);
- vfree(buffers);
-
- queue->allocated_bufs = b->index + b->count;
-
- return 0;
-}
-
-static int virtio_media_prepare_buf(struct file *file, void *fh,
- struct v4l2_buffer *b)
-{
- struct virtio_media_session *session = fh_to_session(fh);
- struct virtio_media_queue_state *queue;
- struct virtio_media_buffer *buffer;
- int i, ret;
-
- if (b->type > VIRTIO_MEDIA_LAST_QUEUE)
- return -EINVAL;
- queue = &session->queues[b->type];
- if (b->index >= queue->allocated_bufs)
- return -EINVAL;
- buffer = &queue->buffers[b->index];
-
- buffer->buffer.m = b->m;
- if (V4L2_TYPE_IS_MULTIPLANAR(b->type)) {
- if (b->length > VIDEO_MAX_PLANES)
- return -EINVAL;
- for (i = 0; i < b->length; i++)
- buffer->planes[i].m = b->m.planes[i].m;
- }
-
- ret = virtio_media_send_buffer_ioctl(fh, VIDIOC_PREPARE_BUF, b);
- if (ret)
- return ret;
-
- buffer->buffer.flags = V4L2_BUF_FLAG_PREPARED;
-
- return 0;
-}
-
-static int virtio_media_qbuf(struct file *file, void *fh, struct v4l2_buffer *b)
-{
- struct virtio_media_session *session = fh_to_session(fh);
- struct virtio_media_queue_state *queue;
- struct virtio_media_buffer *buffer;
- bool prepared;
- u32 old_flags;
- int i, ret;
-
- if (b->type > VIRTIO_MEDIA_LAST_QUEUE)
- return -EINVAL;
- queue = &session->queues[b->type];
- if (b->index >= queue->allocated_bufs)
- return -EINVAL;
- buffer = &queue->buffers[b->index];
- prepared = buffer->buffer.flags & V4L2_BUF_FLAG_PREPARED;
-
- /*
- * Store the buffer and plane `m` information so we can retrieve it again
- * when DQBUF occurs.
- */
- if (!prepared) {
- buffer->buffer.m = b->m;
- if (V4L2_TYPE_IS_MULTIPLANAR(b->type)) {
- if (b->length > VIDEO_MAX_PLANES)
- return -EINVAL;
- for (i = 0; i < b->length; i++)
- buffer->planes[i].m = b->m.planes[i].m;
- }
- }
- old_flags = buffer->buffer.flags;
- buffer->buffer.flags = V4L2_BUF_FLAG_QUEUED;
-
- ret = virtio_media_send_buffer_ioctl(fh, VIDIOC_QBUF, b);
- if (ret) {
- /* Rollback the previous flags as the buffer is not queued. */
- buffer->buffer.flags = old_flags;
- return ret;
- }
-
- queue->queued_bufs += 1;
-
- return 0;
-}
-
-static int virtio_media_dqbuf(struct file *file, void *fh,
- struct v4l2_buffer *b)
-{
- struct video_device *video_dev = video_devdata(file);
- struct virtio_media *vv = to_virtio_media(video_dev);
- struct virtio_media_session *session =
- fh_to_session(file->private_data);
- struct virtio_media_buffer *dqbuf;
- struct virtio_media_queue_state *queue;
- struct list_head *buffer_queue;
- struct v4l2_plane *planes_backup = NULL;
- const bool is_multiplanar = V4L2_TYPE_IS_MULTIPLANAR(b->type);
- int ret;
-
- if (b->type > VIRTIO_MEDIA_LAST_QUEUE)
- return -EINVAL;
-
- queue = &session->queues[b->type];
-
- /*
- * If a buffer with the LAST flag has been returned, subsequent calls to DQBUF
- * must return -EPIPE until the queue is cleared.
- */
- if (queue->is_capture_last)
- return -EPIPE;
-
- buffer_queue = &queue->pending_dqbufs;
-
- if (session->nonblocking_dequeue) {
- if (list_empty(buffer_queue))
- return -EAGAIN;
- } else if (queue->allocated_bufs == 0) {
- return -EINVAL;
- } else if (!queue->streaming) {
- return -EINVAL;
- }
-
- /*
- * vv->lock has been acquired by virtio_media_device_ioctl. Release it
- * while we want to other ioctls for this session can be processed and
- * potentially trigger dqbuf_wait.
- */
- mutex_unlock(&vv->vlock);
- ret = wait_event_interruptible(session->dqbuf_wait,
- !list_empty(buffer_queue));
- mutex_lock(&vv->vlock);
- if (ret)
- return -EINTR;
-
- mutex_lock(&session->queues_lock);
- dqbuf = list_first_entry(buffer_queue, struct virtio_media_buffer,
- list);
- list_del(&dqbuf->list);
- mutex_unlock(&session->queues_lock);
-
- /* Clear the DONE flag as the buffer is now being dequeued. */
- dqbuf->buffer.flags &= ~V4L2_BUF_FLAG_DONE;
-
- if (is_multiplanar) {
- size_t nb_planes = min_t(u32, b->length, VIDEO_MAX_PLANES);
-
- memcpy(b->m.planes, dqbuf->planes,
- nb_planes * sizeof(struct v4l2_plane));
- planes_backup = b->m.planes;
- }
-
- memcpy(b, &dqbuf->buffer, sizeof(*b));
-
- if (is_multiplanar)
- b->m.planes = planes_backup;
-
- if (V4L2_TYPE_IS_CAPTURE(b->type) && b->flags & V4L2_BUF_FLAG_LAST)
- queue->is_capture_last = true;
-
- return 0;
-}
-
-/*
- * s/g_input/output work with an unsigned int - recast this to a u32 so the
- * size is unambiguous.
- */
-
-static int virtio_media_g_input(struct file *file, void *fh, unsigned int *i)
-{
- u32 input;
- int ret;
-
- ret = virtio_media_send_wr_ioctl(fh, VIDIOC_G_INPUT, &input,
- sizeof(input), sizeof(input));
- if (ret)
- return ret;
-
- *i = input;
-
- return 0;
-}
-
-static int virtio_media_s_input(struct file *file, void *fh, unsigned int i)
-{
- u32 input = i;
-
- return virtio_media_send_wr_ioctl(fh, VIDIOC_S_INPUT, &input,
- sizeof(input), sizeof(input));
-}
-
-static int virtio_media_g_output(struct file *file, void *fh, unsigned int *o)
-{
- u32 output;
- int ret;
-
- ret = virtio_media_send_wr_ioctl(fh, VIDIOC_G_OUTPUT, &output,
- sizeof(output), sizeof(output));
- if (ret)
- return ret;
-
- *o = output;
-
- return 0;
-}
-
-static int virtio_media_s_output(struct file *file, void *fh, unsigned int o)
-{
- u32 output = o;
-
- return virtio_media_send_wr_ioctl(fh, VIDIOC_S_OUTPUT, &output,
- sizeof(output), sizeof(output));
-}
-
-/*
- * decoder_cmd can affect the state of the CAPTURE queue.
- */
-
-static int virtio_media_decoder_cmd(struct file *file, void *fh,
- struct v4l2_decoder_cmd *cmd)
-{
- struct virtio_media_session *session = fh_to_session(fh);
- int ret;
-
- ret = virtio_media_send_wr_ioctl(fh, VIDIOC_DECODER_CMD, cmd,
- sizeof(*cmd), sizeof(*cmd));
- if (ret)
- return ret;
-
- /* A START command makes the CAPTURE queue able to dequeue again. */
- if (cmd->cmd == V4L2_DEC_CMD_START) {
- session->queues[V4L2_BUF_TYPE_VIDEO_CAPTURE].is_capture_last =
- false;
- session->queues[V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE]
- .is_capture_last = false;
- }
-
- return 0;
-}
-
-/*
- * s_std doesn't work with a pointer, so we cannot use SIMPLE_W_IOCTL.
- */
-
-static int virtio_media_s_std(struct file *file, void *fh, v4l2_std_id s)
-{
- int ret;
-
- ret = virtio_media_send_w_ioctl(fh, VIDIOC_S_STD, &s, sizeof(s));
- if (ret)
- return ret;
-
- return 0;
-}
-
-const struct v4l2_ioctl_ops virtio_media_ioctl_ops = {
- /* VIDIOC_QUERYCAP handler */
- .vidioc_querycap = virtio_media_querycap,
-
- /* VIDIOC_ENUM_FMT handlers */
- .vidioc_enum_fmt_vid_cap = virtio_media_enum_fmt,
- .vidioc_enum_fmt_vid_overlay = virtio_media_enum_fmt,
- .vidioc_enum_fmt_vid_out = virtio_media_enum_fmt,
- .vidioc_enum_fmt_sdr_cap = virtio_media_enum_fmt,
- .vidioc_enum_fmt_sdr_out = virtio_media_enum_fmt,
- .vidioc_enum_fmt_meta_cap = virtio_media_enum_fmt,
- .vidioc_enum_fmt_meta_out = virtio_media_enum_fmt,
-
- /* VIDIOC_G_FMT handlers */
- .vidioc_g_fmt_vid_cap = virtio_media_g_fmt,
- .vidioc_g_fmt_vid_overlay = virtio_media_g_fmt,
- .vidioc_g_fmt_vid_out = virtio_media_g_fmt,
- .vidioc_g_fmt_vid_out_overlay = virtio_media_g_fmt,
- .vidioc_g_fmt_vbi_cap = virtio_media_g_fmt,
- .vidioc_g_fmt_vbi_out = virtio_media_g_fmt,
- .vidioc_g_fmt_sliced_vbi_cap = virtio_media_g_fmt,
- .vidioc_g_fmt_sliced_vbi_out = virtio_media_g_fmt,
- .vidioc_g_fmt_vid_cap_mplane = virtio_media_g_fmt,
- .vidioc_g_fmt_vid_out_mplane = virtio_media_g_fmt,
- .vidioc_g_fmt_sdr_cap = virtio_media_g_fmt,
- .vidioc_g_fmt_sdr_out = virtio_media_g_fmt,
- .vidioc_g_fmt_meta_cap = virtio_media_g_fmt,
- .vidioc_g_fmt_meta_out = virtio_media_g_fmt,
-
- /* VIDIOC_S_FMT handlers */
- .vidioc_s_fmt_vid_cap = virtio_media_s_fmt,
- .vidioc_s_fmt_vid_overlay = virtio_media_s_fmt,
- .vidioc_s_fmt_vid_out = virtio_media_s_fmt,
- .vidioc_s_fmt_vid_out_overlay = virtio_media_s_fmt,
- .vidioc_s_fmt_vbi_cap = virtio_media_s_fmt,
- .vidioc_s_fmt_vbi_out = virtio_media_s_fmt,
- .vidioc_s_fmt_sliced_vbi_cap = virtio_media_s_fmt,
- .vidioc_s_fmt_sliced_vbi_out = virtio_media_s_fmt,
- .vidioc_s_fmt_vid_cap_mplane = virtio_media_s_fmt,
- .vidioc_s_fmt_vid_out_mplane = virtio_media_s_fmt,
- .vidioc_s_fmt_sdr_cap = virtio_media_s_fmt,
- .vidioc_s_fmt_sdr_out = virtio_media_s_fmt,
- .vidioc_s_fmt_meta_cap = virtio_media_s_fmt,
- .vidioc_s_fmt_meta_out = virtio_media_s_fmt,
-
- /* VIDIOC_TRY_FMT handlers */
- .vidioc_try_fmt_vid_cap = virtio_media_try_fmt,
- .vidioc_try_fmt_vid_overlay = virtio_media_try_fmt,
- .vidioc_try_fmt_vid_out = virtio_media_try_fmt,
- .vidioc_try_fmt_vid_out_overlay = virtio_media_try_fmt,
- .vidioc_try_fmt_vbi_cap = virtio_media_try_fmt,
- .vidioc_try_fmt_vbi_out = virtio_media_try_fmt,
- .vidioc_try_fmt_sliced_vbi_cap = virtio_media_try_fmt,
- .vidioc_try_fmt_sliced_vbi_out = virtio_media_try_fmt,
- .vidioc_try_fmt_vid_cap_mplane = virtio_media_try_fmt,
- .vidioc_try_fmt_vid_out_mplane = virtio_media_try_fmt,
- .vidioc_try_fmt_sdr_cap = virtio_media_try_fmt,
- .vidioc_try_fmt_sdr_out = virtio_media_try_fmt,
- .vidioc_try_fmt_meta_cap = virtio_media_try_fmt,
- .vidioc_try_fmt_meta_out = virtio_media_try_fmt,
-
- /* Buffer handlers */
- .vidioc_reqbufs = virtio_media_reqbufs,
- .vidioc_querybuf = virtio_media_querybuf,
- .vidioc_qbuf = virtio_media_qbuf,
- .vidioc_expbuf = NULL,
- .vidioc_dqbuf = virtio_media_dqbuf,
- .vidioc_create_bufs = virtio_media_create_bufs,
- .vidioc_prepare_buf = virtio_media_prepare_buf,
- /* Overlay interface not supported yet */
- .vidioc_overlay = NULL,
- /* Overlay interface not supported yet */
- .vidioc_g_fbuf = NULL,
- /* Overlay interface not supported yet */
- .vidioc_s_fbuf = NULL,
-
- /* Stream on/off */
- .vidioc_streamon = virtio_media_streamon,
- .vidioc_streamoff = virtio_media_streamoff,
-
- /* Standard handling */
- .vidioc_g_std = virtio_media_g_std,
- .vidioc_s_std = virtio_media_s_std,
- .vidioc_querystd = virtio_media_querystd,
-
- /* Input handling */
- .vidioc_enum_input = virtio_media_enuminput,
- .vidioc_g_input = virtio_media_g_input,
- .vidioc_s_input = virtio_media_s_input,
-
- /* Output handling */
- .vidioc_enum_output = virtio_media_enumoutput,
- .vidioc_g_output = virtio_media_g_output,
- .vidioc_s_output = virtio_media_s_output,
-
- /* Control handling */
- .vidioc_query_ext_ctrl = virtio_media_query_ext_ctrl,
- .vidioc_g_ext_ctrls = virtio_media_g_ext_ctrls,
- .vidioc_s_ext_ctrls = virtio_media_s_ext_ctrls,
- .vidioc_try_ext_ctrls = virtio_media_try_ext_ctrls,
- .vidioc_querymenu = virtio_media_querymenu,
-
- /* Audio ioctls */
- .vidioc_enumaudio = virtio_media_enumaudio,
- .vidioc_g_audio = virtio_media_g_audio,
- .vidioc_s_audio = virtio_media_s_audio,
-
- /* Audio out ioctls */
- .vidioc_enumaudout = virtio_media_enumaudout,
- .vidioc_g_audout = virtio_media_g_audout,
- .vidioc_s_audout = virtio_media_s_audout,
- .vidioc_g_modulator = virtio_media_g_modulator,
- .vidioc_s_modulator = virtio_media_s_modulator,
-
- /* Crop ioctls */
- /* Not directly an ioctl (part of VIDIOC_CROPCAP), so no need to implement */
- .vidioc_g_pixelaspect = NULL,
- .vidioc_g_selection = virtio_media_g_selection,
- .vidioc_s_selection = virtio_media_s_selection,
-
- /* Compression ioctls */
- /* Deprecated in V4L2. */
- .vidioc_g_jpegcomp = NULL,
- /* Deprecated in V4L2. */
- .vidioc_s_jpegcomp = NULL,
- .vidioc_g_enc_index = virtio_media_g_enc_index,
- .vidioc_encoder_cmd = virtio_media_encoder_cmd,
- .vidioc_try_encoder_cmd = virtio_media_try_encoder_cmd,
- .vidioc_decoder_cmd = virtio_media_decoder_cmd,
- .vidioc_try_decoder_cmd = virtio_media_try_decoder_cmd,
-
- /* Stream type-dependent parameter ioctls */
- .vidioc_g_parm = virtio_media_g_parm,
- .vidioc_s_parm = virtio_media_s_parm,
-
- /* Tuner ioctls */
- .vidioc_g_tuner = virtio_media_g_tuner,
- .vidioc_s_tuner = virtio_media_s_tuner,
- .vidioc_g_frequency = virtio_media_g_frequency,
- .vidioc_s_frequency = virtio_media_s_frequency,
- .vidioc_enum_freq_bands = virtio_media_enum_freq_bands,
-
- /* Sliced VBI cap */
- .vidioc_g_sliced_vbi_cap = virtio_media_g_sliced_vbi_cap,
-
- /* Log status ioctl */
- /* Guest-only operation */
- .vidioc_log_status = NULL,
-
- .vidioc_s_hw_freq_seek = virtio_media_s_hw_freq_seek,
-
- .vidioc_enum_framesizes = virtio_media_enum_framesizes,
- .vidioc_enum_frameintervals = virtio_media_enum_frameintervals,
-
- /* DV Timings IOCTLs */
- .vidioc_s_dv_timings = virtio_media_s_dv_timings,
- .vidioc_g_dv_timings = virtio_media_g_dv_timings,
- .vidioc_query_dv_timings = virtio_media_query_dv_timings,
- .vidioc_enum_dv_timings = virtio_media_enum_dv_timings,
- .vidioc_dv_timings_cap = virtio_media_dv_timings_cap,
- .vidioc_g_edid = NULL,
- .vidioc_s_edid = NULL,
-
- .vidioc_subscribe_event = virtio_media_subscribe_event,
- .vidioc_unsubscribe_event = virtio_media_unsubscribe_event,
-
- /* For other private ioctls */
- .vidioc_default = NULL,
-};
-
-long virtio_media_device_ioctl(struct file *file, unsigned int cmd,
- unsigned long arg)
-{
- struct video_device *video_dev = video_devdata(file);
- struct virtio_media *vv = to_virtio_media(video_dev);
- struct v4l2_fh *vfh = NULL;
- struct v4l2_standard standard;
- v4l2_std_id std_id = 0;
- int ret;
-
- if (test_bit(V4L2_FL_USES_V4L2_FH, &video_dev->flags))
- vfh = file->private_data;
-
- mutex_lock(&vv->vlock);
-
- /*
- * We need to handle a few ioctls manually because their result rely on
- * vfd->tvnorms, which is normally updated by the driver as S_INPUT is
- * called. Since we want to just pass these ioctls through, we have to hijack
- * them from here.
- */
- switch (cmd) {
- case VIDIOC_S_STD:
- ret = copy_from_user(&std_id, (void __user *)arg,
- sizeof(std_id));
- if (ret) {
- ret = -EINVAL;
- break;
- }
- ret = virtio_media_s_std(file, vfh, std_id);
- break;
- case VIDIOC_ENUMSTD:
- ret = copy_from_user(&standard, (void __user *)arg,
- sizeof(standard));
- if (ret) {
- ret = -EINVAL;
- break;
- }
- ret = virtio_media_enumstd(file, vfh, &standard);
- if (ret)
- break;
- ret = copy_to_user((void __user *)arg, &standard,
- sizeof(standard));
- if (ret)
- ret = -EINVAL;
- break;
- case VIDIOC_QUERYSTD:
- ret = virtio_media_querystd(file, vfh, &std_id);
- if (ret)
- break;
- ret = copy_to_user((void __user *)arg, &std_id, sizeof(std_id));
- if (ret)
- ret = -EINVAL;
- break;
- default:
- ret = video_ioctl2(file, cmd, arg);
- break;
- }
-
- mutex_unlock(&vv->vlock);
-
- return ret;
-}
diff --git a/drivers/net/ethernet/airoha/airoha_ppe.c b/drivers/net/ethernet/airoha/airoha_ppe.c
index c354d536bc66..47411d2cbd28 100644
--- a/drivers/net/ethernet/airoha/airoha_ppe.c
+++ b/drivers/net/ethernet/airoha/airoha_ppe.c
@@ -508,9 +508,11 @@ static void airoha_ppe_foe_flow_stats_update(struct airoha_ppe *ppe,
FIELD_PREP(AIROHA_FOE_IB2_NBQ, nbq);
}
-struct airoha_foe_entry *airoha_ppe_foe_get_entry(struct airoha_ppe *ppe,
- u32 hash)
+static struct airoha_foe_entry *
+airoha_ppe_foe_get_entry_locked(struct airoha_ppe *ppe, u32 hash)
{
+ lockdep_assert_held(&ppe_lock);
+
if (hash < PPE_SRAM_NUM_ENTRIES) {
u32 *hwe = ppe->foe + hash * sizeof(struct airoha_foe_entry);
struct airoha_eth *eth = ppe->eth;
@@ -537,6 +539,18 @@ struct airoha_foe_entry *airoha_ppe_foe_get_entry(struct airoha_ppe *ppe,
return ppe->foe + hash * sizeof(struct airoha_foe_entry);
}
+struct airoha_foe_entry *airoha_ppe_foe_get_entry(struct airoha_ppe *ppe,
+ u32 hash)
+{
+ struct airoha_foe_entry *hwe;
+
+ spin_lock_bh(&ppe_lock);
+ hwe = airoha_ppe_foe_get_entry_locked(ppe, hash);
+ spin_unlock_bh(&ppe_lock);
+
+ return hwe;
+}
+
static bool airoha_ppe_foe_compare_entry(struct airoha_flow_table_entry *e,
struct airoha_foe_entry *hwe)
{
@@ -651,7 +665,7 @@ airoha_ppe_foe_commit_subflow_entry(struct airoha_ppe *ppe,
struct airoha_flow_table_entry *f;
int type;
- hwe_p = airoha_ppe_foe_get_entry(ppe, hash);
+ hwe_p = airoha_ppe_foe_get_entry_locked(ppe, hash);
if (!hwe_p)
return -EINVAL;
@@ -703,7 +717,7 @@ static void airoha_ppe_foe_insert_entry(struct airoha_ppe *ppe,
spin_lock_bh(&ppe_lock);
- hwe = airoha_ppe_foe_get_entry(ppe, hash);
+ hwe = airoha_ppe_foe_get_entry_locked(ppe, hash);
if (!hwe)
goto unlock;
@@ -818,7 +832,7 @@ airoha_ppe_foe_flow_l2_entry_update(struct airoha_ppe *ppe,
u32 ib1, state;
int idle;
- hwe = airoha_ppe_foe_get_entry(ppe, iter->hash);
+ hwe = airoha_ppe_foe_get_entry_locked(ppe, iter->hash);
if (!hwe)
continue;
@@ -855,7 +869,7 @@ static void airoha_ppe_foe_flow_entry_update(struct airoha_ppe *ppe,
if (e->hash == 0xffff)
goto unlock;
- hwe_p = airoha_ppe_foe_get_entry(ppe, e->hash);
+ hwe_p = airoha_ppe_foe_get_entry_locked(ppe, e->hash);
if (!hwe_p)
goto unlock;
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/en_rx.c b/drivers/net/ethernet/mellanox/mlx5/core/en_rx.c
index 218b1a09534c..b8c609d91d11 100644
--- a/drivers/net/ethernet/mellanox/mlx5/core/en_rx.c
+++ b/drivers/net/ethernet/mellanox/mlx5/core/en_rx.c
@@ -1574,6 +1574,7 @@ static inline void mlx5e_build_rx_skb(struct mlx5_cqe64 *cqe,
unsigned int hdrlen = mlx5e_lro_update_hdr(skb, cqe, cqe_bcnt);
skb_shinfo(skb)->gso_size = DIV_ROUND_UP(cqe_bcnt - hdrlen, lro_num_seg);
+ skb_shinfo(skb)->gso_segs = lro_num_seg;
/* Subtract one since we already counted this as one
* "regular" packet in mlx5e_complete_rx_cqe()
*/
diff --git a/drivers/net/ethernet/sfc/tc_encap_actions.c b/drivers/net/ethernet/sfc/tc_encap_actions.c
index 2258f854e5be..e872f926e438 100644
--- a/drivers/net/ethernet/sfc/tc_encap_actions.c
+++ b/drivers/net/ethernet/sfc/tc_encap_actions.c
@@ -442,7 +442,7 @@ static void efx_tc_update_encap(struct efx_nic *efx,
rule = container_of(acts, struct efx_tc_flow_rule, acts);
if (rule->fallback)
fallback = rule->fallback;
- else /* fallback: deliver to PF */
+ else /* fallback of the fallback: deliver to PF */
fallback = &efx->tc->facts.pf;
rc = efx_mae_update_rule(efx, fallback->fw_id,
rule->fw_id);
diff --git a/drivers/net/mdio/mdio-bcm-unimac.c b/drivers/net/mdio/mdio-bcm-unimac.c
index b6e30bdf5325..7baab230008a 100644
--- a/drivers/net/mdio/mdio-bcm-unimac.c
+++ b/drivers/net/mdio/mdio-bcm-unimac.c
@@ -209,10 +209,9 @@ static int unimac_mdio_clk_set(struct unimac_mdio_priv *priv)
if (ret)
return ret;
- if (!priv->clk)
+ rate = clk_get_rate(priv->clk);
+ if (!rate)
rate = 250000000;
- else
- rate = clk_get_rate(priv->clk);
div = (rate / (2 * priv->clk_freq)) - 1;
if (div & ~MDIO_CLK_DIV_MASK) {
diff --git a/drivers/rtc/rtc-ds1307.c b/drivers/rtc/rtc-ds1307.c
index ce0994d9219a..7205c59ff729 100644
--- a/drivers/rtc/rtc-ds1307.c
+++ b/drivers/rtc/rtc-ds1307.c
@@ -1467,16 +1467,21 @@ static unsigned long ds3231_clk_sqw_recalc_rate(struct clk_hw *hw,
return ds3231_clk_sqw_rates[rate_sel];
}
-static long ds3231_clk_sqw_round_rate(struct clk_hw *hw, unsigned long rate,
- unsigned long *prate)
+static int ds3231_clk_sqw_determine_rate(struct clk_hw *hw,
+ struct clk_rate_request *req)
{
int i;
for (i = ARRAY_SIZE(ds3231_clk_sqw_rates) - 1; i >= 0; i--) {
- if (ds3231_clk_sqw_rates[i] <= rate)
- return ds3231_clk_sqw_rates[i];
+ if (ds3231_clk_sqw_rates[i] <= req->rate) {
+ req->rate = ds3231_clk_sqw_rates[i];
+
+ return 0;
+ }
}
+ req->rate = ds3231_clk_sqw_rates[ARRAY_SIZE(ds3231_clk_sqw_rates) - 1];
+
return 0;
}
@@ -1536,7 +1541,7 @@ static const struct clk_ops ds3231_clk_sqw_ops = {
.unprepare = ds3231_clk_sqw_unprepare,
.is_prepared = ds3231_clk_sqw_is_prepared,
.recalc_rate = ds3231_clk_sqw_recalc_rate,
- .round_rate = ds3231_clk_sqw_round_rate,
+ .determine_rate = ds3231_clk_sqw_determine_rate,
.set_rate = ds3231_clk_sqw_set_rate,
};
diff --git a/drivers/rtc/rtc-ds1685.c b/drivers/rtc/rtc-ds1685.c
index 38e25f63597a..97423f1d0361 100644
--- a/drivers/rtc/rtc-ds1685.c
+++ b/drivers/rtc/rtc-ds1685.c
@@ -3,7 +3,7 @@
* An rtc driver for the Dallas/Maxim DS1685/DS1687 and related real-time
* chips.
*
- * Copyright (C) 2011-2014 Joshua Kinard <kumba@gentoo.org>.
+ * Copyright (C) 2011-2014 Joshua Kinard <linux@kumba.dev>.
* Copyright (C) 2009 Matthias Fuchs <matthias.fuchs@esd-electronics.com>.
*
* References:
@@ -1436,7 +1436,7 @@ EXPORT_SYMBOL_GPL(ds1685_rtc_poweroff);
/* ----------------------------------------------------------------------- */
-MODULE_AUTHOR("Joshua Kinard <kumba@gentoo.org>");
+MODULE_AUTHOR("Joshua Kinard <linux@kumba.dev>");
MODULE_AUTHOR("Matthias Fuchs <matthias.fuchs@esd-electronics.com>");
MODULE_DESCRIPTION("Dallas/Maxim DS1685/DS1687-series RTC driver");
MODULE_LICENSE("GPL");
diff --git a/drivers/rtc/rtc-hym8563.c b/drivers/rtc/rtc-hym8563.c
index 63f11ea3589d..7a170c0f9710 100644
--- a/drivers/rtc/rtc-hym8563.c
+++ b/drivers/rtc/rtc-hym8563.c
@@ -285,14 +285,19 @@ static unsigned long hym8563_clkout_recalc_rate(struct clk_hw *hw,
return clkout_rates[ret];
}
-static long hym8563_clkout_round_rate(struct clk_hw *hw, unsigned long rate,
- unsigned long *prate)
+static int hym8563_clkout_determine_rate(struct clk_hw *hw,
+ struct clk_rate_request *req)
{
int i;
for (i = 0; i < ARRAY_SIZE(clkout_rates); i++)
- if (clkout_rates[i] <= rate)
- return clkout_rates[i];
+ if (clkout_rates[i] <= req->rate) {
+ req->rate = clkout_rates[i];
+
+ return 0;
+ }
+
+ req->rate = clkout_rates[0];
return 0;
}
@@ -363,7 +368,7 @@ static const struct clk_ops hym8563_clkout_ops = {
.unprepare = hym8563_clkout_unprepare,
.is_prepared = hym8563_clkout_is_prepared,
.recalc_rate = hym8563_clkout_recalc_rate,
- .round_rate = hym8563_clkout_round_rate,
+ .determine_rate = hym8563_clkout_determine_rate,
.set_rate = hym8563_clkout_set_rate,
};
diff --git a/drivers/rtc/rtc-m41t80.c b/drivers/rtc/rtc-m41t80.c
index 869358e9305b..740cab013f59 100644
--- a/drivers/rtc/rtc-m41t80.c
+++ b/drivers/rtc/rtc-m41t80.c
@@ -484,16 +484,17 @@ static unsigned long m41t80_sqw_recalc_rate(struct clk_hw *hw,
return sqw_to_m41t80_data(hw)->freq;
}
-static long m41t80_sqw_round_rate(struct clk_hw *hw, unsigned long rate,
- unsigned long *prate)
+static int m41t80_sqw_determine_rate(struct clk_hw *hw,
+ struct clk_rate_request *req)
{
- if (rate >= M41T80_SQW_MAX_FREQ)
- return M41T80_SQW_MAX_FREQ;
- if (rate >= M41T80_SQW_MAX_FREQ / 4)
- return M41T80_SQW_MAX_FREQ / 4;
- if (!rate)
- return 0;
- return 1 << ilog2(rate);
+ if (req->rate >= M41T80_SQW_MAX_FREQ)
+ req->rate = M41T80_SQW_MAX_FREQ;
+ else if (req->rate >= M41T80_SQW_MAX_FREQ / 4)
+ req->rate = M41T80_SQW_MAX_FREQ / 4;
+ else if (req->rate)
+ req->rate = 1 << ilog2(req->rate);
+
+ return 0;
}
static int m41t80_sqw_set_rate(struct clk_hw *hw, unsigned long rate,
@@ -564,7 +565,7 @@ static const struct clk_ops m41t80_sqw_ops = {
.unprepare = m41t80_sqw_unprepare,
.is_prepared = m41t80_sqw_is_prepared,
.recalc_rate = m41t80_sqw_recalc_rate,
- .round_rate = m41t80_sqw_round_rate,
+ .determine_rate = m41t80_sqw_determine_rate,
.set_rate = m41t80_sqw_set_rate,
};
diff --git a/drivers/rtc/rtc-max31335.c b/drivers/rtc/rtc-max31335.c
index a7bb37aaab9e..dfb5bad3a369 100644
--- a/drivers/rtc/rtc-max31335.c
+++ b/drivers/rtc/rtc-max31335.c
@@ -497,15 +497,17 @@ static unsigned long max31335_clkout_recalc_rate(struct clk_hw *hw,
return max31335_clkout_freq[reg & freq_mask];
}
-static long max31335_clkout_round_rate(struct clk_hw *hw, unsigned long rate,
- unsigned long *prate)
+static int max31335_clkout_determine_rate(struct clk_hw *hw,
+ struct clk_rate_request *req)
{
int index;
- index = find_closest(rate, max31335_clkout_freq,
+ index = find_closest(req->rate, max31335_clkout_freq,
ARRAY_SIZE(max31335_clkout_freq));
- return max31335_clkout_freq[index];
+ req->rate = max31335_clkout_freq[index];
+
+ return 0;
}
static int max31335_clkout_set_rate(struct clk_hw *hw, unsigned long rate,
@@ -554,7 +556,7 @@ static int max31335_clkout_is_enabled(struct clk_hw *hw)
static const struct clk_ops max31335_clkout_ops = {
.recalc_rate = max31335_clkout_recalc_rate,
- .round_rate = max31335_clkout_round_rate,
+ .determine_rate = max31335_clkout_determine_rate,
.set_rate = max31335_clkout_set_rate,
.enable = max31335_clkout_enable,
.disable = max31335_clkout_disable,
diff --git a/drivers/rtc/rtc-nct3018y.c b/drivers/rtc/rtc-nct3018y.c
index 76c5f464b2da..cd4b1db902e9 100644
--- a/drivers/rtc/rtc-nct3018y.c
+++ b/drivers/rtc/rtc-nct3018y.c
@@ -367,14 +367,19 @@ static unsigned long nct3018y_clkout_recalc_rate(struct clk_hw *hw,
return clkout_rates[flags];
}
-static long nct3018y_clkout_round_rate(struct clk_hw *hw, unsigned long rate,
- unsigned long *prate)
+static int nct3018y_clkout_determine_rate(struct clk_hw *hw,
+ struct clk_rate_request *req)
{
int i;
for (i = 0; i < ARRAY_SIZE(clkout_rates); i++)
- if (clkout_rates[i] <= rate)
- return clkout_rates[i];
+ if (clkout_rates[i] <= req->rate) {
+ req->rate = clkout_rates[i];
+
+ return 0;
+ }
+
+ req->rate = clkout_rates[0];
return 0;
}
@@ -446,7 +451,7 @@ static const struct clk_ops nct3018y_clkout_ops = {
.unprepare = nct3018y_clkout_unprepare,
.is_prepared = nct3018y_clkout_is_prepared,
.recalc_rate = nct3018y_clkout_recalc_rate,
- .round_rate = nct3018y_clkout_round_rate,
+ .determine_rate = nct3018y_clkout_determine_rate,
.set_rate = nct3018y_clkout_set_rate,
};
diff --git a/drivers/rtc/rtc-pcf85063.c b/drivers/rtc/rtc-pcf85063.c
index e3b58cdb1eda..f643e0bd7351 100644
--- a/drivers/rtc/rtc-pcf85063.c
+++ b/drivers/rtc/rtc-pcf85063.c
@@ -405,14 +405,19 @@ static unsigned long pcf85063_clkout_recalc_rate(struct clk_hw *hw,
return clkout_rates[buf];
}
-static long pcf85063_clkout_round_rate(struct clk_hw *hw, unsigned long rate,
- unsigned long *prate)
+static int pcf85063_clkout_determine_rate(struct clk_hw *hw,
+ struct clk_rate_request *req)
{
int i;
for (i = 0; i < ARRAY_SIZE(clkout_rates); i++)
- if (clkout_rates[i] <= rate)
- return clkout_rates[i];
+ if (clkout_rates[i] <= req->rate) {
+ req->rate = clkout_rates[i];
+
+ return 0;
+ }
+
+ req->rate = clkout_rates[0];
return 0;
}
@@ -486,7 +491,7 @@ static const struct clk_ops pcf85063_clkout_ops = {
.unprepare = pcf85063_clkout_unprepare,
.is_prepared = pcf85063_clkout_is_prepared,
.recalc_rate = pcf85063_clkout_recalc_rate,
- .round_rate = pcf85063_clkout_round_rate,
+ .determine_rate = pcf85063_clkout_determine_rate,
.set_rate = pcf85063_clkout_set_rate,
};
diff --git a/drivers/rtc/rtc-pcf8563.c b/drivers/rtc/rtc-pcf8563.c
index b2611697fa5e..4e61011fb7a9 100644
--- a/drivers/rtc/rtc-pcf8563.c
+++ b/drivers/rtc/rtc-pcf8563.c
@@ -330,14 +330,19 @@ static unsigned long pcf8563_clkout_recalc_rate(struct clk_hw *hw,
return clkout_rates[buf];
}
-static long pcf8563_clkout_round_rate(struct clk_hw *hw, unsigned long rate,
- unsigned long *prate)
+static int pcf8563_clkout_determine_rate(struct clk_hw *hw,
+ struct clk_rate_request *req)
{
int i;
for (i = 0; i < ARRAY_SIZE(clkout_rates); i++)
- if (clkout_rates[i] <= rate)
- return clkout_rates[i];
+ if (clkout_rates[i] <= req->rate) {
+ req->rate = clkout_rates[i];
+
+ return 0;
+ }
+
+ req->rate = clkout_rates[0];
return 0;
}
@@ -413,7 +418,7 @@ static const struct clk_ops pcf8563_clkout_ops = {
.unprepare = pcf8563_clkout_unprepare,
.is_prepared = pcf8563_clkout_is_prepared,
.recalc_rate = pcf8563_clkout_recalc_rate,
- .round_rate = pcf8563_clkout_round_rate,
+ .determine_rate = pcf8563_clkout_determine_rate,
.set_rate = pcf8563_clkout_set_rate,
};
diff --git a/drivers/rtc/rtc-rv3028.c b/drivers/rtc/rtc-rv3028.c
index 868d1b1eb0f4..c2a531f0e125 100644
--- a/drivers/rtc/rtc-rv3028.c
+++ b/drivers/rtc/rtc-rv3028.c
@@ -731,14 +731,19 @@ static unsigned long rv3028_clkout_recalc_rate(struct clk_hw *hw,
return clkout_rates[clkout];
}
-static long rv3028_clkout_round_rate(struct clk_hw *hw, unsigned long rate,
- unsigned long *prate)
+static int rv3028_clkout_determine_rate(struct clk_hw *hw,
+ struct clk_rate_request *req)
{
int i;
for (i = 0; i < ARRAY_SIZE(clkout_rates); i++)
- if (clkout_rates[i] <= rate)
- return clkout_rates[i];
+ if (clkout_rates[i] <= req->rate) {
+ req->rate = clkout_rates[i];
+
+ return 0;
+ }
+
+ req->rate = clkout_rates[0];
return 0;
}
@@ -802,7 +807,7 @@ static const struct clk_ops rv3028_clkout_ops = {
.unprepare = rv3028_clkout_unprepare,
.is_prepared = rv3028_clkout_is_prepared,
.recalc_rate = rv3028_clkout_recalc_rate,
- .round_rate = rv3028_clkout_round_rate,
+ .determine_rate = rv3028_clkout_determine_rate,
.set_rate = rv3028_clkout_set_rate,
};
diff --git a/drivers/rtc/rtc-rv3032.c b/drivers/rtc/rtc-rv3032.c
index 2c6a8918acba..b8376bd1d905 100644
--- a/drivers/rtc/rtc-rv3032.c
+++ b/drivers/rtc/rtc-rv3032.c
@@ -646,19 +646,24 @@ static unsigned long rv3032_clkout_recalc_rate(struct clk_hw *hw,
return clkout_xtal_rates[FIELD_GET(RV3032_CLKOUT2_FD_MSK, clkout)];
}
-static long rv3032_clkout_round_rate(struct clk_hw *hw, unsigned long rate,
- unsigned long *prate)
+static int rv3032_clkout_determine_rate(struct clk_hw *hw,
+ struct clk_rate_request *req)
{
int i, hfd;
- if (rate < RV3032_HFD_STEP)
+ if (req->rate < RV3032_HFD_STEP)
for (i = 0; i < ARRAY_SIZE(clkout_xtal_rates); i++)
- if (clkout_xtal_rates[i] <= rate)
- return clkout_xtal_rates[i];
+ if (clkout_xtal_rates[i] <= req->rate) {
+ req->rate = clkout_xtal_rates[i];
- hfd = DIV_ROUND_CLOSEST(rate, RV3032_HFD_STEP);
+ return 0;
+ }
+
+ hfd = DIV_ROUND_CLOSEST(req->rate, RV3032_HFD_STEP);
- return RV3032_HFD_STEP * clamp(hfd, 0, 8192);
+ req->rate = RV3032_HFD_STEP * clamp(hfd, 0, 8192);
+
+ return 0;
}
static int rv3032_clkout_set_rate(struct clk_hw *hw, unsigned long rate,
@@ -738,7 +743,7 @@ static const struct clk_ops rv3032_clkout_ops = {
.unprepare = rv3032_clkout_unprepare,
.is_prepared = rv3032_clkout_is_prepared,
.recalc_rate = rv3032_clkout_recalc_rate,
- .round_rate = rv3032_clkout_round_rate,
+ .determine_rate = rv3032_clkout_determine_rate,
.set_rate = rv3032_clkout_set_rate,
};
diff --git a/drivers/tee/optee/core.c b/drivers/tee/optee/core.c
index c75fddc83576..ce44e3498d37 100644
--- a/drivers/tee/optee/core.c
+++ b/drivers/tee/optee/core.c
@@ -72,7 +72,7 @@ static ssize_t rpmb_routing_model_show(struct device *dev,
else
s = "user";
- return scnprintf(buf, PAGE_SIZE, "%s\n", s);
+ return sysfs_emit(buf, "%s\n", s);
}
static DEVICE_ATTR_RO(rpmb_routing_model);
diff --git a/drivers/tee/tee_core.c b/drivers/tee/tee_core.c
index acc7998758ad..944f913f8592 100644
--- a/drivers/tee/tee_core.c
+++ b/drivers/tee/tee_core.c
@@ -977,7 +977,7 @@ static ssize_t implementation_id_show(struct device *dev,
struct tee_ioctl_version_data vers;
teedev->desc->ops->get_version(teedev, &vers);
- return scnprintf(buf, PAGE_SIZE, "%d\n", vers.impl_id);
+ return sysfs_emit(buf, "%d\n", vers.impl_id);
}
static DEVICE_ATTR_RO(implementation_id);
diff --git a/drivers/tee/tee_shm.c b/drivers/tee/tee_shm.c
index daf6e5cfd59a..2a7d253d9c55 100644
--- a/drivers/tee/tee_shm.c
+++ b/drivers/tee/tee_shm.c
@@ -230,7 +230,7 @@ int tee_dyn_shm_alloc_helper(struct tee_shm *shm, size_t size, size_t align,
pages = kcalloc(nr_pages, sizeof(*pages), GFP_KERNEL);
if (!pages) {
rc = -ENOMEM;
- goto err;
+ goto err_pages;
}
for (i = 0; i < nr_pages; i++)
@@ -243,11 +243,13 @@ int tee_dyn_shm_alloc_helper(struct tee_shm *shm, size_t size, size_t align,
rc = shm_register(shm->ctx, shm, pages, nr_pages,
(unsigned long)shm->kaddr);
if (rc)
- goto err;
+ goto err_kfree;
}
return 0;
-err:
+err_kfree:
+ kfree(pages);
+err_pages:
free_pages_exact(shm->kaddr, shm->size);
shm->kaddr = NULL;
return rc;
@@ -560,9 +562,13 @@ EXPORT_SYMBOL_GPL(tee_shm_get_from_id);
*/
void tee_shm_put(struct tee_shm *shm)
{
- struct tee_device *teedev = shm->ctx->teedev;
+ struct tee_device *teedev;
bool do_release = false;
+ if (!shm || !shm->ctx || !shm->ctx->teedev)
+ return;
+
+ teedev = shm->ctx->teedev;
mutex_lock(&teedev->mutex);
if (refcount_dec_and_test(&shm->refcount)) {
/*
diff --git a/drivers/vhost/vhost.c b/drivers/vhost/vhost.c
index 23286e4d7b49..8570fdf2e14a 100644
--- a/drivers/vhost/vhost.c
+++ b/drivers/vhost/vhost.c
@@ -615,6 +615,7 @@ void vhost_dev_init(struct vhost_dev *dev,
vq->log = NULL;
vq->indirect = NULL;
vq->heads = NULL;
+ vq->nheads = NULL;
vq->dev = dev;
mutex_init(&vq->mutex);
vhost_vq_reset(dev, vq);
diff --git a/drivers/video/console/vgacon.c b/drivers/video/console/vgacon.c
index f9cdbf8c53e3..37bd18730fe0 100644
--- a/drivers/video/console/vgacon.c
+++ b/drivers/video/console/vgacon.c
@@ -1168,7 +1168,7 @@ static bool vgacon_scroll(struct vc_data *c, unsigned int t, unsigned int b,
c->vc_screenbuf_size - delta);
c->vc_origin = vga_vram_end - c->vc_screenbuf_size;
vga_rolled_over = 0;
- } else if (oldo - delta >= (unsigned long)c->vc_screenbuf)
+ } else
c->vc_origin -= delta;
c->vc_scr_end = c->vc_origin + c->vc_screenbuf_size;
scr_memsetw((u16 *) (c->vc_origin), c->vc_video_erase_char,
diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c
index eabbc4bd7cf6..55f5731e94c3 100644
--- a/drivers/video/fbdev/core/fbcon.c
+++ b/drivers/video/fbdev/core/fbcon.c
@@ -837,7 +837,8 @@ static void con2fb_init_display(struct vc_data *vc, struct fb_info *info,
fg_vc->vc_rows);
}
- update_screen(vc_cons[fg_console].d);
+ if (fg_console != unit)
+ update_screen(vc_cons[fg_console].d);
}
/**
@@ -1375,6 +1376,7 @@ static void fbcon_set_disp(struct fb_info *info, struct fb_var_screeninfo *var,
struct vc_data *svc;
struct fbcon_ops *ops = info->fbcon_par;
int rows, cols;
+ unsigned long ret = 0;
p = &fb_display[unit];
@@ -1425,11 +1427,10 @@ static void fbcon_set_disp(struct fb_info *info, struct fb_var_screeninfo *var,
rows = FBCON_SWAP(ops->rotate, info->var.yres, info->var.xres);
cols /= vc->vc_font.width;
rows /= vc->vc_font.height;
- vc_resize(vc, cols, rows);
+ ret = vc_resize(vc, cols, rows);
- if (con_is_visible(vc)) {
+ if (con_is_visible(vc) && !ret)
update_screen(vc);
- }
}
static __inline__ void ywrap_up(struct vc_data *vc, int count)
diff --git a/drivers/virtio/virtio_ring.c b/drivers/virtio/virtio_ring.c
index 98e990ee2073..c147145a6593 100644
--- a/drivers/virtio/virtio_ring.c
+++ b/drivers/virtio/virtio_ring.c
@@ -1005,7 +1005,7 @@ static void virtqueue_vring_init_split(struct vring_virtqueue_split *vring_split
}
}
-static void virtqueue_reset_split(struct vring_virtqueue *vq)
+static void virtqueue_reinit_split(struct vring_virtqueue *vq)
{
int num;
@@ -1248,7 +1248,7 @@ static int virtqueue_resize_split(struct virtqueue *_vq, u32 num)
err_state_extra:
vring_free_split(&vring_split, vdev, vring_dma_dev(vq));
err:
- virtqueue_reset_split(vq);
+ virtqueue_reinit_split(vq);
return -ENOMEM;
}
@@ -2092,7 +2092,7 @@ static void virtqueue_vring_attach_packed(struct vring_virtqueue *vq,
vq->free_head = 0;
}
-static void virtqueue_reset_packed(struct vring_virtqueue *vq)
+static void virtqueue_reinit_packed(struct vring_virtqueue *vq)
{
memset(vq->packed.vring.device, 0, vq->packed.event_size_in_bytes);
memset(vq->packed.vring.driver, 0, vq->packed.event_size_in_bytes);
@@ -2219,7 +2219,7 @@ static int virtqueue_resize_packed(struct virtqueue *_vq, u32 num)
err_state_extra:
vring_free_packed(&vring_packed, vdev, vring_dma_dev(vq));
err_ring:
- virtqueue_reset_packed(vq);
+ virtqueue_reinit_packed(vq);
return -ENOMEM;
}
@@ -2860,9 +2860,9 @@ int virtqueue_reset(struct virtqueue *_vq,
recycle_done(_vq);
if (vq->packed_ring)
- virtqueue_reset_packed(vq);
+ virtqueue_reinit_packed(vq);
else
- virtqueue_reset_split(vq);
+ virtqueue_reinit_split(vq);
return virtqueue_enable_after_reset(_vq);
}
diff --git a/fs/bcachefs/alloc_background.c b/fs/bcachefs/alloc_background.c
index 7db904c7a7e8..3fc728efbf5c 100644
--- a/fs/bcachefs/alloc_background.c
+++ b/fs/bcachefs/alloc_background.c
@@ -2104,44 +2104,46 @@ static int invalidate_one_bucket(struct btree_trans *trans,
if (bch2_bucket_is_open_safe(c, bucket.inode, bucket.offset))
return 0;
- CLASS(btree_iter, alloc_iter)(trans, BTREE_ID_alloc, bucket, BTREE_ITER_cached);
- struct bkey_s_c alloc_k = bch2_btree_iter_peek_slot(&alloc_iter);
- ret = bkey_err(alloc_k);
- if (ret)
- return ret;
+ {
+ CLASS(btree_iter, alloc_iter)(trans, BTREE_ID_alloc, bucket, BTREE_ITER_cached);
+ struct bkey_s_c alloc_k = bch2_btree_iter_peek_slot(&alloc_iter);
+ ret = bkey_err(alloc_k);
+ if (ret)
+ return ret;
- struct bch_alloc_v4 a_convert;
- const struct bch_alloc_v4 *a = bch2_alloc_to_v4(alloc_k, &a_convert);
+ struct bch_alloc_v4 a_convert;
+ const struct bch_alloc_v4 *a = bch2_alloc_to_v4(alloc_k, &a_convert);
- /* We expect harmless races here due to the btree write buffer: */
- if (lru_pos_time(lru_iter->pos) != alloc_lru_idx_read(*a))
- return 0;
+ /* We expect harmless races here due to the btree write buffer: */
+ if (lru_pos_time(lru_iter->pos) != alloc_lru_idx_read(*a))
+ return 0;
- /*
- * Impossible since alloc_lru_idx_read() only returns nonzero if the
- * bucket is supposed to be on the cached bucket LRU (i.e.
- * BCH_DATA_cached)
- *
- * bch2_lru_validate() also disallows lru keys with lru_pos_time() == 0
- */
- BUG_ON(a->data_type != BCH_DATA_cached);
- BUG_ON(a->dirty_sectors);
+ /*
+ * Impossible since alloc_lru_idx_read() only returns nonzero if the
+ * bucket is supposed to be on the cached bucket LRU (i.e.
+ * BCH_DATA_cached)
+ *
+ * bch2_lru_validate() also disallows lru keys with lru_pos_time() == 0
+ */
+ BUG_ON(a->data_type != BCH_DATA_cached);
+ BUG_ON(a->dirty_sectors);
- if (!a->cached_sectors) {
- bch2_check_bucket_backpointer_mismatch(trans, ca, bucket.offset,
- true, last_flushed);
- return 0;
- }
+ if (!a->cached_sectors) {
+ bch2_check_bucket_backpointer_mismatch(trans, ca, bucket.offset,
+ true, last_flushed);
+ return 0;
+ }
- unsigned cached_sectors = a->cached_sectors;
- u8 gen = a->gen;
+ unsigned cached_sectors = a->cached_sectors;
+ u8 gen = a->gen;
- ret = invalidate_one_bucket_by_bps(trans, ca, bucket, gen, last_flushed);
- if (ret)
- return ret;
+ ret = invalidate_one_bucket_by_bps(trans, ca, bucket, gen, last_flushed);
+ if (ret)
+ return ret;
- trace_and_count(c, bucket_invalidate, c, bucket.inode, bucket.offset, cached_sectors);
- --*nr_to_invalidate;
+ trace_and_count(c, bucket_invalidate, c, bucket.inode, bucket.offset, cached_sectors);
+ --*nr_to_invalidate;
+ }
fsck_err:
return ret;
}
diff --git a/fs/bcachefs/backpointers.c b/fs/bcachefs/backpointers.c
index 1aab9a63d0cb..45d3db41225a 100644
--- a/fs/bcachefs/backpointers.c
+++ b/fs/bcachefs/backpointers.c
@@ -395,22 +395,24 @@ static int bch2_check_backpointer_has_valid_bucket(struct btree_trans *trans, st
return ret;
}
- CLASS(btree_iter, alloc_iter)(trans, BTREE_ID_alloc, bucket, 0);
- struct bkey_s_c alloc_k = bch2_btree_iter_peek_slot(&alloc_iter);
- ret = bkey_err(alloc_k);
- if (ret)
- return ret;
-
- if (alloc_k.k->type != KEY_TYPE_alloc_v4) {
- ret = bch2_backpointers_maybe_flush(trans, k, last_flushed);
+ {
+ CLASS(btree_iter, alloc_iter)(trans, BTREE_ID_alloc, bucket, 0);
+ struct bkey_s_c alloc_k = bch2_btree_iter_peek_slot(&alloc_iter);
+ ret = bkey_err(alloc_k);
if (ret)
return ret;
- if (fsck_err(trans, backpointer_to_missing_alloc,
- "backpointer for nonexistent alloc key: %llu:%llu:0\n%s",
- alloc_iter.pos.inode, alloc_iter.pos.offset,
- (bch2_bkey_val_to_text(&buf, c, k), buf.buf)))
- ret = bch2_backpointer_del(trans, k.k->p);
+ if (alloc_k.k->type != KEY_TYPE_alloc_v4) {
+ ret = bch2_backpointers_maybe_flush(trans, k, last_flushed);
+ if (ret)
+ return ret;
+
+ if (fsck_err(trans, backpointer_to_missing_alloc,
+ "backpointer for nonexistent alloc key: %llu:%llu:0\n%s",
+ alloc_iter.pos.inode, alloc_iter.pos.offset,
+ (bch2_bkey_val_to_text(&buf, c, k), buf.buf)))
+ ret = bch2_backpointer_del(trans, k.k->p);
+ }
}
fsck_err:
return ret;
diff --git a/fs/bcachefs/bcachefs.h b/fs/bcachefs/bcachefs.h
index 45c15bdaa6f4..16d08dfb5f19 100644
--- a/fs/bcachefs/bcachefs.h
+++ b/fs/bcachefs/bcachefs.h
@@ -386,14 +386,6 @@ do { \
##__VA_ARGS__, bch2_err_str(_ret)); \
} while (0)
-static inline int __bch2_err_trace(struct bch_fs *c, int err)
-{
- trace_error_throw(c, err, _THIS_IP_);
- return err;
-}
-
-#define bch_err_throw(_c, _err) __bch2_err_trace(_c, -BCH_ERR_##_err)
-
/* Parameters that are useful for debugging, but should always be compiled in: */
#define BCH_DEBUG_PARAMS_ALWAYS() \
BCH_DEBUG_PARAM(key_merging_disabled, \
@@ -845,8 +837,8 @@ struct bch_fs {
unsigned long errors_silent[BITS_TO_LONGS(BCH_FSCK_ERR_MAX)];
u64 btrees_lost_data;
} sb;
- DARRAY(enum bcachefs_metadata_version)
- incompat_versions_requested;
+
+ unsigned long incompat_versions_requested[BITS_TO_LONGS(BCH_VERSION_MINOR(bcachefs_metadata_version_current))];
struct unicode_map *cf_encoding;
@@ -1153,6 +1145,15 @@ struct bch_fs {
struct mutex fsck_error_counts_lock;
};
+static inline int __bch2_err_trace(struct bch_fs *c, int err)
+{
+ this_cpu_inc(c->counters[BCH_COUNTER_error_throw]);
+ trace_error_throw(c, err, _THIS_IP_);
+ return err;
+}
+
+#define bch_err_throw(_c, _err) __bch2_err_trace(_c, -BCH_ERR_##_err)
+
extern struct wait_queue_head bch2_read_only_wait;
static inline bool bch2_ro_ref_tryget(struct bch_fs *c)
diff --git a/fs/bcachefs/bcachefs_format.h b/fs/bcachefs/bcachefs_format.h
index b4a04df5ea95..7a0b602c1b27 100644
--- a/fs/bcachefs/bcachefs_format.h
+++ b/fs/bcachefs/bcachefs_format.h
@@ -423,7 +423,8 @@ enum bch_bkey_type_flags {
x(logged_op_truncate, 32, BKEY_TYPE_strict_btree_checks) \
x(logged_op_finsert, 33, BKEY_TYPE_strict_btree_checks) \
x(accounting, 34, BKEY_TYPE_strict_btree_checks) \
- x(inode_alloc_cursor, 35, BKEY_TYPE_strict_btree_checks)
+ x(inode_alloc_cursor, 35, BKEY_TYPE_strict_btree_checks) \
+ x(extent_whiteout, 36, BKEY_TYPE_strict_btree_checks)
enum bch_bkey_type {
#define x(name, nr, ...) KEY_TYPE_##name = nr,
@@ -440,6 +441,10 @@ struct bch_whiteout {
struct bch_val v;
};
+struct bch_extent_whiteout {
+ struct bch_val v;
+};
+
struct bch_error {
struct bch_val v;
};
@@ -700,7 +705,8 @@ struct bch_sb_field_ext {
x(extent_flags, BCH_VERSION(1, 25)) \
x(snapshot_deletion_v2, BCH_VERSION(1, 26)) \
x(fast_device_removal, BCH_VERSION(1, 27)) \
- x(inode_has_case_insensitive, BCH_VERSION(1, 28))
+ x(inode_has_case_insensitive, BCH_VERSION(1, 28)) \
+ x(extent_snapshot_whiteouts, BCH_VERSION(1, 29))
enum bcachefs_metadata_version {
bcachefs_metadata_version_min = 9,
@@ -1340,6 +1346,7 @@ enum btree_id_flags {
BTREE_IS_snapshots| \
BTREE_IS_data, \
BIT_ULL(KEY_TYPE_whiteout)| \
+ BIT_ULL(KEY_TYPE_extent_whiteout)| \
BIT_ULL(KEY_TYPE_error)| \
BIT_ULL(KEY_TYPE_cookie)| \
BIT_ULL(KEY_TYPE_extent)| \
@@ -1431,9 +1438,9 @@ enum btree_id {
*/
#define BTREE_ID_NR_MAX 63
-static inline bool btree_id_is_alloc(enum btree_id id)
+static inline bool btree_id_is_alloc(enum btree_id btree)
{
- switch (id) {
+ switch (btree) {
case BTREE_ID_alloc:
case BTREE_ID_backpointers:
case BTREE_ID_need_discard:
@@ -1447,6 +1454,33 @@ static inline bool btree_id_is_alloc(enum btree_id id)
}
}
+/* We can reconstruct these btrees from information in other btrees */
+static inline bool btree_id_can_reconstruct(enum btree_id btree)
+{
+ if (btree_id_is_alloc(btree))
+ return true;
+
+ switch (btree) {
+ case BTREE_ID_snapshot_trees:
+ case BTREE_ID_deleted_inodes:
+ case BTREE_ID_rebalance_work:
+ case BTREE_ID_subvolume_children:
+ return true;
+ default:
+ return false;
+ }
+}
+
+/*
+ * We can reconstruct BTREE_ID_alloc, but reconstucting it from scratch is not
+ * so cheap and OOMs on huge filesystems (until we have online
+ * check_allocations)
+ */
+static inline bool btree_id_recovers_from_scan(enum btree_id btree)
+{
+ return btree == BTREE_ID_alloc || !btree_id_can_reconstruct(btree);
+}
+
#define BTREE_MAX_DEPTH 4U
/* Btree nodes */
diff --git a/fs/bcachefs/bkey_methods.c b/fs/bcachefs/bkey_methods.c
index fcd8c82cba4f..75d73677c4d8 100644
--- a/fs/bcachefs/bkey_methods.c
+++ b/fs/bcachefs/bkey_methods.c
@@ -41,6 +41,10 @@ static int deleted_key_validate(struct bch_fs *c, struct bkey_s_c k,
.key_validate = deleted_key_validate, \
})
+#define bch2_bkey_ops_extent_whiteout ((struct bkey_ops) { \
+ .key_validate = deleted_key_validate, \
+})
+
static int empty_val_key_validate(struct bch_fs *c, struct bkey_s_c k,
struct bkey_validate_context from)
{
@@ -203,7 +207,7 @@ int __bch2_bkey_validate(struct bch_fs *c, struct bkey_s_c k,
? bch2_bkey_types[k.k->type]
: "(unknown)");
- if (btree_node_type_is_extents(type) && !bkey_whiteout(k.k)) {
+ if (btree_node_type_is_extents(type) && !bkey_extent_whiteout(k.k)) {
bkey_fsck_err_on(k.k->size == 0,
c, bkey_extent_size_zero,
"size == 0");
diff --git a/fs/bcachefs/bkey_types.h b/fs/bcachefs/bkey_types.h
index b4f328f9853c..88a48ce63656 100644
--- a/fs/bcachefs/bkey_types.h
+++ b/fs/bcachefs/bkey_types.h
@@ -44,6 +44,11 @@ static inline void set_bkey_val_bytes(struct bkey *k, unsigned bytes)
#define bkey_whiteout(_k) \
((_k)->type == KEY_TYPE_deleted || (_k)->type == KEY_TYPE_whiteout)
+#define bkey_extent_whiteout(_k) \
+ ((_k)->type == KEY_TYPE_deleted || \
+ (_k)->type == KEY_TYPE_whiteout || \
+ (_k)->type == KEY_TYPE_extent_whiteout)
+
/* bkey with split value, const */
struct bkey_s_c {
const struct bkey *k;
diff --git a/fs/bcachefs/btree_cache.c b/fs/bcachefs/btree_cache.c
index 2f7c384a8c81..59638d09e1fd 100644
--- a/fs/bcachefs/btree_cache.c
+++ b/fs/bcachefs/btree_cache.c
@@ -214,7 +214,7 @@ void bch2_node_pin(struct bch_fs *c, struct btree *b)
struct btree_cache *bc = &c->btree_cache;
guard(mutex)(&bc->lock);
- if (b != btree_node_root(c, b) && !btree_node_pinned(b)) {
+ if (!btree_node_is_root(c, b) && !btree_node_pinned(b)) {
set_btree_node_pinned(b);
list_move(&b->list, &bc->live[1].list);
bc->live[0].nr--;
@@ -788,7 +788,7 @@ struct btree *bch2_btree_node_mem_alloc(struct btree_trans *trans, bool pcpu_rea
goto got_node;
}
- b = __btree_node_mem_alloc(c, GFP_NOWAIT|__GFP_NOWARN);
+ b = __btree_node_mem_alloc(c, GFP_NOWAIT);
if (b) {
bch2_btree_lock_init(&b->c, pcpu_read_locks ? SIX_LOCK_INIT_PCPU : 0, GFP_NOWAIT);
} else {
@@ -826,7 +826,7 @@ got_node:
mutex_unlock(&bc->lock);
- if (btree_node_data_alloc(c, b, GFP_NOWAIT|__GFP_NOWARN)) {
+ if (btree_node_data_alloc(c, b, GFP_NOWAIT)) {
bch2_trans_unlock(trans);
if (btree_node_data_alloc(c, b, GFP_KERNEL|__GFP_NOWARN))
goto err;
diff --git a/fs/bcachefs/btree_cache.h b/fs/bcachefs/btree_cache.h
index 649e9dfd178a..035b2cb25077 100644
--- a/fs/bcachefs/btree_cache.h
+++ b/fs/bcachefs/btree_cache.h
@@ -144,6 +144,14 @@ static inline struct btree *btree_node_root(struct bch_fs *c, struct btree *b)
return r ? r->b : NULL;
}
+static inline bool btree_node_is_root(struct bch_fs *c, struct btree *b)
+{
+ struct btree *root = btree_node_root(c, b);
+
+ BUG_ON(b != root && b->c.level >= root->c.level);
+ return b == root;
+}
+
const char *bch2_btree_id_str(enum btree_id); /* avoid */
void bch2_btree_id_to_text(struct printbuf *, enum btree_id);
void bch2_btree_id_level_to_text(struct printbuf *, enum btree_id, unsigned);
diff --git a/fs/bcachefs/btree_gc.c b/fs/bcachefs/btree_gc.c
index ce3c7750a922..ae7d260589d8 100644
--- a/fs/bcachefs/btree_gc.c
+++ b/fs/bcachefs/btree_gc.c
@@ -44,27 +44,6 @@
#include <linux/rcupdate.h>
#include <linux/sched/task.h>
-/*
- * Returns true if it's a btree we can easily reconstruct, or otherwise won't
- * cause data loss if it's missing:
- */
-static bool btree_id_important(enum btree_id btree)
-{
- if (btree_id_is_alloc(btree))
- return false;
-
- switch (btree) {
- case BTREE_ID_quotas:
- case BTREE_ID_snapshot_trees:
- case BTREE_ID_logged_ops:
- case BTREE_ID_rebalance_work:
- case BTREE_ID_subvolume_children:
- return false;
- default:
- return true;
- }
-}
-
static const char * const bch2_gc_phase_strs[] = {
#define x(n) #n,
GC_PHASES()
@@ -282,6 +261,41 @@ fsck_err:
return ret;
}
+static int btree_check_root_boundaries(struct btree_trans *trans, struct btree *b)
+{
+ struct bch_fs *c = trans->c;
+ struct printbuf buf = PRINTBUF;
+ int ret = 0;
+
+ BUG_ON(b->key.k.type == KEY_TYPE_btree_ptr_v2 &&
+ !bpos_eq(bkey_i_to_btree_ptr_v2(&b->key)->v.min_key,
+ b->data->min_key));
+
+ prt_str(&buf, " at ");
+ bch2_btree_pos_to_text(&buf, c, b);
+
+ if (mustfix_fsck_err_on(!bpos_eq(b->data->min_key, POS_MIN),
+ trans, btree_node_topology_bad_root_min_key,
+ "btree root with incorrect min_key%s", buf.buf)) {
+ ret = set_node_min(c, b, POS_MIN);
+ if (ret)
+ goto err;
+ }
+
+ if (mustfix_fsck_err_on(!bpos_eq(b->data->max_key, SPOS_MAX),
+ trans, btree_node_topology_bad_root_max_key,
+ "btree root with incorrect min_key%s", buf.buf)) {
+ ret = set_node_max(c, b, SPOS_MAX);
+ if (ret)
+ goto err;
+ }
+
+err:
+fsck_err:
+ printbuf_exit(&buf);
+ return ret;
+}
+
static int btree_repair_node_end(struct btree_trans *trans, struct btree *b,
struct btree *child, struct bpos *pulled_from_scan)
{
@@ -522,45 +536,55 @@ fsck_err:
return ret;
}
-static int bch2_check_root(struct btree_trans *trans, enum btree_id btree,
+static int bch2_topology_check_root(struct btree_trans *trans, enum btree_id btree,
bool *reconstructed_root)
{
struct bch_fs *c = trans->c;
struct btree_root *r = bch2_btree_id_root(c, btree);
- CLASS(printbuf, buf)();
- int ret = 0;
- bch2_btree_id_to_text(&buf, btree);
-
- if (r->error) {
- bch_info(c, "btree root %s unreadable, must recover from scan", buf.buf);
+ if (!r->error)
+ return 0;
- ret = bch2_btree_has_scanned_nodes(c, btree);
- if (ret < 0)
- goto err;
+ CLASS(printbuf, buf)();
+ int ret = 0;
- if (!ret) {
- __fsck_err(trans,
- FSCK_CAN_FIX|(!btree_id_important(btree) ? FSCK_AUTOFIX : 0),
- btree_root_unreadable_and_scan_found_nothing,
- "no nodes found for btree %s, continue?", buf.buf);
+ if (!btree_id_recovers_from_scan(btree)) {
+ r->alive = false;
+ r->error = 0;
+ bch2_btree_root_alloc_fake_trans(trans, btree, 0);
+ ret = bch2_btree_lost_data(c, &buf, btree);
+ bch2_print_str(c, KERN_NOTICE, buf.buf);
+ goto out;
+ }
- r->alive = false;
- r->error = 0;
- bch2_btree_root_alloc_fake_trans(trans, btree, 0);
- } else {
- r->alive = false;
- r->error = 0;
- bch2_btree_root_alloc_fake_trans(trans, btree, 1);
+ bch2_btree_id_to_text(&buf, btree);
+ bch_info(c, "btree root %s unreadable, must recover from scan", buf.buf);
- bch2_shoot_down_journal_keys(c, btree, 1, BTREE_MAX_DEPTH, POS_MIN, SPOS_MAX);
- ret = bch2_get_scanned_nodes(c, btree, 0, POS_MIN, SPOS_MAX);
- if (ret)
- return ret;
- }
+ ret = bch2_btree_has_scanned_nodes(c, btree);
+ if (ret < 0)
+ goto err;
- *reconstructed_root = true;
+ if (!ret) {
+ __fsck_err(trans,
+ FSCK_CAN_FIX|(btree_id_can_reconstruct(btree) ? FSCK_AUTOFIX : 0),
+ btree_root_unreadable_and_scan_found_nothing,
+ "no nodes found for btree %s, continue?", buf.buf);
+
+ r->alive = false;
+ r->error = 0;
+ bch2_btree_root_alloc_fake_trans(trans, btree, 0);
+ } else {
+ r->alive = false;
+ r->error = 0;
+ bch2_btree_root_alloc_fake_trans(trans, btree, 1);
+
+ bch2_shoot_down_journal_keys(c, btree, 1, BTREE_MAX_DEPTH, POS_MIN, SPOS_MAX);
+ ret = bch2_get_scanned_nodes(c, btree, 0, POS_MIN, SPOS_MAX);
+ if (ret)
+ return ret;
}
+out:
+ *reconstructed_root = true;
err:
fsck_err:
bch_err_fn(c, ret);
@@ -578,7 +602,7 @@ int bch2_check_topology(struct bch_fs *c)
for (unsigned i = 0; i < btree_id_nr_alive(c) && !ret; i++) {
bool reconstructed_root = false;
recover:
- ret = lockrestart_do(trans, bch2_check_root(trans, i, &reconstructed_root));
+ ret = lockrestart_do(trans, bch2_topology_check_root(trans, i, &reconstructed_root));
if (ret)
break;
@@ -586,7 +610,8 @@ recover:
struct btree *b = r->b;
btree_node_lock_nopath_nofail(trans, &b->c, SIX_LOCK_read);
- ret = bch2_btree_repair_topology_recurse(trans, b, &pulled_from_scan);
+ ret = btree_check_root_boundaries(trans, b) ?:
+ bch2_btree_repair_topology_recurse(trans, b, &pulled_from_scan);
six_unlock_read(&b->c.lock);
if (bch2_err_matches(ret, BCH_ERR_topology_repair_drop_this_node)) {
diff --git a/fs/bcachefs/btree_io.c b/fs/bcachefs/btree_io.c
index 8a03cd75a64f..276cf088539e 100644
--- a/fs/bcachefs/btree_io.c
+++ b/fs/bcachefs/btree_io.c
@@ -131,7 +131,7 @@ static void *btree_bounce_alloc(struct bch_fs *c, size_t size,
BUG_ON(size > c->opts.btree_node_size);
*used_mempool = false;
- p = kvmalloc(size, __GFP_NOWARN|GFP_NOWAIT);
+ p = kvmalloc(size, GFP_NOWAIT);
if (!p) {
*used_mempool = true;
p = mempool_alloc(&c->btree_bounce_pool, GFP_NOFS);
diff --git a/fs/bcachefs/btree_iter.c b/fs/bcachefs/btree_iter.c
index ff580f76a641..546b559fe3ce 100644
--- a/fs/bcachefs/btree_iter.c
+++ b/fs/bcachefs/btree_iter.c
@@ -2366,7 +2366,9 @@ struct bkey_s_c bch2_btree_iter_peek_max(struct btree_iter *iter, struct bpos en
bch2_trans_verify_not_unlocked_or_in_restart(trans);
bch2_btree_iter_verify_entry_exit(iter);
- EBUG_ON((iter->flags & BTREE_ITER_filter_snapshots) && bkey_eq(end, POS_MAX));
+ EBUG_ON((iter->flags & BTREE_ITER_filter_snapshots) &&
+ !(iter->flags & BTREE_ITER_nofilter_whiteouts) &&
+ bkey_eq(end, POS_MAX));
ret = trans_maybe_inject_restart(trans, _RET_IP_);
if (unlikely(ret)) {
@@ -2450,10 +2452,27 @@ struct bkey_s_c bch2_btree_iter_peek_max(struct btree_iter *iter, struct bpos en
continue;
}
- if (bkey_whiteout(k.k) &&
- !(iter->flags & BTREE_ITER_key_cache_fill)) {
- search_key = bkey_successor(iter, k.k->p);
- continue;
+ if (!(iter->flags & BTREE_ITER_nofilter_whiteouts)) {
+ /*
+ * KEY_TYPE_extent_whiteout indicates that there
+ * are no extents that overlap with this
+ * whiteout - meaning bkey_start_pos() is
+ * monotonically increasing when including
+ * KEY_TYPE_extent_whiteout (not
+ * KEY_TYPE_whiteout).
+ *
+ * Without this @end wouldn't be able to
+ * terminate searches and we'd have to scan
+ * through tons of whiteouts:
+ */
+ if (k.k->type == KEY_TYPE_extent_whiteout &&
+ bkey_ge(k.k->p, end))
+ goto end;
+
+ if (bkey_extent_whiteout(k.k)) {
+ search_key = bkey_successor(iter, k.k->p);
+ continue;
+ }
}
}
@@ -2711,7 +2730,7 @@ struct bkey_s_c bch2_btree_iter_peek_prev_min(struct btree_iter *iter, struct bp
saved_path = 0;
}
- if (!bkey_whiteout(k.k)) {
+ if (!bkey_extent_whiteout(k.k)) {
saved_path = btree_path_clone(trans, iter->path,
iter->flags & BTREE_ITER_intent,
_THIS_IP_);
@@ -2724,7 +2743,7 @@ struct bkey_s_c bch2_btree_iter_peek_prev_min(struct btree_iter *iter, struct bp
continue;
}
- if (bkey_whiteout(k.k)) {
+ if (bkey_extent_whiteout(k.k)) {
search_key = bkey_predecessor(iter, k.k->p);
search_key.snapshot = U32_MAX;
continue;
@@ -2865,9 +2884,9 @@ struct bkey_s_c bch2_btree_iter_peek_slot(struct btree_iter *iter)
iter->k = *k.k;
}
- if (unlikely(k.k->type == KEY_TYPE_whiteout &&
+ if (unlikely(bkey_extent_whiteout(k.k) &&
(iter->flags & BTREE_ITER_filter_snapshots) &&
- !(iter->flags & BTREE_ITER_key_cache_fill)))
+ !(iter->flags & BTREE_ITER_nofilter_whiteouts)))
iter->k.type = KEY_TYPE_deleted;
} else {
struct bpos next;
@@ -2878,31 +2897,40 @@ struct bkey_s_c bch2_btree_iter_peek_slot(struct btree_iter *iter)
EBUG_ON(btree_iter_path(trans, iter)->level);
- if (iter->flags & BTREE_ITER_intent) {
- struct btree_iter iter2;
+ struct btree_iter iter2;
- bch2_trans_copy_iter(&iter2, iter);
- k = bch2_btree_iter_peek_max(&iter2, end);
+ bch2_trans_copy_iter(&iter2, iter);
+ iter2.flags |= BTREE_ITER_nofilter_whiteouts;
- if (k.k && !bkey_err(k)) {
- swap(iter->key_cache_path, iter2.key_cache_path);
- iter->k = iter2.k;
- k.k = &iter->k;
+ while (1) {
+ k = bch2_btree_iter_peek_max(&iter2, end);
+ if ((iter2.flags & BTREE_ITER_is_extents) &&
+ k.k &&
+ !bkey_err(k) &&
+ k.k->type == KEY_TYPE_whiteout) {
+ bch2_btree_iter_set_pos(&iter2, k.k->p);
+ continue;
}
- bch2_trans_iter_exit(&iter2);
- } else {
- struct bpos pos = iter->pos;
- k = bch2_btree_iter_peek_max(iter, end);
- if (unlikely(bkey_err(k)))
- bch2_btree_iter_set_pos(iter, pos);
- else
- iter->pos = pos;
+ break;
+ }
+
+ if (k.k && !bkey_err(k)) {
+ swap(iter->key_cache_path, iter2.key_cache_path);
+ iter->k = iter2.k;
+ k.k = &iter->k;
}
+ bch2_trans_iter_exit(&iter2);
if (unlikely(bkey_err(k)))
goto out;
+ if (unlikely(k.k &&
+ bkey_extent_whiteout(k.k) &&
+ (iter->flags & BTREE_ITER_filter_snapshots) &&
+ !(iter->flags & BTREE_ITER_nofilter_whiteouts)))
+ iter->k.type = KEY_TYPE_deleted;
+
next = k.k ? bkey_start_pos(k.k) : POS_MAX;
if (bkey_lt(iter->pos, next)) {
diff --git a/fs/bcachefs/btree_iter.h b/fs/bcachefs/btree_iter.h
index b117cb5d7f94..c8fc6ee01d96 100644
--- a/fs/bcachefs/btree_iter.h
+++ b/fs/bcachefs/btree_iter.h
@@ -954,7 +954,7 @@ struct bkey_s_c bch2_btree_iter_peek_and_restart_outlined(struct btree_iter *);
#define allocate_dropping_locks_errcode(_trans, _do) \
({ \
- gfp_t _gfp = GFP_NOWAIT|__GFP_NOWARN; \
+ gfp_t _gfp = GFP_NOWAIT; \
int _ret = _do; \
\
if (bch2_err_matches(_ret, ENOMEM)) { \
@@ -966,7 +966,7 @@ struct bkey_s_c bch2_btree_iter_peek_and_restart_outlined(struct btree_iter *);
#define allocate_dropping_locks(_trans, _ret, _do) \
({ \
- gfp_t _gfp = GFP_NOWAIT|__GFP_NOWARN; \
+ gfp_t _gfp = GFP_NOWAIT; \
typeof(_do) _p = _do; \
\
_ret = 0; \
@@ -979,7 +979,7 @@ struct bkey_s_c bch2_btree_iter_peek_and_restart_outlined(struct btree_iter *);
#define allocate_dropping_locks_norelock(_trans, _lock_dropped, _do) \
({ \
- gfp_t _gfp = GFP_NOWAIT|__GFP_NOWARN; \
+ gfp_t _gfp = GFP_NOWAIT; \
typeof(_do) _p = _do; \
_lock_dropped = false; \
if (unlikely(!_p)) { \
diff --git a/fs/bcachefs/btree_key_cache.c b/fs/bcachefs/btree_key_cache.c
index 72c803f7b8d1..4890cbc88e7c 100644
--- a/fs/bcachefs/btree_key_cache.c
+++ b/fs/bcachefs/btree_key_cache.c
@@ -325,6 +325,7 @@ static noinline int btree_key_cache_fill(struct btree_trans *trans,
CLASS(btree_iter, iter)(trans, ck_path->btree_id, ck_path->pos,
BTREE_ITER_intent|
+ BTREE_ITER_nofilter_whiteouts|
BTREE_ITER_key_cache_fill|
BTREE_ITER_cached_nofill);
iter.flags &= ~BTREE_ITER_with_journal;
diff --git a/fs/bcachefs/btree_node_scan.c b/fs/bcachefs/btree_node_scan.c
index 4b7b5ca74ba1..b618a0bd1186 100644
--- a/fs/bcachefs/btree_node_scan.c
+++ b/fs/bcachefs/btree_node_scan.c
@@ -149,7 +149,7 @@ static void try_read_btree_node(struct find_btree_nodes *f, struct bch_dev *ca,
bch2_encrypt(c, BSET_CSUM_TYPE(&bn->keys), nonce, &bn->flags, bytes);
}
- if (btree_id_is_alloc(BTREE_NODE_ID(bn)))
+ if (btree_id_can_reconstruct(BTREE_NODE_ID(bn)))
return;
if (BTREE_NODE_LEVEL(bn) >= BTREE_MAX_DEPTH)
@@ -534,7 +534,7 @@ int bch2_btree_has_scanned_nodes(struct bch_fs *c, enum btree_id btree)
int bch2_get_scanned_nodes(struct bch_fs *c, enum btree_id btree,
unsigned level, struct bpos node_min, struct bpos node_max)
{
- if (btree_id_is_alloc(btree))
+ if (!btree_id_recovers_from_scan(btree))
return 0;
struct find_btree_nodes *f = &c->found_btree_nodes;
diff --git a/fs/bcachefs/btree_trans_commit.c b/fs/bcachefs/btree_trans_commit.c
index 8b94a8156fbf..4d58bdb233e9 100644
--- a/fs/bcachefs/btree_trans_commit.c
+++ b/fs/bcachefs/btree_trans_commit.c
@@ -449,7 +449,7 @@ static int btree_key_can_insert_cached(struct btree_trans *trans, unsigned flags
return 0;
new_u64s = roundup_pow_of_two(u64s);
- new_k = krealloc(ck->k, new_u64s * sizeof(u64), GFP_NOWAIT|__GFP_NOWARN);
+ new_k = krealloc(ck->k, new_u64s * sizeof(u64), GFP_NOWAIT);
if (unlikely(!new_k))
return btree_key_can_insert_cached_slowpath(trans, flags, path, new_u64s);
diff --git a/fs/bcachefs/btree_types.h b/fs/bcachefs/btree_types.h
index ffa250008d91..e893eb938bb3 100644
--- a/fs/bcachefs/btree_types.h
+++ b/fs/bcachefs/btree_types.h
@@ -229,6 +229,7 @@ struct btree_node_iter {
x(snapshot_field) \
x(all_snapshots) \
x(filter_snapshots) \
+ x(nofilter_whiteouts) \
x(nopreserve) \
x(cached_nofill) \
x(key_cache_fill) \
@@ -839,15 +840,15 @@ static inline bool btree_node_type_has_triggers(enum btree_node_type type)
return BIT_ULL(type) & BTREE_NODE_TYPE_HAS_TRIGGERS;
}
-static inline bool btree_id_is_extents(enum btree_id btree)
-{
- const u64 mask = 0
+static const u64 btree_is_extents_mask = 0
#define x(name, nr, flags, ...) |((!!((flags) & BTREE_IS_extents)) << nr)
- BCH_BTREE_IDS()
+BCH_BTREE_IDS()
#undef x
- ;
+;
- return BIT_ULL(btree) & mask;
+static inline bool btree_id_is_extents(enum btree_id btree)
+{
+ return BIT_ULL(btree) & btree_is_extents_mask;
}
static inline bool btree_node_type_is_extents(enum btree_node_type type)
@@ -866,6 +867,11 @@ static inline bool btree_type_has_snapshots(enum btree_id btree)
return BIT_ULL(btree) & btree_has_snapshots_mask;
}
+static inline bool btree_id_is_extents_snapshots(enum btree_id btree)
+{
+ return BIT_ULL(btree) & btree_has_snapshots_mask & btree_is_extents_mask;
+}
+
static inline bool btree_type_has_snapshot_field(enum btree_id btree)
{
const u64 mask = 0
diff --git a/fs/bcachefs/btree_update.c b/fs/bcachefs/btree_update.c
index 566478728aa2..053a837cf241 100644
--- a/fs/bcachefs/btree_update.c
+++ b/fs/bcachefs/btree_update.c
@@ -215,7 +215,7 @@ int bch2_trans_update_extent_overwrite(struct btree_trans *trans,
return ret;
}
- if (bkey_le(old.k->p, new.k->p)) {
+ if (!back_split) {
update = bch2_trans_kmalloc(trans, sizeof(*update));
if ((ret = PTR_ERR_OR_ZERO(update)))
return ret;
@@ -224,23 +224,21 @@ int bch2_trans_update_extent_overwrite(struct btree_trans *trans,
update->k.p = old.k->p;
update->k.p.snapshot = new.k->p.snapshot;
- if (new.k->p.snapshot != old.k->p.snapshot) {
- update->k.type = KEY_TYPE_whiteout;
- } else if (btree_type_has_snapshots(btree_id)) {
- ret = need_whiteout_for_snapshot(trans, btree_id, update->k.p);
+ if (btree_type_has_snapshots(btree_id)) {
+ ret = new.k->p.snapshot != old.k->p.snapshot
+ ? 1
+ : need_whiteout_for_snapshot(trans, btree_id, update->k.p);
if (ret < 0)
return ret;
if (ret)
- update->k.type = KEY_TYPE_whiteout;
+ update->k.type = extent_whiteout_type(trans->c, iter->btree_id, new.k);
}
ret = bch2_btree_insert_nonextent(trans, btree_id, update,
BTREE_UPDATE_internal_snapshot_node|flags);
if (ret)
return ret;
- }
-
- if (back_split) {
+ } else {
update = bch2_bkey_make_mut_noupdate(trans, old);
if ((ret = PTR_ERR_OR_ZERO(update)))
return ret;
@@ -267,7 +265,8 @@ static int bch2_trans_update_extent(struct btree_trans *trans,
CLASS(btree_iter, iter)(trans, btree_id, bkey_start_pos(&insert->k),
BTREE_ITER_intent|
BTREE_ITER_with_updates|
- BTREE_ITER_not_extents);
+ BTREE_ITER_not_extents|
+ BTREE_ITER_nofilter_whiteouts);
struct bkey_s_c k = bch2_btree_iter_peek_max(&iter, POS(insert->k.p.inode, U64_MAX));
int ret = bkey_err(k);
if (ret)
@@ -285,12 +284,40 @@ static int bch2_trans_update_extent(struct btree_trans *trans,
goto next;
}
- while (bkey_gt(insert->k.p, bkey_start_pos(k.k))) {
- bool done = bkey_lt(insert->k.p, k.k->p);
+ while (true) {
+ BUG_ON(bkey_le(k.k->p, bkey_start_pos(&insert->k)));
- ret = bch2_trans_update_extent_overwrite(trans, &iter, flags, k, bkey_i_to_s_c(insert));
- if (ret)
- return ret;
+ /*
+ * When KEY_TYPE_whiteout is included, bkey_start_pos is not
+ * monotonically increasing
+ */
+ if (k.k->type != KEY_TYPE_whiteout && bkey_le(insert->k.p, bkey_start_pos(k.k)))
+ break;
+
+ bool done = k.k->type != KEY_TYPE_whiteout && bkey_lt(insert->k.p, k.k->p);
+
+ if (bkey_extent_whiteout(k.k)) {
+ enum bch_bkey_type whiteout_type = extent_whiteout_type(trans->c, btree_id, &insert->k);
+
+ if (bkey_le(k.k->p, insert->k.p) &&
+ k.k->type != whiteout_type) {
+ struct bkey_i *update = bch2_bkey_make_mut_noupdate(trans, k);
+ ret = PTR_ERR_OR_ZERO(update);
+ if (ret)
+ return ret;
+
+ update->k.p.snapshot = iter.snapshot;
+ update->k.type = whiteout_type;
+
+ ret = bch2_trans_update(trans, &iter, update, 0);
+ if (ret)
+ return ret;
+ }
+ } else {
+ ret = bch2_trans_update_extent_overwrite(trans, &iter, flags, k, bkey_i_to_s_c(insert));
+ if (ret)
+ return ret;
+ }
if (done)
goto out;
diff --git a/fs/bcachefs/btree_update.h b/fs/bcachefs/btree_update.h
index 663739db82b1..18560ca80057 100644
--- a/fs/bcachefs/btree_update.h
+++ b/fs/bcachefs/btree_update.h
@@ -5,6 +5,7 @@
#include "btree_iter.h"
#include "journal.h"
#include "snapshot.h"
+#include "super-io.h"
struct bch_fs;
struct btree;
@@ -110,6 +111,22 @@ static inline int bch2_insert_snapshot_whiteouts(struct btree_trans *trans,
: 0;
}
+static inline enum bch_bkey_type extent_whiteout_type(struct bch_fs *c, enum btree_id btree,
+ const struct bkey *k)
+{
+ /*
+ * KEY_TYPE_extent_whiteout indicates that there isn't a real extent
+ * present at that position: key start positions inclusive of
+ * KEY_TYPE_extent_whiteout (but not KEY_TYPE_whiteout) are
+ * monotonically increasing
+ */
+ return btree_id_is_extents_snapshots(btree) &&
+ bkey_deleted(k) &&
+ !bch2_request_incompat_feature(c, bcachefs_metadata_version_extent_snapshot_whiteouts)
+ ? KEY_TYPE_extent_whiteout
+ : KEY_TYPE_whiteout;
+}
+
int bch2_trans_update_extent_overwrite(struct btree_trans *, struct btree_iter *,
enum btree_iter_update_trigger_flags,
struct bkey_s_c, struct bkey_s_c);
diff --git a/fs/bcachefs/btree_update_interior.c b/fs/bcachefs/btree_update_interior.c
index 5f4f82967105..65ca54c5b0ff 100644
--- a/fs/bcachefs/btree_update_interior.c
+++ b/fs/bcachefs/btree_update_interior.c
@@ -66,6 +66,10 @@ int bch2_btree_node_check_topology(struct btree_trans *trans, struct btree *b)
bkey_init(&prev.k->k);
bch2_btree_and_journal_iter_init_node_iter(trans, &iter, b);
+ /*
+ * Don't use btree_node_is_root(): we're called by btree split, after
+ * creating a new root but before setting it
+ */
if (b == btree_node_root(c, b)) {
if (!bpos_eq(b->data->min_key, POS_MIN)) {
bch2_log_msg_start(c, &buf);
@@ -332,6 +336,20 @@ static struct btree *__bch2_btree_node_alloc(struct btree_trans *trans,
BUG_ON(b->ob.nr);
mutex_lock(&c->btree_reserve_cache_lock);
+ if (unlikely(c->open_buckets_nr_free <= bch2_open_buckets_reserved(watermark))) {
+ guard(spinlock)(&c->freelist_lock);
+ if (c->open_buckets_nr_free <= bch2_open_buckets_reserved(watermark)) {
+ if (cl)
+ closure_wait(&c->open_buckets_wait, cl);
+
+ ret = cl
+ ? bch_err_throw(c, bucket_alloc_blocked)
+ : bch_err_throw(c, open_buckets_empty);
+ mutex_unlock(&c->btree_reserve_cache_lock);
+ goto err;
+ }
+ }
+
if (c->btree_reserve_cache_nr > nr_reserve) {
for (struct btree_alloc *a = c->btree_reserve_cache;
a < c->btree_reserve_cache + c->btree_reserve_cache_nr;) {
@@ -1655,7 +1673,7 @@ static int btree_split(struct btree_update *as, struct btree_trans *trans,
int ret = 0;
bch2_verify_btree_nr_keys(b);
- BUG_ON(!parent && (b != btree_node_root(c, b)));
+ BUG_ON(!parent && !btree_node_is_root(c, b));
BUG_ON(parent && !btree_node_intent_locked(trans->paths + path, b->c.level + 1));
ret = bch2_btree_node_check_topology(trans, b);
@@ -2527,7 +2545,7 @@ static int __bch2_btree_node_update_key(struct btree_trans *trans,
if (ret)
goto err;
} else {
- BUG_ON(btree_node_root(c, b) != b);
+ BUG_ON(!btree_node_is_root(c, b));
struct jset_entry *e = bch2_trans_jset_entry_alloc(trans,
jset_u64s(new_key->k.u64s));
diff --git a/fs/bcachefs/btree_write_buffer.c b/fs/bcachefs/btree_write_buffer.c
index afad11831e1d..755fb25a8eba 100644
--- a/fs/bcachefs/btree_write_buffer.c
+++ b/fs/bcachefs/btree_write_buffer.c
@@ -701,8 +701,16 @@ int bch2_accounting_key_to_wb_slowpath(struct bch_fs *c, enum btree_id btree,
struct bkey_i_accounting *k)
{
struct btree_write_buffer *wb = &c->btree_write_buffer;
- struct btree_write_buffered_key new = { .btree = btree };
+ if (trace_accounting_key_to_wb_slowpath_enabled()) {
+ CLASS(printbuf, buf)();
+ prt_printf(&buf, "have: %zu\n", wb->accounting.nr);
+ bch2_bkey_val_to_text(&buf, c, bkey_i_to_s_c(&k->k_i));
+ trace_accounting_key_to_wb_slowpath(c, buf.buf);
+ }
+ count_event(c, accounting_key_to_wb_slowpath);
+
+ struct btree_write_buffered_key new = { .btree = btree };
bkey_copy(&new.k, &k->k_i);
int ret = darray_push(&wb->accounting, new);
diff --git a/fs/bcachefs/btree_write_buffer.h b/fs/bcachefs/btree_write_buffer.h
index e484cd6b90b0..b862bdf67f58 100644
--- a/fs/bcachefs/btree_write_buffer.h
+++ b/fs/bcachefs/btree_write_buffer.h
@@ -95,7 +95,7 @@ static inline int bch2_journal_key_to_wb(struct bch_fs *c,
EBUG_ON(!dst->seq);
- return k->k.type == KEY_TYPE_accounting
+ return bch2_bkey_is_accounting_mem(&k->k)
? bch2_accounting_key_to_wb(c, btree, bkey_i_to_accounting(k))
: __bch2_journal_key_to_wb(c, dst, btree, k);
}
diff --git a/fs/bcachefs/data_update.c b/fs/bcachefs/data_update.c
index 01838a3a189d..a314d70c6b8e 100644
--- a/fs/bcachefs/data_update.c
+++ b/fs/bcachefs/data_update.c
@@ -225,7 +225,7 @@ static void trace_io_move_created_rebalance2(struct data_update *m,
trace_io_move_created_rebalance(c, buf.buf);
- this_cpu_inc(c->counters[BCH_COUNTER_io_move_created_rebalance]);
+ count_event(c, io_move_created_rebalance);
}
noinline_for_stack
@@ -693,6 +693,15 @@ int bch2_extent_drop_ptrs(struct btree_trans *trans,
if (ret)
return ret;
+ const union bch_extent_entry *entry;
+ struct extent_ptr_decoded p;
+ unsigned i = 0;
+ bkey_for_each_ptr_decode(k.k, bch2_bkey_ptrs_c(k), p, entry) {
+ if (data_opts->kill_ec_ptrs & BIT(i))
+ bch2_bkey_drop_ec(n, p.ptr.dev);
+ i++;
+ }
+
while (data_opts->kill_ptrs) {
unsigned i = 0, drop = __fls(data_opts->kill_ptrs);
diff --git a/fs/bcachefs/data_update.h b/fs/bcachefs/data_update.h
index 5e14d13568de..fc12aa65366f 100644
--- a/fs/bcachefs/data_update.h
+++ b/fs/bcachefs/data_update.h
@@ -12,6 +12,7 @@ struct moving_context;
struct data_update_opts {
unsigned rewrite_ptrs;
unsigned kill_ptrs;
+ unsigned kill_ec_ptrs;
u16 target;
u8 extra_replicas;
unsigned btree_insert_flags;
diff --git a/fs/bcachefs/dirent.c b/fs/bcachefs/dirent.c
index 982d8ec17803..cb44b35e0f1d 100644
--- a/fs/bcachefs/dirent.c
+++ b/fs/bcachefs/dirent.c
@@ -740,21 +740,22 @@ found:
int bch2_fsck_remove_dirent(struct btree_trans *trans, struct bpos pos)
{
struct bch_fs *c = trans->c;
- struct bch_inode_unpacked dir_inode;
- struct bch_hash_info dir_hash_info;
+ struct bch_inode_unpacked dir_inode;
int ret = lookup_first_inode(trans, pos.inode, &dir_inode);
if (ret)
goto err;
- dir_hash_info = bch2_hash_info_init(c, &dir_inode);
+ {
+ struct bch_hash_info dir_hash_info = bch2_hash_info_init(c, &dir_inode);
- CLASS(btree_iter, iter)(trans, BTREE_ID_dirents, pos, BTREE_ITER_intent);
+ CLASS(btree_iter, iter)(trans, BTREE_ID_dirents, pos, BTREE_ITER_intent);
- ret = bch2_btree_iter_traverse(&iter) ?:
- bch2_hash_delete_at(trans, bch2_dirent_hash_desc,
- &dir_hash_info, &iter,
- BTREE_UPDATE_internal_snapshot_node);
+ ret = bch2_btree_iter_traverse(&iter) ?:
+ bch2_hash_delete_at(trans, bch2_dirent_hash_desc,
+ &dir_hash_info, &iter,
+ BTREE_UPDATE_internal_snapshot_node);
+ }
err:
bch_err_fn(c, ret);
return ret;
diff --git a/fs/bcachefs/disk_accounting.c b/fs/bcachefs/disk_accounting.c
index f96530c70262..5944ad6d0f8d 100644
--- a/fs/bcachefs/disk_accounting.c
+++ b/fs/bcachefs/disk_accounting.c
@@ -184,6 +184,9 @@ int bch2_accounting_validate(struct bch_fs *c, struct bkey_s_c k,
void *end = &acc_k + 1;
int ret = 0;
+ if (acc_k.type >= BCH_DISK_ACCOUNTING_TYPE_NR)
+ return 0;
+
bkey_fsck_err_on((from.flags & BCH_VALIDATE_commit) &&
bversion_zero(k.k->bversion),
c, accounting_key_version_0,
diff --git a/fs/bcachefs/disk_accounting.h b/fs/bcachefs/disk_accounting.h
index 43f4b21d0aab..cc73cce98a44 100644
--- a/fs/bcachefs/disk_accounting.h
+++ b/fs/bcachefs/disk_accounting.h
@@ -145,6 +145,16 @@ static inline bool bch2_accounting_is_mem(struct disk_accounting_pos *acc)
acc->type != BCH_DISK_ACCOUNTING_inum;
}
+static inline bool bch2_bkey_is_accounting_mem(struct bkey *k)
+{
+ if (k->type != KEY_TYPE_accounting)
+ return false;
+
+ struct disk_accounting_pos acc_k;
+ bpos_to_disk_accounting_pos(&acc_k, k->p);
+ return bch2_accounting_is_mem(&acc_k);
+}
+
/*
* Update in memory counters so they match the btree update we're doing; called
* from transaction commit path
diff --git a/fs/bcachefs/ec.c b/fs/bcachefs/ec.c
index c2840cb674b2..00e16801417a 100644
--- a/fs/bcachefs/ec.c
+++ b/fs/bcachefs/ec.c
@@ -35,6 +35,8 @@
#include <linux/raid/pq.h>
#include <linux/raid/xor.h>
+static bool bch2_stripe_is_open(struct bch_fs *, u64);
+
static void raid5_recov(unsigned disks, unsigned failed_idx,
size_t size, void **data)
{
@@ -386,11 +388,20 @@ int bch2_trigger_stripe(struct btree_trans *trans,
new_s->nr_redundant != old_s->nr_redundant));
if (flags & BTREE_TRIGGER_transactional) {
+ u64 old_lru_pos = stripe_lru_pos(old_s);
+ u64 new_lru_pos = stripe_lru_pos(new_s);
+
+ if (new_lru_pos == STRIPE_LRU_POS_EMPTY &&
+ !bch2_stripe_is_open(c, idx)) {
+ _new.k->type = KEY_TYPE_deleted;
+ set_bkey_val_u64s(_new.k, 0);
+ new_s = NULL;
+ new_lru_pos = 0;
+ }
+
int ret = bch2_lru_change(trans,
- BCH_LRU_STRIPE_FRAGMENTATION,
- idx,
- stripe_lru_pos(old_s),
- stripe_lru_pos(new_s));
+ BCH_LRU_STRIPE_FRAGMENTATION, idx,
+ old_lru_pos, new_lru_pos);
if (ret)
return ret;
}
@@ -954,7 +965,7 @@ static int ec_stripe_delete(struct btree_trans *trans, u64 idx)
*/
if (k.k->type == KEY_TYPE_stripe &&
!bch2_stripe_is_open(trans->c, idx) &&
- stripe_lru_pos(bkey_s_c_to_stripe(k).v) == 1)
+ stripe_lru_pos(bkey_s_c_to_stripe(k).v) == STRIPE_LRU_POS_EMPTY)
return bch2_btree_delete_at(trans, &iter, 0);
return 0;
@@ -1778,8 +1789,19 @@ static int __get_existing_stripe(struct btree_trans *trans,
return 0;
struct bkey_s_c_stripe s = bkey_s_c_to_stripe(k);
- if (stripe_lru_pos(s.v) <= 1)
- return 0;
+
+ if (stripe_lru_pos(s.v) == STRIPE_LRU_POS_EMPTY) {
+ /*
+ * We can't guarantee that the trigger will always delete
+ * stripes - the stripe might still be open when the last data
+ * in it was deleted
+ */
+ return !bch2_stripe_is_open(c, idx)
+ ? bch2_btree_delete_at(trans, &iter, 0) ?:
+ bch2_trans_commit(trans, NULL, NULL, BCH_TRANS_COMMIT_no_enospc) ?:
+ bch_err_throw(c, transaction_restart_commit)
+ : 0;
+ }
if (s.v->disk_label == head->disk_label &&
s.v->algorithm == head->algo &&
diff --git a/fs/bcachefs/errcode.h b/fs/bcachefs/errcode.h
index cec8b0f47d3d..adc1f9315eab 100644
--- a/fs/bcachefs/errcode.h
+++ b/fs/bcachefs/errcode.h
@@ -119,6 +119,7 @@
x(ENOENT, ENOENT_not_directory) \
x(ENOENT, ENOENT_directory_dead) \
x(ENOENT, ENOENT_subvolume) \
+ x(ENOENT, ENOENT_snapshot) \
x(ENOENT, ENOENT_snapshot_tree) \
x(ENOENT, ENOENT_dirent_doesnt_match_inode) \
x(ENOENT, ENOENT_dev_not_found) \
diff --git a/fs/bcachefs/error.h b/fs/bcachefs/error.h
index 0c3c3a24fc6f..213814787dd6 100644
--- a/fs/bcachefs/error.h
+++ b/fs/bcachefs/error.h
@@ -173,7 +173,8 @@ do { \
if (!bch2_err_matches(_ret, BCH_ERR_fsck_fix) && \
!bch2_err_matches(_ret, BCH_ERR_fsck_ignore)) \
ret = _ret; \
- ret = bch_err_throw(c, fsck_delete_bkey); \
+ else \
+ ret = bch_err_throw(c, fsck_delete_bkey); \
goto fsck_err; \
} while (0)
diff --git a/fs/bcachefs/extent_update.c b/fs/bcachefs/extent_update.c
index c4b0ea1adaa8..7ddb156c765c 100644
--- a/fs/bcachefs/extent_update.c
+++ b/fs/bcachefs/extent_update.c
@@ -98,11 +98,13 @@ static int count_iters_for_insert(struct btree_trans *trans,
return ret2 ?: ret;
}
-int bch2_extent_atomic_end(struct btree_trans *trans,
- struct btree_iter *iter,
- struct bpos *end)
+int bch2_extent_trim_atomic(struct btree_trans *trans,
+ struct btree_iter *iter,
+ struct bkey_i *insert)
{
- unsigned nr_iters = 0;
+ enum bch_bkey_type whiteout_type =
+ extent_whiteout_type(trans->c, iter->btree_id, &insert->k);
+ struct bpos end = insert->k.p;
struct btree_iter copy;
bch2_trans_copy_iter(&copy, iter);
@@ -111,42 +113,54 @@ int bch2_extent_atomic_end(struct btree_trans *trans,
if (ret)
goto err;
+ copy.flags |= BTREE_ITER_nofilter_whiteouts;
+
struct bkey_s_c k;
- for_each_btree_key_max_continue_norestart(copy, *end, 0, k, ret) {
+ unsigned nr_iters = 0;
+ for_each_btree_key_continue_norestart(copy, 0, k, ret) {
unsigned offset = 0;
if (bkey_gt(iter->pos, bkey_start_pos(k.k)))
offset = iter->pos.offset - bkey_start_offset(k.k);
- ret = count_iters_for_insert(trans, k, offset, end, &nr_iters);
- if (ret)
- break;
+ if (bkey_extent_whiteout(k.k)) {
+ if (bpos_gt(k.k->p, insert->k.p)) {
+ if (k.k->type == KEY_TYPE_extent_whiteout)
+ break;
+ else
+ continue;
+ } else if (k.k->type != whiteout_type) {
+ nr_iters += 1;
+ if (nr_iters >= EXTENT_ITERS_MAX) {
+ end = bpos_min(end, k.k->p);
+ break;
+ }
+ }
+ } else {
+ if (bpos_ge(bkey_start_pos(k.k), end))
+ break;
+
+ ret = count_iters_for_insert(trans, k, offset, &end, &nr_iters);
+ if (ret)
+ break;
+ }
}
err:
bch2_trans_iter_exit(&copy);
- return ret < 0 ? ret : 0;
-}
-
-int bch2_extent_trim_atomic(struct btree_trans *trans,
- struct btree_iter *iter,
- struct bkey_i *k)
-{
- struct bpos end = k->k.p;
- int ret = bch2_extent_atomic_end(trans, iter, &end);
- if (ret)
+ if (ret < 0)
return ret;
/* tracepoint */
- if (bpos_lt(end, k->k.p)) {
+ if (bpos_lt(end, insert->k.p)) {
if (trace_extent_trim_atomic_enabled()) {
CLASS(printbuf, buf)();
bch2_bpos_to_text(&buf, end);
prt_newline(&buf);
- bch2_bkey_val_to_text(&buf, trans->c, bkey_i_to_s_c(k));
+ bch2_bkey_val_to_text(&buf, trans->c, bkey_i_to_s_c(insert));
trace_extent_trim_atomic(trans->c, buf.buf);
}
- bch2_cut_back(end, k);
+ bch2_cut_back(end, insert);
}
return 0;
}
diff --git a/fs/bcachefs/extent_update.h b/fs/bcachefs/extent_update.h
index 34467db53f45..2d956d971b11 100644
--- a/fs/bcachefs/extent_update.h
+++ b/fs/bcachefs/extent_update.h
@@ -4,8 +4,6 @@
#include "bcachefs.h"
-int bch2_extent_atomic_end(struct btree_trans *, struct btree_iter *,
- struct bpos *);
int bch2_extent_trim_atomic(struct btree_trans *, struct btree_iter *,
struct bkey_i *);
diff --git a/fs/bcachefs/extents.c b/fs/bcachefs/extents.c
index b879a586b7f6..7ab0398707d8 100644
--- a/fs/bcachefs/extents.c
+++ b/fs/bcachefs/extents.c
@@ -995,6 +995,22 @@ void bch2_bkey_drop_device_noerror(struct bkey_s k, unsigned dev)
bch2_bkey_drop_ptrs_noerror(k, ptr, ptr->dev == dev);
}
+void bch2_bkey_drop_ec(struct bkey_i *k, unsigned dev)
+{
+ struct bkey_ptrs ptrs = bch2_bkey_ptrs(bkey_i_to_s(k));
+ union bch_extent_entry *entry, *ec = NULL;
+
+ bkey_extent_entry_for_each(ptrs, entry) {
+ if (extent_entry_type(entry) == BCH_EXTENT_ENTRY_stripe_ptr)
+ ec = entry;
+ else if (extent_entry_type(entry) == BCH_EXTENT_ENTRY_ptr &&
+ entry->ptr.dev == dev) {
+ bch2_bkey_extent_entry_drop(k, ec);
+ return;
+ }
+ }
+}
+
const struct bch_extent_ptr *bch2_bkey_has_device_c(struct bkey_s_c k, unsigned dev)
{
struct bkey_ptrs_c ptrs = bch2_bkey_ptrs_c(k);
@@ -1757,3 +1773,4 @@ int bch2_cut_back_s(struct bpos where, struct bkey_s k)
memset(bkey_val_end(k), 0, val_u64s_delta * sizeof(u64));
return -val_u64s_delta;
}
+
diff --git a/fs/bcachefs/extents.h b/fs/bcachefs/extents.h
index 35ee03cd5065..f6dcb17108cd 100644
--- a/fs/bcachefs/extents.h
+++ b/fs/bcachefs/extents.h
@@ -650,6 +650,7 @@ void bch2_bkey_drop_ptr(struct bkey_s, struct bch_extent_ptr *);
void bch2_bkey_drop_device_noerror(struct bkey_s, unsigned);
void bch2_bkey_drop_device(struct bkey_s, unsigned);
+void bch2_bkey_drop_ec(struct bkey_i *k, unsigned);
#define bch2_bkey_drop_ptrs_noerror(_k, _ptr, _cond) \
do { \
diff --git a/fs/bcachefs/fs-io-buffered.c b/fs/bcachefs/fs-io-buffered.c
index 1630590068a7..456a624fe0eb 100644
--- a/fs/bcachefs/fs-io-buffered.c
+++ b/fs/bcachefs/fs-io-buffered.c
@@ -759,7 +759,6 @@ int bch2_write_end(const struct kiocb *iocb, struct address_space *mapping,
struct bch2_folio_reservation *res = fsdata;
unsigned offset = pos - folio_pos(folio);
- lockdep_assert_held(&inode->v.i_rwsem);
BUG_ON(offset + copied > folio_size(folio));
if (unlikely(copied < len && !folio_test_uptodate(folio))) {
diff --git a/fs/bcachefs/fs.c b/fs/bcachefs/fs.c
index d768a7e7a204..beb2edbd0cf8 100644
--- a/fs/bcachefs/fs.c
+++ b/fs/bcachefs/fs.c
@@ -268,7 +268,7 @@ restart:
rht_for_each_entry_rcu_from(inode, he, rht_ptr_rcu(bkt), tbl, hash, hash) {
if (inode->ei_inum.inum == inum) {
ret = darray_push_gfp(&subvols, inode->ei_inum.subvol,
- GFP_NOWAIT|__GFP_NOWARN);
+ GFP_NOWAIT);
if (ret) {
rcu_read_unlock();
ret = darray_make_room(&subvols, 1);
@@ -511,8 +511,8 @@ struct inode *bch2_vfs_inode_get(struct bch_fs *c, subvol_inum inum)
struct bch_subvolume subvol;
int ret = lockrestart_do(trans,
bch2_subvolume_get(trans, inum.subvol, true, &subvol) ?:
- bch2_inode_find_by_inum_trans(trans, inum, &inode_u)) ?:
- PTR_ERR_OR_ZERO(inode = bch2_inode_hash_init_insert(trans, inum, &inode_u, &subvol));
+ bch2_inode_find_by_inum_trans(trans, inum, &inode_u) ?:
+ PTR_ERR_OR_ZERO(inode = bch2_inode_hash_init_insert(trans, inum, &inode_u, &subvol)));
return ret ? ERR_PTR(ret) : &inode->v;
}
@@ -826,14 +826,6 @@ int __bch2_unlink(struct inode *vdir, struct dentry *dentry,
bch2_inode_update_after_write(trans, inode, &inode_u,
ATTR_MTIME);
- if (inode_u.bi_subvol) {
- /*
- * Subvolume deletion is asynchronous, but we still want to tell
- * the VFS that it's been deleted here:
- */
- set_nlink(&inode->v, 0);
- }
-
if (IS_CASEFOLDED(vdir))
d_invalidate(dentry);
err:
@@ -865,9 +857,7 @@ static int bch2_symlink(struct mnt_idmap *idmap,
if (IS_ERR(inode))
return bch2_err_class(PTR_ERR(inode));
- inode_lock(&inode->v);
ret = page_symlink(&inode->v, symname, strlen(symname) + 1);
- inode_unlock(&inode->v);
if (unlikely(ret))
goto err;
diff --git a/fs/bcachefs/fsck.c b/fs/bcachefs/fsck.c
index d6fd25f1db1f..01c1c6372229 100644
--- a/fs/bcachefs/fsck.c
+++ b/fs/bcachefs/fsck.c
@@ -923,9 +923,10 @@ lookup_inode_for_snapshot(struct btree_trans *trans, struct inode_walker *w, str
bkey_init(&whiteout.k);
whiteout.k.type = KEY_TYPE_whiteout;
whiteout.k.p = SPOS(0, i->inode.bi_inum, k.k->p.snapshot);
- ret = bch2_btree_insert_nonextent(trans, BTREE_ID_inodes,
- &whiteout,
- BTREE_UPDATE_internal_snapshot_node);
+ ret = bch2_btree_insert_trans(trans, BTREE_ID_inodes,
+ &whiteout,
+ BTREE_ITER_cached|
+ BTREE_UPDATE_internal_snapshot_node);
}
if (ret)
@@ -1443,7 +1444,7 @@ static int check_key_has_inode(struct btree_trans *trans,
if (ret)
return ret;
- if (k.k->type == KEY_TYPE_whiteout)
+ if (bkey_extent_whiteout(k.k))
return 0;
bool have_inode = i && !i->whiteout;
@@ -1923,7 +1924,9 @@ static int check_extent(struct btree_trans *trans, struct btree_iter *iter,
&inode->recalculate_sums);
if (ret)
goto err;
+ }
+ if (!bkey_extent_whiteout(k.k)) {
/*
* Check inodes in reverse order, from oldest snapshots to
* newest, starting from the inode that matches this extent's
@@ -2121,6 +2124,7 @@ static int check_dirent_to_subvol(struct btree_trans *trans, struct btree_iter *
struct bkey_s_c_dirent d)
{
struct bch_fs *c = trans->c;
+ struct btree_iter subvol_iter = {};
struct bch_inode_unpacked subvol_root;
u32 parent_subvol = le32_to_cpu(d.v->d_parent_subvol);
u32 target_subvol = le32_to_cpu(d.v->d_child_subvol);
@@ -2177,18 +2181,19 @@ static int check_dirent_to_subvol(struct btree_trans *trans, struct btree_iter *
new_dirent->v.d_parent_subvol = cpu_to_le32(new_parent_subvol);
}
- CLASS(btree_iter, subvol_iter)(trans, BTREE_ID_subvolumes, POS(0, target_subvol), 0);
+ bch2_trans_iter_init(trans, &subvol_iter, BTREE_ID_subvolumes, POS(0, target_subvol), 0);
struct bkey_s_c_subvolume s = bch2_bkey_get_typed(&subvol_iter, subvolume);
ret = bkey_err(s.s_c);
if (ret && !bch2_err_matches(ret, ENOENT))
- return ret;
+ goto err;
if (ret) {
if (fsck_err(trans, dirent_to_missing_subvol,
"dirent points to missing subvolume\n%s",
(bch2_bkey_val_to_text(&buf, c, d.s_c), buf.buf)))
return bch2_fsck_remove_dirent(trans, d.k->p);
- return 0;
+ ret = 0;
+ goto out;
}
if (le32_to_cpu(s.v->fs_path_parent) != parent_subvol) {
@@ -2200,7 +2205,7 @@ static int check_dirent_to_subvol(struct btree_trans *trans, struct btree_iter *
ret = bch2_inum_to_path(trans, (subvol_inum) { s.k->p.offset,
le64_to_cpu(s.v->inode) }, &buf);
if (ret)
- return ret;
+ goto err;
prt_newline(&buf);
bch2_bkey_val_to_text(&buf, c, s.s_c);
@@ -2209,7 +2214,7 @@ static int check_dirent_to_subvol(struct btree_trans *trans, struct btree_iter *
bch2_bkey_make_mut_typed(trans, &subvol_iter, &s.s_c, 0, subvolume);
ret = PTR_ERR_OR_ZERO(n);
if (ret)
- return ret;
+ goto err;
n->v.fs_path_parent = cpu_to_le32(parent_subvol);
}
@@ -2221,11 +2226,12 @@ static int check_dirent_to_subvol(struct btree_trans *trans, struct btree_iter *
ret = bch2_inode_find_by_inum_snapshot(trans, target_inum, target_snapshot,
&subvol_root, 0);
if (ret && !bch2_err_matches(ret, ENOENT))
- return ret;
+ goto err;
if (ret) {
bch_err(c, "subvol %u points to missing inode root %llu", target_subvol, target_inum);
- return bch_err_throw(c, fsck_repair_unimplemented);
+ ret = bch_err_throw(c, fsck_repair_unimplemented);
+ goto err;
}
if (fsck_err_on(!ret && parent_subvol != subvol_root.bi_parent_subvol,
@@ -2237,13 +2243,16 @@ static int check_dirent_to_subvol(struct btree_trans *trans, struct btree_iter *
subvol_root.bi_snapshot = le32_to_cpu(s.v->snapshot);
ret = __bch2_fsck_write_inode(trans, &subvol_root);
if (ret)
- return ret;
+ goto err;
}
ret = bch2_check_dirent_target(trans, iter, d, &subvol_root, true);
if (ret)
- return ret;
+ goto err;
+out:
+err:
fsck_err:
+ bch2_trans_iter_exit(&subvol_iter);
return ret;
}
diff --git a/fs/bcachefs/inode.c b/fs/bcachefs/inode.c
index 85013e8d6166..d5e5190f0663 100644
--- a/fs/bcachefs/inode.c
+++ b/fs/bcachefs/inode.c
@@ -463,9 +463,10 @@ int __bch2_fsck_write_inode(struct btree_trans *trans, struct bch_inode_unpacked
bch2_inode_pack(inode_p, inode);
inode_p->inode.k.p.snapshot = inode->bi_snapshot;
- return bch2_btree_insert_nonextent(trans, BTREE_ID_inodes,
- &inode_p->inode.k_i,
- BTREE_UPDATE_internal_snapshot_node);
+ return bch2_btree_insert_trans(trans, BTREE_ID_inodes,
+ &inode_p->inode.k_i,
+ BTREE_ITER_cached|
+ BTREE_UPDATE_internal_snapshot_node);
}
int bch2_fsck_write_inode(struct btree_trans *trans, struct bch_inode_unpacked *inode)
diff --git a/fs/bcachefs/io_misc.c b/fs/bcachefs/io_misc.c
index 3f9defd144a4..fa0b06e17d17 100644
--- a/fs/bcachefs/io_misc.c
+++ b/fs/bcachefs/io_misc.c
@@ -274,13 +274,15 @@ static int __bch2_resume_logged_op_truncate(struct btree_trans *trans,
if (ret)
goto err;
- CLASS(btree_iter, fpunch_iter)(trans, BTREE_ID_extents,
- POS(inum.inum, round_up(new_i_size, block_bytes(c)) >> 9),
- BTREE_ITER_intent);
- ret = bch2_fpunch_at(trans, &fpunch_iter, inum, U64_MAX, i_sectors_delta);
+ {
+ CLASS(btree_iter, fpunch_iter)(trans, BTREE_ID_extents,
+ POS(inum.inum, round_up(new_i_size, block_bytes(c)) >> 9),
+ BTREE_ITER_intent);
+ ret = bch2_fpunch_at(trans, &fpunch_iter, inum, U64_MAX, i_sectors_delta);
- if (bch2_err_matches(ret, BCH_ERR_transaction_restart))
- ret = 0;
+ if (bch2_err_matches(ret, BCH_ERR_transaction_restart))
+ ret = 0;
+ }
err:
if (warn_errors)
bch_err_fn(c, ret);
diff --git a/fs/bcachefs/logged_ops.h b/fs/bcachefs/logged_ops.h
index 30ae9ef737dd..6dea6e2ac7a8 100644
--- a/fs/bcachefs/logged_ops.h
+++ b/fs/bcachefs/logged_ops.h
@@ -10,7 +10,7 @@
static inline int bch2_logged_op_update(struct btree_trans *trans, struct bkey_i *op)
{
- return bch2_btree_insert_nonextent(trans, BTREE_ID_logged_ops, op, 0);
+ return bch2_btree_insert_trans(trans, BTREE_ID_logged_ops, op, BTREE_ITER_cached);
}
int bch2_resume_logged_ops(struct bch_fs *);
diff --git a/fs/bcachefs/lru.h b/fs/bcachefs/lru.h
index 8abd0aa2083a..6f1e0a7b5db5 100644
--- a/fs/bcachefs/lru.h
+++ b/fs/bcachefs/lru.h
@@ -24,6 +24,16 @@ static inline struct bpos lru_pos(u16 lru_id, u64 dev_bucket, u64 time)
return pos;
}
+static inline struct bpos lru_start(u16 lru_id)
+{
+ return lru_pos(lru_id, 0, 0);
+}
+
+static inline struct bpos lru_end(u16 lru_id)
+{
+ return lru_pos(lru_id, U64_MAX, LRU_TIME_MAX);
+}
+
static inline enum bch_lru_type lru_type(struct bkey_s_c l)
{
u16 lru_id = l.k->p.inode >> 48;
diff --git a/fs/bcachefs/move.c b/fs/bcachefs/move.c
index a38996f5366f..df6833416855 100644
--- a/fs/bcachefs/move.c
+++ b/fs/bcachefs/move.c
@@ -150,7 +150,7 @@ static void move_write_done(struct bch_write_op *op)
bch2_write_op_to_text(&buf, op);
trace_io_move_write_fail(c, buf.buf);
}
- this_cpu_inc(c->counters[BCH_COUNTER_io_move_write_fail]);
+ count_event(c, io_move_write_fail);
ctxt->write_error = true;
}
@@ -344,9 +344,13 @@ int bch2_move_extent(struct moving_context *ctxt,
if (!data_opts.rewrite_ptrs &&
!data_opts.extra_replicas &&
!data_opts.scrub) {
- if (data_opts.kill_ptrs)
+ if (data_opts.kill_ptrs|data_opts.kill_ec_ptrs) {
+ this_cpu_add(c->counters[BCH_COUNTER_io_move_drop_only], k.k->size);
return bch2_extent_drop_ptrs(trans, iter, k, &io_opts, &data_opts);
- return 0;
+ } else {
+ this_cpu_add(c->counters[BCH_COUNTER_io_move_noop], k.k->size);
+ return 0;
+ }
}
struct moving_io *io = allocate_dropping_locks(trans, ret,
@@ -538,7 +542,7 @@ int bch2_move_ratelimit(struct moving_context *ctxt)
if (ctxt->wait_on_copygc && c->copygc_running) {
bch2_moving_ctxt_flush_all(ctxt);
- wait_event_killable(c->copygc_running_wq,
+ wait_event_freezable(c->copygc_running_wq,
!c->copygc_running ||
(is_kthread && kthread_should_stop()));
}
@@ -1276,7 +1280,17 @@ static bool drop_extra_replicas_pred(struct bch_fs *c, void *arg,
i++;
}
- return data_opts->kill_ptrs != 0;
+ i = 0;
+ bkey_for_each_ptr_decode(k.k, bch2_bkey_ptrs_c(k), p, entry) {
+ if (p.has_ec && durability - p.ec.redundancy >= replicas) {
+ data_opts->kill_ec_ptrs |= BIT(i);
+ durability -= p.ec.redundancy;
+ }
+
+ i++;
+ }
+
+ return (data_opts->kill_ptrs|data_opts->kill_ec_ptrs) != 0;
}
static bool scrub_pred(struct bch_fs *c, void *_arg,
diff --git a/fs/bcachefs/movinggc.c b/fs/bcachefs/movinggc.c
index b0cbe3c1aab6..f36d60b8fb07 100644
--- a/fs/bcachefs/movinggc.c
+++ b/fs/bcachefs/movinggc.c
@@ -14,6 +14,7 @@
#include "btree_write_buffer.h"
#include "buckets.h"
#include "clock.h"
+#include "ec.h"
#include "errcode.h"
#include "error.h"
#include "lru.h"
@@ -131,72 +132,153 @@ static bool bucket_in_flight(struct buckets_in_flight *list,
return rhashtable_lookup_fast(list->table, &k, bch_move_bucket_params);
}
+static int try_add_copygc_bucket(struct btree_trans *trans,
+ struct buckets_in_flight *buckets_in_flight,
+ struct bpos bucket, u64 lru_time)
+{
+ struct move_bucket b = { .k.bucket = bucket };
+
+ int ret = bch2_bucket_is_movable(trans, &b, lru_time);
+ if (ret <= 0)
+ return ret;
+
+ if (bucket_in_flight(buckets_in_flight, b.k))
+ return 0;
+
+ struct move_bucket *b_i = kmalloc(sizeof(*b_i), GFP_KERNEL);
+ if (!b_i)
+ return -ENOMEM;
+
+ *b_i = b;
+
+ ret = darray_push(&buckets_in_flight->to_evacuate, b_i);
+ if (ret) {
+ kfree(b_i);
+ return ret;
+ }
+
+ ret = rhashtable_lookup_insert_fast(buckets_in_flight->table, &b_i->hash,
+ bch_move_bucket_params);
+ BUG_ON(ret);
+
+ size_t nr_to_get = max_t(size_t, 16U, buckets_in_flight->nr / 4);
+ return buckets_in_flight->to_evacuate.nr >= nr_to_get;
+}
+
static int bch2_copygc_get_buckets(struct moving_context *ctxt,
struct buckets_in_flight *buckets_in_flight)
{
struct btree_trans *trans = ctxt->trans;
- struct bch_fs *c = trans->c;
- size_t nr_to_get = max_t(size_t, 16U, buckets_in_flight->nr / 4);
- size_t saw = 0, in_flight = 0, not_movable = 0, sectors = 0;
- int ret;
- move_buckets_wait(ctxt, buckets_in_flight, false);
+ int ret = for_each_btree_key_max(trans, iter, BTREE_ID_lru,
+ lru_start(BCH_LRU_BUCKET_FRAGMENTATION),
+ lru_end(BCH_LRU_BUCKET_FRAGMENTATION),
+ 0, k,
+ try_add_copygc_bucket(trans, buckets_in_flight,
+ u64_to_bucket(k.k->p.offset),
+ lru_pos_time(k.k->p))
+ );
- ret = bch2_btree_write_buffer_tryflush(trans);
- if (bch2_err_matches(ret, EROFS))
- return ret;
+ return ret < 0 ? ret : 0;
+}
- if (bch2_fs_fatal_err_on(ret, c, "%s: from bch2_btree_write_buffer_tryflush()", bch2_err_str(ret)))
- return ret;
+static int bch2_copygc_get_stripe_buckets(struct moving_context *ctxt,
+ struct buckets_in_flight *buckets_in_flight)
+{
+ struct btree_trans *trans = ctxt->trans;
- ret = for_each_btree_key_max(trans, iter, BTREE_ID_lru,
- lru_pos(BCH_LRU_BUCKET_FRAGMENTATION, 0, 0),
- lru_pos(BCH_LRU_BUCKET_FRAGMENTATION, U64_MAX, LRU_TIME_MAX),
- 0, k, ({
- struct move_bucket b = { .k.bucket = u64_to_bucket(k.k->p.offset) };
- int ret2 = 0;
+ int ret = for_each_btree_key_max(trans, iter, BTREE_ID_lru,
+ lru_start(BCH_LRU_STRIPE_FRAGMENTATION),
+ lru_end(BCH_LRU_STRIPE_FRAGMENTATION),
+ 0, lru_k, ({
+ CLASS(btree_iter, s_iter)(trans, BTREE_ID_stripes, POS(0, lru_k.k->p.offset), 0);
+ struct bkey_s_c s_k = bch2_btree_iter_peek_slot(&s_iter);
+ int ret2 = bkey_err(s_k);
+ if (ret2)
+ goto err;
- saw++;
+ if (s_k.k->type != KEY_TYPE_stripe)
+ continue;
- ret2 = bch2_bucket_is_movable(trans, &b, lru_pos_time(k.k->p));
- if (ret2 < 0)
- goto err;
+ const struct bch_stripe *s = bkey_s_c_to_stripe(s_k).v;
- if (!ret2)
- not_movable++;
- else if (bucket_in_flight(buckets_in_flight, b.k))
- in_flight++;
- else {
- struct move_bucket *b_i = kmalloc(sizeof(*b_i), GFP_KERNEL);
- ret2 = b_i ? 0 : -ENOMEM;
+ /* write buffer race? */
+ if (stripe_lru_pos(s) != lru_pos_time(lru_k.k->p))
+ continue;
+
+ unsigned nr_data = s->nr_blocks - s->nr_redundant;
+ for (unsigned i = 0; i < nr_data; i++) {
+ if (!stripe_blockcount_get(s, i))
+ continue;
+
+ const struct bch_extent_ptr *ptr = s->ptrs + i;
+ CLASS(bch2_dev_tryget, ca)(trans->c, ptr->dev);
+ if (unlikely(!ca))
+ continue;
+
+ ret2 = try_add_copygc_bucket(trans, buckets_in_flight,
+ PTR_BUCKET_POS(ca, ptr), U64_MAX);
if (ret2)
- goto err;
+ break;
+ }
+err:
+ ret2;
+ }));
- *b_i = b;
+ return ret < 0 ? ret : 0;
+}
+
+static bool should_do_ec_copygc(struct btree_trans *trans)
+{
+ u64 stripe_frag_ratio = 0;
+
+ for_each_btree_key_max(trans, iter, BTREE_ID_lru,
+ lru_start(BCH_LRU_STRIPE_FRAGMENTATION),
+ lru_end(BCH_LRU_STRIPE_FRAGMENTATION),
+ 0, lru_k, ({
+ CLASS(btree_iter, s_iter)(trans, BTREE_ID_stripes, POS(0, lru_k.k->p.offset), 0);
+ struct bkey_s_c s_k = bch2_btree_iter_peek_slot(&s_iter);
+ int ret = bkey_err(s_k);
+ if (ret)
+ goto err;
- ret2 = darray_push(&buckets_in_flight->to_evacuate, b_i);
- if (ret2) {
- kfree(b_i);
- goto err;
- }
+ if (s_k.k->type != KEY_TYPE_stripe)
+ continue;
- ret2 = rhashtable_lookup_insert_fast(buckets_in_flight->table, &b_i->hash,
- bch_move_bucket_params);
- BUG_ON(ret2);
+ const struct bch_stripe *s = bkey_s_c_to_stripe(s_k).v;
- sectors += b.sectors;
- }
+ /* write buffer race? */
+ if (stripe_lru_pos(s) != lru_pos_time(lru_k.k->p))
+ continue;
- ret2 = buckets_in_flight->to_evacuate.nr >= nr_to_get;
+ unsigned nr_data = s->nr_blocks - s->nr_redundant, blocks_nonempty = 0;
+ for (unsigned i = 0; i < nr_data; i++)
+ blocks_nonempty += !!stripe_blockcount_get(s, i);
+
+ /* stripe is pending delete */
+ if (!blocks_nonempty)
+ continue;
+
+ /* This matches the calculation in alloc_lru_idx_fragmentation, so we can
+ * directly compare without actually looking up the bucket pointed to by the
+ * bucket fragmentation lru:
+ */
+ stripe_frag_ratio = div_u64(blocks_nonempty * (1ULL << 31), nr_data);
+ break;
err:
- ret2;
+ ret;
}));
- pr_debug("have: %zu (%zu) saw %zu in flight %zu not movable %zu got %zu (%zu)/%zu buckets ret %i",
- buckets_in_flight->nr, buckets_in_flight->sectors,
- saw, in_flight, not_movable, buckets_in_flight->to_evacuate.nr, sectors, nr_to_get, ret);
+ CLASS(btree_iter, iter)(trans, BTREE_ID_lru, lru_start(BCH_LRU_BUCKET_FRAGMENTATION), 0);
+ struct bkey_s_c lru_k;
- return ret < 0 ? ret : 0;
+ lockrestart_do(trans, bkey_err(lru_k = bch2_btree_iter_peek_max(&iter,
+ lru_end(BCH_LRU_BUCKET_FRAGMENTATION))));
+
+ u64 bucket_frag_ratio = lru_k.k && !bkey_err(lru_k) ? lru_pos_time(lru_k.k->p) : 0;
+
+ /* Prefer normal bucket copygc */
+ return stripe_frag_ratio && stripe_frag_ratio * 2 < bucket_frag_ratio;
}
noinline
@@ -213,7 +295,18 @@ static int bch2_copygc(struct moving_context *ctxt,
u64 sectors_moved = atomic64_read(&ctxt->stats->sectors_moved);
int ret = 0;
- ret = bch2_copygc_get_buckets(ctxt, buckets_in_flight);
+ move_buckets_wait(ctxt, buckets_in_flight, false);
+
+ ret = bch2_btree_write_buffer_tryflush(trans);
+ if (bch2_err_matches(ret, EROFS))
+ goto err;
+
+ if (bch2_fs_fatal_err_on(ret, c, "%s: from bch2_btree_write_buffer_tryflush()", bch2_err_str(ret)))
+ goto err;
+
+ ret = should_do_ec_copygc(trans)
+ ? bch2_copygc_get_stripe_buckets(ctxt, buckets_in_flight)
+ : bch2_copygc_get_buckets(ctxt, buckets_in_flight);
if (ret)
goto err;
@@ -265,7 +358,8 @@ static u64 bch2_copygc_dev_wait_amount(struct bch_dev *ca)
for (unsigned i = 0; i < BCH_DATA_NR; i++)
if (data_type_movable(i))
- fragmented += usage_full.d[i].fragmented;
+ fragmented += usage_full.d[i].buckets * ca->mi.bucket_size -
+ usage_full.d[i].sectors;
return max(0LL, fragmented_allowed - fragmented);
}
diff --git a/fs/bcachefs/namei.c b/fs/bcachefs/namei.c
index da758c2767ea..d1019052f182 100644
--- a/fs/bcachefs/namei.c
+++ b/fs/bcachefs/namei.c
@@ -743,6 +743,7 @@ static int bch2_check_dirent_inode_dirent(struct btree_trans *trans,
{
struct bch_fs *c = trans->c;
CLASS(printbuf, buf)();
+ struct btree_iter bp_iter = {};
int ret = 0;
if (inode_points_to_dirent(target, d))
@@ -773,8 +774,8 @@ static int bch2_check_dirent_inode_dirent(struct btree_trans *trans,
return __bch2_fsck_write_inode(trans, target);
}
- CLASS(btree_iter, bp_iter)(trans, BTREE_ID_dirents,
- SPOS(target->bi_dir, target->bi_dir_offset, target->bi_snapshot), 0);
+ bch2_trans_iter_init(trans, &bp_iter, BTREE_ID_dirents,
+ SPOS(target->bi_dir, target->bi_dir_offset, target->bi_snapshot), 0);
struct bkey_s_c_dirent bp_dirent = bch2_bkey_get_typed(&bp_iter, dirent);
ret = bkey_err(bp_dirent);
if (ret && !bch2_err_matches(ret, ENOENT))
@@ -824,6 +825,8 @@ static int bch2_check_dirent_inode_dirent(struct btree_trans *trans,
S_ISDIR(target->bi_mode) ? "directory" : "subvolume",
target->bi_inum, target->bi_snapshot, buf.buf);
}
+
+ goto out;
} else {
/*
* hardlinked file with nlink 0:
@@ -837,11 +840,15 @@ static int bch2_check_dirent_inode_dirent(struct btree_trans *trans,
target->bi_nlink++;
target->bi_flags &= ~BCH_INODE_unlinked;
ret = __bch2_fsck_write_inode(trans, target);
+ if (ret)
+ goto err;
}
}
}
+out:
err:
fsck_err:
+ bch2_trans_iter_exit(&bp_iter);
bch_err_fn(c, ret);
return ret;
}
diff --git a/fs/bcachefs/rebalance.c b/fs/bcachefs/rebalance.c
index c0c5fe961a83..17ca56b0e2ac 100644
--- a/fs/bcachefs/rebalance.c
+++ b/fs/bcachefs/rebalance.c
@@ -292,12 +292,48 @@ static int bch2_clear_rebalance_needs_scan(struct btree_trans *trans, u64 inum,
: 0;
}
-static struct bkey_s_c next_rebalance_entry(struct btree_trans *trans,
- struct btree_iter *work_iter)
+#define REBALANCE_WORK_BUF_NR 1024
+DEFINE_DARRAY_NAMED(darray_rebalance_work, struct bkey_i_cookie);
+
+static struct bkey_i *next_rebalance_entry(struct btree_trans *trans,
+ darray_rebalance_work *buf, struct bpos *work_pos)
{
- return !kthread_should_stop()
- ? bch2_btree_iter_peek(work_iter)
- : bkey_s_c_null;
+ if (unlikely(!buf->nr)) {
+ /*
+ * Avoid contention with write buffer flush: buffer up rebalance
+ * work entries in a darray
+ */
+
+ BUG_ON(!buf->size);;
+
+ bch2_trans_begin(trans);
+
+ for_each_btree_key(trans, iter, BTREE_ID_rebalance_work, *work_pos,
+ BTREE_ITER_all_snapshots|BTREE_ITER_prefetch, k, ({
+ /* we previously used darray_make_room */
+ BUG_ON(bkey_bytes(k.k) > sizeof(buf->data[0]));
+
+ bkey_reassemble(&darray_top(*buf).k_i, k);
+ buf->nr++;
+
+ *work_pos = bpos_successor(iter.pos);
+ if (buf->nr == buf->size)
+ break;
+ 0;
+ }));
+
+ if (!buf->nr)
+ return NULL;
+
+ unsigned l = 0, r = buf->nr - 1;
+ while (l < r) {
+ swap(buf->data[l], buf->data[r]);
+ l++;
+ --r;
+ }
+ }
+
+ return &(&darray_pop(buf))->k_i;
}
static int bch2_bkey_clear_needs_rebalance(struct btree_trans *trans,
@@ -464,10 +500,9 @@ static int do_rebalance_scan(struct moving_context *ctxt, u64 inum, u64 cookie)
per_snapshot_io_opts_init(&snapshot_io_opts, c);
int ret = for_each_btree_key_max(trans, iter, BTREE_ID_extents,
- r->scan_start.pos, r->scan_end.pos,
- BTREE_ITER_all_snapshots|
- BTREE_ITER_not_extents|
- BTREE_ITER_prefetch, k, ({
+ r->scan_start.pos, r->scan_end.pos,
+ BTREE_ITER_all_snapshots|
+ BTREE_ITER_prefetch, k, ({
ctxt->stats->pos = BBPOS(iter.btree_id, iter.pos);
struct bch_io_opts *io_opts = bch2_move_get_io_opts(trans,
@@ -524,49 +559,37 @@ static int do_rebalance(struct moving_context *ctxt)
struct btree_trans *trans = ctxt->trans;
struct bch_fs *c = trans->c;
struct bch_fs_rebalance *r = &c->rebalance;
- struct btree_iter extent_iter = { NULL };
- struct bkey_s_c k;
+ struct btree_iter extent_iter = {};
u32 kick = r->kick;
- int ret = 0;
- bch2_trans_begin(trans);
+ struct bpos work_pos = POS_MIN;
+ CLASS(darray_rebalance_work, work)();
+ int ret = darray_make_room(&work, REBALANCE_WORK_BUF_NR);
+ if (ret)
+ return ret;
bch2_move_stats_init(&r->work_stats, "rebalance_work");
bch2_move_stats_init(&r->scan_stats, "rebalance_scan");
- CLASS(btree_iter, rebalance_work_iter)(trans,
- BTREE_ID_rebalance_work, POS_MIN,
- BTREE_ITER_all_snapshots);
-
while (!bch2_move_ratelimit(ctxt)) {
if (!bch2_rebalance_enabled(c)) {
bch2_moving_ctxt_flush_all(ctxt);
kthread_wait_freezable(bch2_rebalance_enabled(c) ||
kthread_should_stop());
+ if (kthread_should_stop())
+ break;
}
- if (kthread_should_stop())
+ struct bkey_i *k = next_rebalance_entry(trans, &work, &work_pos);
+ if (!k)
break;
- bch2_trans_begin(trans);
-
- ret = bkey_err(k = next_rebalance_entry(trans, &rebalance_work_iter));
- if (bch2_err_matches(ret, BCH_ERR_transaction_restart))
- continue;
- if (ret || !k.k)
- break;
-
- ret = k.k->type == KEY_TYPE_cookie
- ? do_rebalance_scan(ctxt, k.k->p.inode,
- le64_to_cpu(bkey_s_c_to_cookie(k).v->cookie))
- : do_rebalance_extent(ctxt, k.k->p, &extent_iter);
-
- if (bch2_err_matches(ret, BCH_ERR_transaction_restart))
- continue;
+ ret = k->k.type == KEY_TYPE_cookie
+ ? do_rebalance_scan(ctxt, k->k.p.inode,
+ le64_to_cpu(bkey_i_to_cookie(k)->v.cookie))
+ : lockrestart_do(trans, do_rebalance_extent(ctxt, k->k.p, &extent_iter));
if (ret)
break;
-
- bch2_btree_iter_advance(&rebalance_work_iter);
}
bch2_trans_iter_exit(&extent_iter);
diff --git a/fs/bcachefs/recovery.c b/fs/bcachefs/recovery.c
index c57ff235a97a..29e81f96db0f 100644
--- a/fs/bcachefs/recovery.c
+++ b/fs/bcachefs/recovery.c
@@ -607,7 +607,7 @@ static int read_btree_roots(struct bch_fs *c)
c, btree_root_read_error,
"error reading btree root %s: %s",
buf.buf, bch2_err_str(ret))) {
- if (btree_id_is_alloc(i))
+ if (btree_id_can_reconstruct(i))
r->error = 0;
ret = 0;
}
@@ -626,93 +626,6 @@ fsck_err:
return ret;
}
-static bool check_version_upgrade(struct bch_fs *c)
-{
- unsigned latest_version = bcachefs_metadata_version_current;
- unsigned latest_compatible = min(latest_version,
- bch2_latest_compatible_version(c->sb.version));
- unsigned old_version = c->sb.version_upgrade_complete ?: c->sb.version;
- unsigned new_version = 0;
- bool ret = false;
-
- if (old_version < bcachefs_metadata_required_upgrade_below) {
- if (c->opts.version_upgrade == BCH_VERSION_UPGRADE_incompatible ||
- latest_compatible < bcachefs_metadata_required_upgrade_below)
- new_version = latest_version;
- else
- new_version = latest_compatible;
- } else {
- switch (c->opts.version_upgrade) {
- case BCH_VERSION_UPGRADE_compatible:
- new_version = latest_compatible;
- break;
- case BCH_VERSION_UPGRADE_incompatible:
- new_version = latest_version;
- break;
- case BCH_VERSION_UPGRADE_none:
- new_version = min(old_version, latest_version);
- break;
- }
- }
-
- if (new_version > old_version) {
- CLASS(printbuf, buf)();
-
- if (old_version < bcachefs_metadata_required_upgrade_below)
- prt_str(&buf, "Version upgrade required:\n");
-
- if (old_version != c->sb.version) {
- prt_str(&buf, "Version upgrade from ");
- bch2_version_to_text(&buf, c->sb.version_upgrade_complete);
- prt_str(&buf, " to ");
- bch2_version_to_text(&buf, c->sb.version);
- prt_str(&buf, " incomplete\n");
- }
-
- prt_printf(&buf, "Doing %s version upgrade from ",
- BCH_VERSION_MAJOR(old_version) != BCH_VERSION_MAJOR(new_version)
- ? "incompatible" : "compatible");
- bch2_version_to_text(&buf, old_version);
- prt_str(&buf, " to ");
- bch2_version_to_text(&buf, new_version);
- prt_newline(&buf);
-
- struct bch_sb_field_ext *ext = bch2_sb_field_get(c->disk_sb.sb, ext);
- __le64 passes = ext->recovery_passes_required[0];
- bch2_sb_set_upgrade(c, old_version, new_version);
- passes = ext->recovery_passes_required[0] & ~passes;
-
- if (passes) {
- prt_str(&buf, " running recovery passes: ");
- prt_bitflags(&buf, bch2_recovery_passes,
- bch2_recovery_passes_from_stable(le64_to_cpu(passes)));
- }
-
- bch_notice(c, "%s", buf.buf);
- ret = true;
- }
-
- if (new_version > c->sb.version_incompat_allowed &&
- c->opts.version_upgrade == BCH_VERSION_UPGRADE_incompatible) {
- CLASS(printbuf, buf)();
-
- prt_str(&buf, "Now allowing incompatible features up to ");
- bch2_version_to_text(&buf, new_version);
- prt_str(&buf, ", previously allowed up to ");
- bch2_version_to_text(&buf, c->sb.version_incompat_allowed);
- prt_newline(&buf);
-
- bch_notice(c, "%s", buf.buf);
- ret = true;
- }
-
- if (ret)
- bch2_sb_upgrade(c, new_version,
- c->opts.version_upgrade == BCH_VERSION_UPGRADE_incompatible);
-
- return ret;
-}
-
int bch2_fs_recovery(struct bch_fs *c)
{
struct bch_sb_field_clean *clean = NULL;
@@ -732,108 +645,6 @@ int bch2_fs_recovery(struct bch_fs *c)
bch_info(c, "recovering from unclean shutdown");
}
- if (!(c->sb.features & (1ULL << BCH_FEATURE_new_extent_overwrite))) {
- bch_err(c, "feature new_extent_overwrite not set, filesystem no longer supported");
- ret = -EINVAL;
- goto err;
- }
-
- if (!c->sb.clean &&
- !(c->sb.features & (1ULL << BCH_FEATURE_extents_above_btree_updates))) {
- bch_err(c, "filesystem needs recovery from older version; run fsck from older bcachefs-tools to fix");
- ret = -EINVAL;
- goto err;
- }
-
- if (c->opts.norecovery) {
- c->opts.recovery_pass_last = c->opts.recovery_pass_last
- ? min(c->opts.recovery_pass_last, BCH_RECOVERY_PASS_snapshots_read)
- : BCH_RECOVERY_PASS_snapshots_read;
- c->opts.nochanges = true;
- }
-
- if (c->opts.nochanges)
- c->opts.read_only = true;
-
- if (c->opts.journal_rewind) {
- bch_info(c, "rewinding journal, fsck required");
- c->opts.fsck = true;
- }
-
- if (go_rw_in_recovery(c)) {
- /*
- * start workqueues/kworkers early - kthread creation checks for
- * pending signals, which is _very_ annoying
- */
- ret = bch2_fs_init_rw(c);
- if (ret)
- goto err;
- }
-
- mutex_lock(&c->sb_lock);
- struct bch_sb_field_ext *ext = bch2_sb_field_get(c->disk_sb.sb, ext);
- bool write_sb = false;
-
- if (BCH_SB_HAS_TOPOLOGY_ERRORS(c->disk_sb.sb)) {
- ext->recovery_passes_required[0] |=
- cpu_to_le64(bch2_recovery_passes_to_stable(BIT_ULL(BCH_RECOVERY_PASS_check_topology)));
- write_sb = true;
- }
-
- u64 sb_passes = bch2_recovery_passes_from_stable(le64_to_cpu(ext->recovery_passes_required[0]));
- if (sb_passes) {
- CLASS(printbuf, buf)();
- prt_str(&buf, "superblock requires following recovery passes to be run:\n ");
- prt_bitflags(&buf, bch2_recovery_passes, sb_passes);
- bch_info(c, "%s", buf.buf);
- }
-
- if (bch2_check_version_downgrade(c)) {
- CLASS(printbuf, buf)();
-
- prt_str(&buf, "Version downgrade required:");
-
- __le64 passes = ext->recovery_passes_required[0];
- bch2_sb_set_downgrade(c,
- BCH_VERSION_MINOR(bcachefs_metadata_version_current),
- BCH_VERSION_MINOR(c->sb.version));
- passes = ext->recovery_passes_required[0] & ~passes;
- if (passes) {
- prt_str(&buf, "\n running recovery passes: ");
- prt_bitflags(&buf, bch2_recovery_passes,
- bch2_recovery_passes_from_stable(le64_to_cpu(passes)));
- }
-
- bch_info(c, "%s", buf.buf);
- write_sb = true;
- }
-
- if (check_version_upgrade(c))
- write_sb = true;
-
- c->opts.recovery_passes |= bch2_recovery_passes_from_stable(le64_to_cpu(ext->recovery_passes_required[0]));
-
- if (c->sb.version_upgrade_complete < bcachefs_metadata_version_autofix_errors) {
- SET_BCH_SB_ERROR_ACTION(c->disk_sb.sb, BCH_ON_ERROR_fix_safe);
- write_sb = true;
- }
-
- if (write_sb)
- bch2_write_super(c);
- mutex_unlock(&c->sb_lock);
-
- if (c->sb.clean)
- set_bit(BCH_FS_clean_recovery, &c->flags);
- if (c->opts.fsck)
- set_bit(BCH_FS_in_fsck, &c->flags);
- set_bit(BCH_FS_in_recovery, &c->flags);
-
- ret = bch2_blacklist_table_initialize(c);
- if (ret) {
- bch_err(c, "error initializing blacklist table");
- goto err;
- }
-
bch2_journal_pos_from_member_info_resume(c);
if (!c->sb.clean || c->opts.retain_recovery_info) {
@@ -1053,8 +864,8 @@ use_clean:
}
mutex_lock(&c->sb_lock);
- ext = bch2_sb_field_get(c->disk_sb.sb, ext);
- write_sb = false;
+ struct bch_sb_field_ext *ext = bch2_sb_field_get(c->disk_sb.sb, ext);
+ bool write_sb = false;
if (BCH_SB_VERSION_UPGRADE_COMPLETE(c->disk_sb.sb) != le16_to_cpu(c->disk_sb.sb->version)) {
SET_BCH_SB_VERSION_UPGRADE_COMPLETE(c->disk_sb.sb, le16_to_cpu(c->disk_sb.sb->version));
diff --git a/fs/bcachefs/sb-counters_format.h b/fs/bcachefs/sb-counters_format.h
index 2e3a56bfd085..44bc12573a0c 100644
--- a/fs/bcachefs/sb-counters_format.h
+++ b/fs/bcachefs/sb-counters_format.h
@@ -31,6 +31,8 @@ enum counters_flags {
x(io_move_fail, 38, TYPE_COUNTER) \
x(io_move_write_fail, 82, TYPE_COUNTER) \
x(io_move_start_fail, 39, TYPE_COUNTER) \
+ x(io_move_drop_only, 91, TYPE_COUNTER) \
+ x(io_move_noop, 92, TYPE_COUNTER) \
x(io_move_created_rebalance, 83, TYPE_COUNTER) \
x(io_move_evacuate_bucket, 84, TYPE_COUNTER) \
x(bucket_invalidate, 3, TYPE_COUNTER) \
@@ -99,7 +101,9 @@ enum counters_flags {
x(trans_restart_write_buffer_flush, 75, TYPE_COUNTER) \
x(trans_restart_split_race, 76, TYPE_COUNTER) \
x(write_buffer_flush_slowpath, 77, TYPE_COUNTER) \
- x(write_buffer_flush_sync, 78, TYPE_COUNTER)
+ x(write_buffer_flush_sync, 78, TYPE_COUNTER) \
+ x(accounting_key_to_wb_slowpath, 94, TYPE_COUNTER) \
+ x(error_throw, 93, TYPE_COUNTER)
enum bch_persistent_counters {
#define x(t, n, ...) BCH_COUNTER_##t,
diff --git a/fs/bcachefs/sb-errors_format.h b/fs/bcachefs/sb-errors_format.h
index dd4ee46606d7..5317b1bfe2e5 100644
--- a/fs/bcachefs/sb-errors_format.h
+++ b/fs/bcachefs/sb-errors_format.h
@@ -76,6 +76,8 @@ enum bch_fsck_flags {
x(btree_node_read_error, 62, FSCK_AUTOFIX) \
x(btree_node_topology_bad_min_key, 63, FSCK_AUTOFIX) \
x(btree_node_topology_bad_max_key, 64, FSCK_AUTOFIX) \
+ x(btree_node_topology_bad_root_min_key, 323, FSCK_AUTOFIX) \
+ x(btree_node_topology_bad_root_max_key, 324, FSCK_AUTOFIX) \
x(btree_node_topology_overwritten_by_prev_node, 65, FSCK_AUTOFIX) \
x(btree_node_topology_overwritten_by_next_node, 66, FSCK_AUTOFIX) \
x(btree_node_topology_interior_node_empty, 67, FSCK_AUTOFIX) \
@@ -334,7 +336,7 @@ enum bch_fsck_flags {
x(dirent_stray_data_after_cf_name, 305, 0) \
x(rebalance_work_incorrectly_set, 309, FSCK_AUTOFIX) \
x(rebalance_work_incorrectly_unset, 310, FSCK_AUTOFIX) \
- x(MAX, 323, 0)
+ x(MAX, 325, 0)
enum bch_sb_error_id {
#define x(t, n, ...) BCH_FSCK_ERR_##t = n,
diff --git a/fs/bcachefs/sb-members.c b/fs/bcachefs/sb-members.c
index 0573c7b00151..e3c73d903898 100644
--- a/fs/bcachefs/sb-members.c
+++ b/fs/bcachefs/sb-members.c
@@ -68,34 +68,13 @@ struct bch_member *bch2_members_v2_get_mut(struct bch_sb *sb, int i)
return __bch2_members_v2_get_mut(bch2_sb_field_get(sb, members_v2), i);
}
-static struct bch_member members_v2_get(struct bch_sb_field_members_v2 *mi, int i)
-{
- struct bch_member ret, *p = __bch2_members_v2_get_mut(mi, i);
- memset(&ret, 0, sizeof(ret));
- memcpy(&ret, p, min_t(size_t, le16_to_cpu(mi->member_bytes), sizeof(ret)));
- return ret;
-}
-
-static struct bch_member *members_v1_get_mut(struct bch_sb_field_members_v1 *mi, int i)
-{
- return (void *) mi->_members + (i * BCH_MEMBER_V1_BYTES);
-}
-
-static struct bch_member members_v1_get(struct bch_sb_field_members_v1 *mi, int i)
-{
- struct bch_member ret, *p = members_v1_get_mut(mi, i);
- memset(&ret, 0, sizeof(ret));
- memcpy(&ret, p, min_t(size_t, BCH_MEMBER_V1_BYTES, sizeof(ret)));
- return ret;
-}
-
struct bch_member bch2_sb_member_get(struct bch_sb *sb, int i)
{
struct bch_sb_field_members_v2 *mi2 = bch2_sb_field_get(sb, members_v2);
if (mi2)
- return members_v2_get(mi2, i);
+ return bch2_members_v2_get(mi2, i);
struct bch_sb_field_members_v1 *mi1 = bch2_sb_field_get(sb, members_v1);
- return members_v1_get(mi1, i);
+ return bch2_members_v1_get(mi1, i);
}
static int sb_members_v2_resize_entries(struct bch_fs *c)
@@ -211,33 +190,25 @@ static int validate_member(struct printbuf *err,
return 0;
}
-static void member_to_text(struct printbuf *out,
- struct bch_member m,
- struct bch_sb_field_disk_groups *gi,
- struct bch_sb *sb,
- int i)
+void bch2_member_to_text(struct printbuf *out,
+ struct bch_member *m,
+ struct bch_sb_field_disk_groups *gi,
+ struct bch_sb *sb,
+ unsigned idx)
{
- unsigned data_have = bch2_sb_dev_has_data(sb, i);
- u64 bucket_size = le16_to_cpu(m.bucket_size);
- u64 device_size = le64_to_cpu(m.nbuckets) * bucket_size;
-
- if (!bch2_member_alive(&m))
- return;
-
- prt_printf(out, "Device:\t%u\n", i);
-
- printbuf_indent_add(out, 2);
+ u64 bucket_size = le16_to_cpu(m->bucket_size);
+ u64 device_size = le64_to_cpu(m->nbuckets) * bucket_size;
prt_printf(out, "Label:\t");
- if (BCH_MEMBER_GROUP(&m))
+ if (BCH_MEMBER_GROUP(m))
bch2_disk_path_to_text_sb(out, sb,
- BCH_MEMBER_GROUP(&m) - 1);
+ BCH_MEMBER_GROUP(m) - 1);
else
prt_printf(out, "(none)");
prt_newline(out);
prt_printf(out, "UUID:\t");
- pr_uuid(out, m.uuid.b);
+ pr_uuid(out, m->uuid.b);
prt_newline(out);
prt_printf(out, "Size:\t");
@@ -245,40 +216,41 @@ static void member_to_text(struct printbuf *out,
prt_newline(out);
for (unsigned i = 0; i < BCH_MEMBER_ERROR_NR; i++)
- prt_printf(out, "%s errors:\t%llu\n", bch2_member_error_strs[i], le64_to_cpu(m.errors[i]));
+ prt_printf(out, "%s errors:\t%llu\n", bch2_member_error_strs[i], le64_to_cpu(m->errors[i]));
for (unsigned i = 0; i < BCH_IOPS_NR; i++)
- prt_printf(out, "%s iops:\t%u\n", bch2_iops_measurements[i], le32_to_cpu(m.iops[i]));
+ prt_printf(out, "%s iops:\t%u\n", bch2_iops_measurements[i], le32_to_cpu(m->iops[i]));
prt_printf(out, "Bucket size:\t");
prt_units_u64(out, bucket_size << 9);
prt_newline(out);
- prt_printf(out, "First bucket:\t%u\n", le16_to_cpu(m.first_bucket));
- prt_printf(out, "Buckets:\t%llu\n", le64_to_cpu(m.nbuckets));
+ prt_printf(out, "First bucket:\t%u\n", le16_to_cpu(m->first_bucket));
+ prt_printf(out, "Buckets:\t%llu\n", le64_to_cpu(m->nbuckets));
prt_printf(out, "Last mount:\t");
- if (m.last_mount)
- bch2_prt_datetime(out, le64_to_cpu(m.last_mount));
+ if (m->last_mount)
+ bch2_prt_datetime(out, le64_to_cpu(m->last_mount));
else
prt_printf(out, "(never)");
prt_newline(out);
- prt_printf(out, "Last superblock write:\t%llu\n", le64_to_cpu(m.seq));
+ prt_printf(out, "Last superblock write:\t%llu\n", le64_to_cpu(m->seq));
prt_printf(out, "State:\t%s\n",
- BCH_MEMBER_STATE(&m) < BCH_MEMBER_STATE_NR
- ? bch2_member_states[BCH_MEMBER_STATE(&m)]
+ BCH_MEMBER_STATE(m) < BCH_MEMBER_STATE_NR
+ ? bch2_member_states[BCH_MEMBER_STATE(m)]
: "unknown");
prt_printf(out, "Data allowed:\t");
- if (BCH_MEMBER_DATA_ALLOWED(&m))
- prt_bitflags(out, __bch2_data_types, BCH_MEMBER_DATA_ALLOWED(&m));
+ if (BCH_MEMBER_DATA_ALLOWED(m))
+ prt_bitflags(out, __bch2_data_types, BCH_MEMBER_DATA_ALLOWED(m));
else
prt_printf(out, "(none)");
prt_newline(out);
prt_printf(out, "Has data:\t");
+ unsigned data_have = bch2_sb_dev_has_data(sb, idx);
if (data_have)
prt_bitflags(out, __bch2_data_types, data_have);
else
@@ -286,22 +258,36 @@ static void member_to_text(struct printbuf *out,
prt_newline(out);
prt_printf(out, "Btree allocated bitmap blocksize:\t");
- if (m.btree_bitmap_shift < 64)
- prt_units_u64(out, 1ULL << m.btree_bitmap_shift);
+ if (m->btree_bitmap_shift < 64)
+ prt_units_u64(out, 1ULL << m->btree_bitmap_shift);
else
- prt_printf(out, "(invalid shift %u)", m.btree_bitmap_shift);
+ prt_printf(out, "(invalid shift %u)", m->btree_bitmap_shift);
prt_newline(out);
prt_printf(out, "Btree allocated bitmap:\t");
- bch2_prt_u64_base2_nbits(out, le64_to_cpu(m.btree_allocated_bitmap), 64);
+ bch2_prt_u64_base2_nbits(out, le64_to_cpu(m->btree_allocated_bitmap), 64);
prt_newline(out);
- prt_printf(out, "Durability:\t%llu\n", BCH_MEMBER_DURABILITY(&m) ? BCH_MEMBER_DURABILITY(&m) - 1 : 1);
+ prt_printf(out, "Durability:\t%llu\n", BCH_MEMBER_DURABILITY(m) ? BCH_MEMBER_DURABILITY(m) - 1 : 1);
+
+ prt_printf(out, "Discard:\t%llu\n", BCH_MEMBER_DISCARD(m));
+ prt_printf(out, "Freespace initialized:\t%llu\n", BCH_MEMBER_FREESPACE_INITIALIZED(m));
+ prt_printf(out, "Resize on mount:\t%llu\n", BCH_MEMBER_RESIZE_ON_MOUNT(m));
+}
+
+static void member_to_text(struct printbuf *out,
+ struct bch_member m,
+ struct bch_sb_field_disk_groups *gi,
+ struct bch_sb *sb,
+ unsigned idx)
+{
+ if (!bch2_member_alive(&m))
+ return;
- prt_printf(out, "Discard:\t%llu\n", BCH_MEMBER_DISCARD(&m));
- prt_printf(out, "Freespace initialized:\t%llu\n", BCH_MEMBER_FREESPACE_INITIALIZED(&m));
- prt_printf(out, "Resize on mount:\t%llu\n", BCH_MEMBER_RESIZE_ON_MOUNT(&m));
+ prt_printf(out, "Device:\t%u\n", idx);
+ printbuf_indent_add(out, 2);
+ bch2_member_to_text(out, &m, gi, sb, idx);
printbuf_indent_sub(out, 2);
}
@@ -317,7 +303,7 @@ static int bch2_sb_members_v1_validate(struct bch_sb *sb, struct bch_sb_field *f
}
for (i = 0; i < sb->nr_devices; i++) {
- struct bch_member m = members_v1_get(mi, i);
+ struct bch_member m = bch2_members_v1_get(mi, i);
int ret = validate_member(err, m, sb, i);
if (ret)
@@ -343,7 +329,7 @@ static void bch2_sb_members_v1_to_text(struct printbuf *out, struct bch_sb *sb,
prt_printf(out, "nr_devices mismatch: have %i entries, should be %u", nr, sb->nr_devices);
for (unsigned i = 0; i < min(sb->nr_devices, nr); i++)
- member_to_text(out, members_v1_get(mi, i), gi, sb, i);
+ member_to_text(out, bch2_members_v1_get(mi, i), gi, sb, i);
}
const struct bch_sb_field_ops bch_sb_field_ops_members_v1 = {
@@ -377,7 +363,7 @@ static void bch2_sb_members_v2_to_text(struct printbuf *out, struct bch_sb *sb,
*/
for (unsigned i = 0; i < min(sb->nr_devices, nr); i++)
- member_to_text(out, members_v2_get(mi, i), gi, sb, i);
+ member_to_text(out, bch2_members_v2_get(mi, i), gi, sb, i);
}
static int bch2_sb_members_v2_validate(struct bch_sb *sb, struct bch_sb_field *f,
@@ -394,7 +380,7 @@ static int bch2_sb_members_v2_validate(struct bch_sb *sb, struct bch_sb_field *f
}
for (unsigned i = 0; i < sb->nr_devices; i++) {
- int ret = validate_member(err, members_v2_get(mi, i), sb, i);
+ int ret = validate_member(err, bch2_members_v2_get(mi, i), sb, i);
if (ret)
return ret;
}
@@ -430,7 +416,7 @@ void bch2_sb_members_to_cpu(struct bch_fs *c)
struct bch_sb_field_members_v2 *mi2 = bch2_sb_field_get(c->disk_sb.sb, members_v2);
if (mi2)
for (unsigned i = 0; i < c->sb.nr_devices; i++) {
- struct bch_member m = members_v2_get(mi2, i);
+ struct bch_member m = bch2_members_v2_get(mi2, i);
bool removed = uuid_equal(&m.uuid, &BCH_SB_MEMBER_DELETED_UUID);
mod_bit(i, c->devs_removed.d, removed);
}
diff --git a/fs/bcachefs/sb-members.h b/fs/bcachefs/sb-members.h
index 35d4ab9b6197..6de999cf71cb 100644
--- a/fs/bcachefs/sb-members.h
+++ b/fs/bcachefs/sb-members.h
@@ -14,11 +14,36 @@ __bch2_members_v2_get_mut(struct bch_sb_field_members_v2 *mi, unsigned i)
return (void *) mi->_members + (i * le16_to_cpu(mi->member_bytes));
}
+static inline struct bch_member bch2_members_v2_get(struct bch_sb_field_members_v2 *mi, int i)
+{
+ struct bch_member ret, *p = __bch2_members_v2_get_mut(mi, i);
+ memset(&ret, 0, sizeof(ret));
+ memcpy(&ret, p, min_t(size_t, le16_to_cpu(mi->member_bytes), sizeof(ret)));
+ return ret;
+}
+
+static inline struct bch_member *members_v1_get_mut(struct bch_sb_field_members_v1 *mi, int i)
+{
+ return (void *) mi->_members + (i * BCH_MEMBER_V1_BYTES);
+}
+
+static inline struct bch_member bch2_members_v1_get(struct bch_sb_field_members_v1 *mi, int i)
+{
+ struct bch_member ret, *p = members_v1_get_mut(mi, i);
+ memset(&ret, 0, sizeof(ret));
+ memcpy(&ret, p, min_t(size_t, BCH_MEMBER_V1_BYTES, sizeof(ret)));
+ return ret;
+}
+
int bch2_sb_members_v2_init(struct bch_fs *c);
int bch2_sb_members_cpy_v2_v1(struct bch_sb_handle *disk_sb);
struct bch_member *bch2_members_v2_get_mut(struct bch_sb *sb, int i);
struct bch_member bch2_sb_member_get(struct bch_sb *sb, int i);
+void bch2_member_to_text(struct printbuf *, struct bch_member *,
+ struct bch_sb_field_disk_groups *,
+ struct bch_sb *, unsigned);
+
static inline bool bch2_dev_is_online(struct bch_dev *ca)
{
return !enumerated_ref_is_zero(&ca->io_ref[READ]);
diff --git a/fs/bcachefs/snapshot.c b/fs/bcachefs/snapshot.c
index 5a1f81749661..84f987d3a02a 100644
--- a/fs/bcachefs/snapshot.c
+++ b/fs/bcachefs/snapshot.c
@@ -1146,7 +1146,7 @@ static int bch2_snapshot_node_delete(struct btree_trans *trans, u32 id)
if (bch2_fs_inconsistent_on(i == 2, c,
"snapshot %u missing child pointer to %u",
parent_id, id))
- return ret;
+ return bch_err_throw(c, ENOENT_snapshot);
parent->v.children[i] = cpu_to_le32(child_id);
diff --git a/fs/bcachefs/super-io.c b/fs/bcachefs/super-io.c
index c88759964575..be7ed612d28f 100644
--- a/fs/bcachefs/super-io.c
+++ b/fs/bcachefs/super-io.c
@@ -68,28 +68,33 @@ enum bcachefs_metadata_version bch2_latest_compatible_version(enum bcachefs_meta
int bch2_set_version_incompat(struct bch_fs *c, enum bcachefs_metadata_version version)
{
- guard(mutex)(&c->sb_lock);
-
if (((c->sb.features & BIT_ULL(BCH_FEATURE_incompat_version_field)) &&
version <= c->sb.version_incompat_allowed)) {
- SET_BCH_SB_VERSION_INCOMPAT(c->disk_sb.sb,
- max(BCH_SB_VERSION_INCOMPAT(c->disk_sb.sb), version));
- bch2_write_super(c);
+ guard(mutex)(&c->sb_lock);
+
+ if (version > c->sb.version_incompat) {
+ SET_BCH_SB_VERSION_INCOMPAT(c->disk_sb.sb,
+ max(BCH_SB_VERSION_INCOMPAT(c->disk_sb.sb), version));
+ bch2_write_super(c);
+ }
return 0;
} else {
- darray_for_each(c->incompat_versions_requested, i)
- if (version == *i)
- return bch_err_throw(c, may_not_use_incompat_feature);
+ BUILD_BUG_ON(BCH_VERSION_MAJOR(bcachefs_metadata_version_current) != 1);
- darray_push(&c->incompat_versions_requested, version);
- CLASS(printbuf, buf)();
- prt_str(&buf, "requested incompat feature ");
- bch2_version_to_text(&buf, version);
- prt_str(&buf, " currently not enabled, allowed up to ");
- bch2_version_to_text(&buf, version);
- prt_printf(&buf, "\n set version_upgrade=incompat to enable");
+ unsigned minor = BCH_VERSION_MINOR(version);
+
+ if (!test_bit(minor, c->incompat_versions_requested) &&
+ !test_and_set_bit(minor, c->incompat_versions_requested)) {
+ CLASS(printbuf, buf)();
+ prt_str(&buf, "requested incompat feature ");
+ bch2_version_to_text(&buf, version);
+ prt_str(&buf, " currently not enabled, allowed up to ");
+ bch2_version_to_text(&buf, version);
+ prt_printf(&buf, "\n set version_upgrade=incompat to enable");
+
+ bch_notice(c, "%s", buf.buf);
+ }
- bch_notice(c, "%s", buf.buf);
return bch_err_throw(c, may_not_use_incompat_feature);
}
}
diff --git a/fs/bcachefs/super.c b/fs/bcachefs/super.c
index b3b2d8353a36..ef15e614f4f3 100644
--- a/fs/bcachefs/super.c
+++ b/fs/bcachefs/super.c
@@ -55,6 +55,7 @@
#include "replicas.h"
#include "sb-clean.h"
#include "sb-counters.h"
+#include "sb-downgrade.h"
#include "sb-errors.h"
#include "sb-members.h"
#include "snapshot.h"
@@ -653,7 +654,6 @@ static void __bch2_fs_free(struct bch_fs *c)
free_percpu(c->online_reserved);
}
- darray_exit(&c->incompat_versions_requested);
darray_exit(&c->btree_roots_extra);
free_percpu(c->pcpu);
free_percpu(c->usage);
@@ -843,6 +843,233 @@ int bch2_fs_init_rw(struct bch_fs *c)
return 0;
}
+static bool check_version_upgrade(struct bch_fs *c)
+{
+ unsigned latest_version = bcachefs_metadata_version_current;
+ unsigned latest_compatible = min(latest_version,
+ bch2_latest_compatible_version(c->sb.version));
+ unsigned old_version = c->sb.version_upgrade_complete ?: c->sb.version;
+ unsigned new_version = 0;
+ bool ret = false;
+
+ if (old_version < bcachefs_metadata_required_upgrade_below) {
+ if (c->opts.version_upgrade == BCH_VERSION_UPGRADE_incompatible ||
+ latest_compatible < bcachefs_metadata_required_upgrade_below)
+ new_version = latest_version;
+ else
+ new_version = latest_compatible;
+ } else {
+ switch (c->opts.version_upgrade) {
+ case BCH_VERSION_UPGRADE_compatible:
+ new_version = latest_compatible;
+ break;
+ case BCH_VERSION_UPGRADE_incompatible:
+ new_version = latest_version;
+ break;
+ case BCH_VERSION_UPGRADE_none:
+ new_version = min(old_version, latest_version);
+ break;
+ }
+ }
+
+ if (new_version > old_version) {
+ CLASS(printbuf, buf)();
+
+ if (old_version < bcachefs_metadata_required_upgrade_below)
+ prt_str(&buf, "Version upgrade required:\n");
+
+ if (old_version != c->sb.version) {
+ prt_str(&buf, "Version upgrade from ");
+ bch2_version_to_text(&buf, c->sb.version_upgrade_complete);
+ prt_str(&buf, " to ");
+ bch2_version_to_text(&buf, c->sb.version);
+ prt_str(&buf, " incomplete\n");
+ }
+
+ prt_printf(&buf, "Doing %s version upgrade from ",
+ BCH_VERSION_MAJOR(old_version) != BCH_VERSION_MAJOR(new_version)
+ ? "incompatible" : "compatible");
+ bch2_version_to_text(&buf, old_version);
+ prt_str(&buf, " to ");
+ bch2_version_to_text(&buf, new_version);
+ prt_newline(&buf);
+
+ struct bch_sb_field_ext *ext = bch2_sb_field_get(c->disk_sb.sb, ext);
+ __le64 passes = ext->recovery_passes_required[0];
+ bch2_sb_set_upgrade(c, old_version, new_version);
+ passes = ext->recovery_passes_required[0] & ~passes;
+
+ if (passes) {
+ prt_str(&buf, " running recovery passes: ");
+ prt_bitflags(&buf, bch2_recovery_passes,
+ bch2_recovery_passes_from_stable(le64_to_cpu(passes)));
+ }
+
+ bch_notice(c, "%s", buf.buf);
+ ret = true;
+ }
+
+ if (new_version > c->sb.version_incompat_allowed &&
+ c->opts.version_upgrade == BCH_VERSION_UPGRADE_incompatible) {
+ CLASS(printbuf, buf)();
+
+ prt_str(&buf, "Now allowing incompatible features up to ");
+ bch2_version_to_text(&buf, new_version);
+ prt_str(&buf, ", previously allowed up to ");
+ bch2_version_to_text(&buf, c->sb.version_incompat_allowed);
+ prt_newline(&buf);
+
+ bch_notice(c, "%s", buf.buf);
+ ret = true;
+ }
+
+ if (ret)
+ bch2_sb_upgrade(c, new_version,
+ c->opts.version_upgrade == BCH_VERSION_UPGRADE_incompatible);
+
+ return ret;
+}
+
+noinline_for_stack
+static int bch2_fs_opt_version_init(struct bch_fs *c)
+{
+ int ret = 0;
+
+ if (c->opts.norecovery) {
+ c->opts.recovery_pass_last = c->opts.recovery_pass_last
+ ? min(c->opts.recovery_pass_last, BCH_RECOVERY_PASS_snapshots_read)
+ : BCH_RECOVERY_PASS_snapshots_read;
+ c->opts.nochanges = true;
+ }
+
+ if (c->opts.nochanges)
+ c->opts.read_only = true;
+
+ if (c->opts.journal_rewind)
+ c->opts.fsck = true;
+
+ CLASS(printbuf, p)();
+ bch2_log_msg_start(c, &p);
+
+ prt_str(&p, "starting version ");
+ bch2_version_to_text(&p, c->sb.version);
+
+ bool first = true;
+ for (enum bch_opt_id i = 0; i < bch2_opts_nr; i++) {
+ const struct bch_option *opt = &bch2_opt_table[i];
+ u64 v = bch2_opt_get_by_id(&c->opts, i);
+
+ if (!(opt->flags & OPT_MOUNT))
+ continue;
+
+ if (v == bch2_opt_get_by_id(&bch2_opts_default, i))
+ continue;
+
+ prt_str(&p, first ? " opts=" : ",");
+ first = false;
+ bch2_opt_to_text(&p, c, c->disk_sb.sb, opt, v, OPT_SHOW_MOUNT_STYLE);
+ }
+
+ if (c->sb.version_incompat_allowed != c->sb.version) {
+ prt_printf(&p, "\nallowing incompatible features above ");
+ bch2_version_to_text(&p, c->sb.version_incompat_allowed);
+ }
+
+ if (c->opts.verbose) {
+ prt_printf(&p, "\nfeatures: ");
+ prt_bitflags(&p, bch2_sb_features, c->sb.features);
+ }
+
+ if (c->sb.multi_device) {
+ prt_printf(&p, "\nwith devices");
+ for_each_online_member(c, ca, BCH_DEV_READ_REF_bch2_online_devs) {
+ prt_char(&p, ' ');
+ prt_str(&p, ca->name);
+ }
+ }
+
+ if (c->cf_encoding)
+ prt_printf(&p, "\nUsing encoding defined by superblock: utf8-%u.%u.%u",
+ unicode_major(BCH_FS_DEFAULT_UTF8_ENCODING),
+ unicode_minor(BCH_FS_DEFAULT_UTF8_ENCODING),
+ unicode_rev(BCH_FS_DEFAULT_UTF8_ENCODING));
+
+ if (c->opts.journal_rewind)
+ prt_printf(&p, "\nrewinding journal, fsck required");
+
+ scoped_guard(mutex, &c->sb_lock) {
+ struct bch_sb_field_ext *ext = bch2_sb_field_get_minsize(&c->disk_sb, ext,
+ sizeof(struct bch_sb_field_ext) / sizeof(u64));
+ if (!ext)
+ return bch_err_throw(c, ENOSPC_sb);
+
+ ret = bch2_sb_members_v2_init(c);
+ if (ret)
+ return ret;
+
+ __le64 now = cpu_to_le64(ktime_get_real_seconds());
+ for_each_online_member_rcu(c, ca)
+ bch2_members_v2_get_mut(c->disk_sb.sb, ca->dev_idx)->last_mount = now;
+
+ if (BCH_SB_HAS_TOPOLOGY_ERRORS(c->disk_sb.sb))
+ ext->recovery_passes_required[0] |=
+ cpu_to_le64(bch2_recovery_passes_to_stable(BIT_ULL(BCH_RECOVERY_PASS_check_topology)));
+
+ u64 sb_passes = bch2_recovery_passes_from_stable(le64_to_cpu(ext->recovery_passes_required[0]));
+ if (sb_passes) {
+ prt_str(&p, "\nsuperblock requires following recovery passes to be run:\n ");
+ prt_bitflags(&p, bch2_recovery_passes, sb_passes);
+ }
+
+ if (bch2_check_version_downgrade(c)) {
+ prt_str(&p, "\nVersion downgrade required:");
+
+ __le64 passes = ext->recovery_passes_required[0];
+ bch2_sb_set_downgrade(c,
+ BCH_VERSION_MINOR(bcachefs_metadata_version_current),
+ BCH_VERSION_MINOR(c->sb.version));
+ passes = ext->recovery_passes_required[0] & ~passes;
+ if (passes) {
+ prt_str(&p, "\nrunning recovery passes: ");
+ prt_bitflags(&p, bch2_recovery_passes,
+ bch2_recovery_passes_from_stable(le64_to_cpu(passes)));
+ }
+ }
+
+ check_version_upgrade(c);
+
+ c->opts.recovery_passes |= bch2_recovery_passes_from_stable(le64_to_cpu(ext->recovery_passes_required[0]));
+
+ if (c->sb.version_upgrade_complete < bcachefs_metadata_version_autofix_errors)
+ SET_BCH_SB_ERROR_ACTION(c->disk_sb.sb, BCH_ON_ERROR_fix_safe);
+
+ /* Don't write the superblock, defer that until we go rw */
+ }
+
+ if (c->sb.clean)
+ set_bit(BCH_FS_clean_recovery, &c->flags);
+ if (c->opts.fsck)
+ set_bit(BCH_FS_in_fsck, &c->flags);
+ set_bit(BCH_FS_in_recovery, &c->flags);
+
+ bch2_print_str(c, KERN_INFO, p.buf);
+
+ if (BCH_SB_INITIALIZED(c->disk_sb.sb)) {
+ if (!(c->sb.features & (1ULL << BCH_FEATURE_new_extent_overwrite))) {
+ bch_err(c, "feature new_extent_overwrite not set, filesystem no longer supported");
+ return -EINVAL;
+ }
+
+ if (!c->sb.clean &&
+ !(c->sb.features & (1ULL << BCH_FEATURE_extents_above_btree_updates))) {
+ bch_err(c, "filesystem needs recovery from older version; run fsck from older bcachefs-tools to fix");
+ return -EINVAL;
+ }
+ }
+
+ return 0;
+}
+
static struct bch_fs *bch2_fs_alloc(struct bch_sb *sb, struct bch_opts *opts,
bch_sb_handles *sbs)
{
@@ -1014,6 +1241,7 @@ static struct bch_fs *bch2_fs_alloc(struct bch_sb *sb, struct bch_opts *opts,
ret =
bch2_fs_async_obj_init(c) ?:
+ bch2_blacklist_table_initialize(c) ?:
bch2_fs_btree_cache_init(c) ?:
bch2_fs_btree_iter_init(c) ?:
bch2_fs_btree_key_cache_init(&c->btree_key_cache) ?:
@@ -1064,7 +1292,7 @@ static struct bch_fs *bch2_fs_alloc(struct bch_sb *sb, struct bch_opts *opts,
}
#endif
- for (i = 0; i < c->sb.nr_devices; i++) {
+ for (unsigned i = 0; i < c->sb.nr_devices; i++) {
if (!bch2_member_exists(c->disk_sb.sb, i))
continue;
ret = bch2_dev_alloc(c, i);
@@ -1079,6 +1307,20 @@ static struct bch_fs *bch2_fs_alloc(struct bch_sb *sb, struct bch_opts *opts,
&c->clock_journal_res,
(sizeof(struct jset_entry_clock) / sizeof(u64)) * 2);
+ ret = bch2_fs_opt_version_init(c);
+ if (ret)
+ goto err;
+
+ /*
+ * start workqueues/kworkers early - kthread creation checks for pending
+ * signals, which is _very_ annoying
+ */
+ if (go_rw_in_recovery(c)) {
+ ret = bch2_fs_init_rw(c);
+ if (ret)
+ goto err;
+ }
+
scoped_guard(mutex, &bch_fs_list_lock)
ret = bch2_fs_online(c);
@@ -1094,53 +1336,6 @@ err:
goto out;
}
-noinline_for_stack
-static void print_mount_opts(struct bch_fs *c)
-{
- enum bch_opt_id i;
- CLASS(printbuf, p)();
- bch2_log_msg_start(c, &p);
-
- prt_str(&p, "starting version ");
- bch2_version_to_text(&p, c->sb.version);
-
- bool first = true;
- for (i = 0; i < bch2_opts_nr; i++) {
- const struct bch_option *opt = &bch2_opt_table[i];
- u64 v = bch2_opt_get_by_id(&c->opts, i);
-
- if (!(opt->flags & OPT_MOUNT))
- continue;
-
- if (v == bch2_opt_get_by_id(&bch2_opts_default, i))
- continue;
-
- prt_str(&p, first ? " opts=" : ",");
- first = false;
- bch2_opt_to_text(&p, c, c->disk_sb.sb, opt, v, OPT_SHOW_MOUNT_STYLE);
- }
-
- if (c->sb.version_incompat_allowed != c->sb.version) {
- prt_printf(&p, "\nallowing incompatible features above ");
- bch2_version_to_text(&p, c->sb.version_incompat_allowed);
- }
-
- if (c->opts.verbose) {
- prt_printf(&p, "\nfeatures: ");
- prt_bitflags(&p, bch2_sb_features, c->sb.features);
- }
-
- if (c->sb.multi_device) {
- prt_printf(&p, "\nwith devices");
- for_each_online_member(c, ca, BCH_DEV_READ_REF_bch2_online_devs) {
- prt_char(&p, ' ');
- prt_str(&p, ca->name);
- }
- }
-
- bch2_print_str(c, KERN_INFO, p.buf);
-}
-
static bool bch2_fs_may_start(struct bch_fs *c)
{
struct bch_dev *ca;
@@ -1175,38 +1370,16 @@ static bool bch2_fs_may_start(struct bch_fs *c)
int bch2_fs_start(struct bch_fs *c)
{
- time64_t now = ktime_get_real_seconds();
int ret = 0;
BUG_ON(test_bit(BCH_FS_started, &c->flags));
- print_mount_opts(c);
-
- if (c->cf_encoding)
- bch_info(c, "Using encoding defined by superblock: utf8-%u.%u.%u",
- unicode_major(BCH_FS_DEFAULT_UTF8_ENCODING),
- unicode_minor(BCH_FS_DEFAULT_UTF8_ENCODING),
- unicode_rev(BCH_FS_DEFAULT_UTF8_ENCODING));
-
if (!bch2_fs_may_start(c))
return bch_err_throw(c, insufficient_devices_to_start);
scoped_guard(rwsem_write, &c->state_lock) {
- guard(mutex)(&c->sb_lock);
- if (!bch2_sb_field_get_minsize(&c->disk_sb, ext,
- sizeof(struct bch_sb_field_ext) / sizeof(u64))) {
- ret = bch_err_throw(c, ENOSPC_sb);
- goto err;
- }
-
- ret = bch2_sb_members_v2_init(c);
- if (ret)
- goto err;
-
scoped_guard(rcu)
for_each_online_member_rcu(c, ca) {
- bch2_members_v2_get_mut(c->disk_sb.sb, ca->dev_idx)->last_mount =
- cpu_to_le64(now);
if (ca->mi.state == BCH_MEMBER_STATE_rw)
bch2_dev_allocator_add(c, ca);
}
diff --git a/fs/bcachefs/trace.h b/fs/bcachefs/trace.h
index 3776a1403104..269cdf1a87a4 100644
--- a/fs/bcachefs/trace.h
+++ b/fs/bcachefs/trace.h
@@ -1179,6 +1179,11 @@ DEFINE_EVENT(transaction_event, trans_restart_write_buffer_flush,
TP_ARGS(trans, caller_ip)
);
+DEFINE_EVENT(fs_str, accounting_key_to_wb_slowpath,
+ TP_PROTO(struct bch_fs *c, const char *str),
+ TP_ARGS(c, str)
+);
+
TRACE_EVENT(path_downgrade,
TP_PROTO(struct btree_trans *trans,
unsigned long caller_ip,
diff --git a/fs/ext4/namei.c b/fs/ext4/namei.c
index d83f91b62317..bb2370829928 100644
--- a/fs/ext4/namei.c
+++ b/fs/ext4/namei.c
@@ -2965,7 +2965,6 @@ int ext4_init_new_dir(handle_t *handle, struct inode *dir,
struct inode *inode)
{
struct buffer_head *dir_block = NULL;
- struct ext4_dir_entry_2 *de;
ext4_lblk_t block = 0;
int err;
@@ -2982,7 +2981,6 @@ int ext4_init_new_dir(handle_t *handle, struct inode *dir,
dir_block = ext4_append(handle, inode, &block);
if (IS_ERR(dir_block))
return PTR_ERR(dir_block);
- de = (struct ext4_dir_entry_2 *)dir_block->b_data;
err = ext4_init_dirblock(handle, inode, dir_block, dir->i_ino, NULL, 0);
if (err)
goto out;
diff --git a/fs/smb/client/cifs_debug.c b/fs/smb/client/cifs_debug.c
index f1cea365b6f1..ca7c2265c25f 100644
--- a/fs/smb/client/cifs_debug.c
+++ b/fs/smb/client/cifs_debug.c
@@ -481,10 +481,8 @@ static int cifs_debug_data_proc_show(struct seq_file *m, void *v)
server->smbd_conn->receive_credit_target);
seq_printf(m, "\nPending send_pending: %x ",
atomic_read(&server->smbd_conn->send_pending));
- seq_printf(m, "\nReceive buffers count_receive_queue: %x "
- "count_empty_packet_queue: %x",
- server->smbd_conn->count_receive_queue,
- server->smbd_conn->count_empty_packet_queue);
+ seq_printf(m, "\nReceive buffers count_receive_queue: %x ",
+ server->smbd_conn->count_receive_queue);
seq_printf(m, "\nMR responder_resources: %x "
"max_frmr_depth: %x mr_type: %x",
server->smbd_conn->responder_resources,
diff --git a/fs/smb/client/smbdirect.c b/fs/smb/client/smbdirect.c
index 754e94a0e07f..58321e483a1a 100644
--- a/fs/smb/client/smbdirect.c
+++ b/fs/smb/client/smbdirect.c
@@ -13,8 +13,6 @@
#include "cifsproto.h"
#include "smb2proto.h"
-static struct smbd_response *get_empty_queue_buffer(
- struct smbd_connection *info);
static struct smbd_response *get_receive_buffer(
struct smbd_connection *info);
static void put_receive_buffer(
@@ -23,8 +21,6 @@ static void put_receive_buffer(
static int allocate_receive_buffers(struct smbd_connection *info, int num_buf);
static void destroy_receive_buffers(struct smbd_connection *info);
-static void put_empty_packet(
- struct smbd_connection *info, struct smbd_response *response);
static void enqueue_reassembly(
struct smbd_connection *info,
struct smbd_response *response, int data_length);
@@ -281,18 +277,20 @@ static void send_done(struct ib_cq *cq, struct ib_wc *wc)
log_rdma_send(INFO, "smbd_request 0x%p completed wc->status=%d\n",
request, wc->status);
- if (wc->status != IB_WC_SUCCESS || wc->opcode != IB_WC_SEND) {
- log_rdma_send(ERR, "wc->status=%d wc->opcode=%d\n",
- wc->status, wc->opcode);
- smbd_disconnect_rdma_connection(request->info);
- }
-
for (i = 0; i < request->num_sge; i++)
ib_dma_unmap_single(sc->ib.dev,
request->sge[i].addr,
request->sge[i].length,
DMA_TO_DEVICE);
+ if (wc->status != IB_WC_SUCCESS || wc->opcode != IB_WC_SEND) {
+ log_rdma_send(ERR, "wc->status=%d wc->opcode=%d\n",
+ wc->status, wc->opcode);
+ mempool_free(request, request->info->request_mempool);
+ smbd_disconnect_rdma_connection(request->info);
+ return;
+ }
+
if (atomic_dec_and_test(&request->info->send_pending))
wake_up(&request->info->wait_send_pending);
@@ -391,7 +389,6 @@ static bool process_negotiation_response(
static void smbd_post_send_credits(struct work_struct *work)
{
int ret = 0;
- int use_receive_queue = 1;
int rc;
struct smbd_response *response;
struct smbd_connection *info =
@@ -407,18 +404,9 @@ static void smbd_post_send_credits(struct work_struct *work)
if (info->receive_credit_target >
atomic_read(&info->receive_credits)) {
while (true) {
- if (use_receive_queue)
- response = get_receive_buffer(info);
- else
- response = get_empty_queue_buffer(info);
- if (!response) {
- /* now switch to empty packet queue */
- if (use_receive_queue) {
- use_receive_queue = 0;
- continue;
- } else
- break;
- }
+ response = get_receive_buffer(info);
+ if (!response)
+ break;
response->type = SMBD_TRANSFER_DATA;
response->first_segment = false;
@@ -466,7 +454,6 @@ static void recv_done(struct ib_cq *cq, struct ib_wc *wc)
if (wc->status != IB_WC_SUCCESS || wc->opcode != IB_WC_RECV) {
log_rdma_recv(INFO, "wc->status=%d opcode=%d\n",
wc->status, wc->opcode);
- smbd_disconnect_rdma_connection(info);
goto error;
}
@@ -483,18 +470,15 @@ static void recv_done(struct ib_cq *cq, struct ib_wc *wc)
info->full_packet_received = true;
info->negotiate_done =
process_negotiation_response(response, wc->byte_len);
+ put_receive_buffer(info, response);
complete(&info->negotiate_completion);
- break;
+ return;
/* SMBD data transfer packet */
case SMBD_TRANSFER_DATA:
data_transfer = smbd_response_payload(response);
data_length = le32_to_cpu(data_transfer->data_length);
- /*
- * If this is a packet with data playload place the data in
- * reassembly queue and wake up the reading thread
- */
if (data_length) {
if (info->full_packet_received)
response->first_segment = true;
@@ -503,16 +487,7 @@ static void recv_done(struct ib_cq *cq, struct ib_wc *wc)
info->full_packet_received = false;
else
info->full_packet_received = true;
-
- enqueue_reassembly(
- info,
- response,
- data_length);
- } else
- put_empty_packet(info, response);
-
- if (data_length)
- wake_up_interruptible(&info->wait_reassembly_queue);
+ }
atomic_dec(&info->receive_credits);
info->receive_credit_target =
@@ -540,15 +515,27 @@ static void recv_done(struct ib_cq *cq, struct ib_wc *wc)
info->keep_alive_requested = KEEP_ALIVE_PENDING;
}
- return;
+ /*
+ * If this is a packet with data playload place the data in
+ * reassembly queue and wake up the reading thread
+ */
+ if (data_length) {
+ enqueue_reassembly(info, response, data_length);
+ wake_up_interruptible(&info->wait_reassembly_queue);
+ } else
+ put_receive_buffer(info, response);
- default:
- log_rdma_recv(ERR,
- "unexpected response type=%d\n", response->type);
+ return;
}
+ /*
+ * This is an internal error!
+ */
+ log_rdma_recv(ERR, "unexpected response type=%d\n", response->type);
+ WARN_ON_ONCE(response->type != SMBD_TRANSFER_DATA);
error:
put_receive_buffer(info, response);
+ smbd_disconnect_rdma_connection(info);
}
static struct rdma_cm_id *smbd_create_id(
@@ -1069,6 +1056,7 @@ static int smbd_post_recv(
if (rc) {
ib_dma_unmap_single(sc->ib.dev, response->sge.addr,
response->sge.length, DMA_FROM_DEVICE);
+ response->sge.length = 0;
smbd_disconnect_rdma_connection(info);
log_rdma_recv(ERR, "ib_post_recv failed rc=%d\n", rc);
}
@@ -1113,17 +1101,6 @@ static int smbd_negotiate(struct smbd_connection *info)
return rc;
}
-static void put_empty_packet(
- struct smbd_connection *info, struct smbd_response *response)
-{
- spin_lock(&info->empty_packet_queue_lock);
- list_add_tail(&response->list, &info->empty_packet_queue);
- info->count_empty_packet_queue++;
- spin_unlock(&info->empty_packet_queue_lock);
-
- queue_work(info->workqueue, &info->post_send_credits_work);
-}
-
/*
* Implement Connection.FragmentReassemblyBuffer defined in [MS-SMBD] 3.1.1.1
* This is a queue for reassembling upper layer payload and present to upper
@@ -1172,25 +1149,6 @@ static struct smbd_response *_get_first_reassembly(struct smbd_connection *info)
return ret;
}
-static struct smbd_response *get_empty_queue_buffer(
- struct smbd_connection *info)
-{
- struct smbd_response *ret = NULL;
- unsigned long flags;
-
- spin_lock_irqsave(&info->empty_packet_queue_lock, flags);
- if (!list_empty(&info->empty_packet_queue)) {
- ret = list_first_entry(
- &info->empty_packet_queue,
- struct smbd_response, list);
- list_del(&ret->list);
- info->count_empty_packet_queue--;
- }
- spin_unlock_irqrestore(&info->empty_packet_queue_lock, flags);
-
- return ret;
-}
-
/*
* Get a receive buffer
* For each remote send, we need to post a receive. The receive buffers are
@@ -1228,8 +1186,13 @@ static void put_receive_buffer(
struct smbdirect_socket *sc = &info->socket;
unsigned long flags;
- ib_dma_unmap_single(sc->ib.dev, response->sge.addr,
- response->sge.length, DMA_FROM_DEVICE);
+ if (likely(response->sge.length != 0)) {
+ ib_dma_unmap_single(sc->ib.dev,
+ response->sge.addr,
+ response->sge.length,
+ DMA_FROM_DEVICE);
+ response->sge.length = 0;
+ }
spin_lock_irqsave(&info->receive_queue_lock, flags);
list_add_tail(&response->list, &info->receive_queue);
@@ -1255,10 +1218,6 @@ static int allocate_receive_buffers(struct smbd_connection *info, int num_buf)
spin_lock_init(&info->receive_queue_lock);
info->count_receive_queue = 0;
- INIT_LIST_HEAD(&info->empty_packet_queue);
- spin_lock_init(&info->empty_packet_queue_lock);
- info->count_empty_packet_queue = 0;
-
init_waitqueue_head(&info->wait_receive_queues);
for (i = 0; i < num_buf; i++) {
@@ -1267,6 +1226,7 @@ static int allocate_receive_buffers(struct smbd_connection *info, int num_buf)
goto allocate_failed;
response->info = info;
+ response->sge.length = 0;
list_add_tail(&response->list, &info->receive_queue);
info->count_receive_queue++;
}
@@ -1292,9 +1252,6 @@ static void destroy_receive_buffers(struct smbd_connection *info)
while ((response = get_receive_buffer(info)))
mempool_free(response, info->response_mempool);
-
- while ((response = get_empty_queue_buffer(info)))
- mempool_free(response, info->response_mempool);
}
/* Implement idle connection timer [MS-SMBD] 3.1.6.2 */
@@ -1381,8 +1338,7 @@ void smbd_destroy(struct TCP_Server_Info *server)
log_rdma_event(INFO, "free receive buffers\n");
wait_event(info->wait_receive_queues,
- info->count_receive_queue + info->count_empty_packet_queue
- == sp->recv_credit_max);
+ info->count_receive_queue == sp->recv_credit_max);
destroy_receive_buffers(info);
/*
diff --git a/fs/smb/client/smbdirect.h b/fs/smb/client/smbdirect.h
index 75b3f491c3ad..ea04ce8a9763 100644
--- a/fs/smb/client/smbdirect.h
+++ b/fs/smb/client/smbdirect.h
@@ -110,10 +110,6 @@ struct smbd_connection {
int count_receive_queue;
spinlock_t receive_queue_lock;
- struct list_head empty_packet_queue;
- int count_empty_packet_queue;
- spinlock_t empty_packet_queue_lock;
-
wait_queue_head_t wait_receive_queues;
/* Reassembly queue */
diff --git a/include/crypto/hash.h b/include/crypto/hash.h
index db294d452e8c..bbaeae705ef0 100644
--- a/include/crypto/hash.h
+++ b/include/crypto/hash.h
@@ -184,7 +184,7 @@ struct shash_desc {
* Worst case is hmac(sha3-224-s390). Its context is a nested 'shash_desc'
* containing a 'struct s390_sha_ctx'.
*/
-#define HASH_MAX_DESCSIZE (sizeof(struct shash_desc) + 360)
+#define HASH_MAX_DESCSIZE (sizeof(struct shash_desc) + 361)
#define MAX_SYNC_HASH_REQSIZE (sizeof(struct ahash_request) + \
HASH_MAX_DESCSIZE)
diff --git a/include/linux/module.h b/include/linux/module.h
index 3319a5269d28..e135cc79acee 100644
--- a/include/linux/module.h
+++ b/include/linux/module.h
@@ -244,14 +244,22 @@ struct module_kobject *lookup_or_create_module_kobject(const char *name);
/* What your module does. */
#define MODULE_DESCRIPTION(_description) MODULE_INFO(description, _description)
-#ifdef MODULE
+/*
+ * Format: __mod_device_table__kmod_<modname>__<type>__<name>
+ * Parts of the string `__kmod_` and `__` are used as delimiters when parsing
+ * a symbol in file2alias.c
+ */
+#define __mod_device_table(type, name) \
+ __PASTE(__mod_device_table__, \
+ __PASTE(__KBUILD_MODNAME, \
+ __PASTE(__, \
+ __PASTE(type, \
+ __PASTE(__, name)))))
+
/* Creates an alias so file2alias.c can find device table. */
#define MODULE_DEVICE_TABLE(type, name) \
-static typeof(name) __mod_device_table__##type##__##name \
+static typeof(name) __mod_device_table(type, name) \
__attribute__ ((used, alias(__stringify(name))))
-#else /* !MODULE */
-#define MODULE_DEVICE_TABLE(type, name)
-#endif
/* Version of form [<epoch>:]<version>[-<extra-version>].
* Or for CVS/RCS ID version, everything but the number is stripped.
diff --git a/include/linux/ring_buffer.h b/include/linux/ring_buffer.h
index bc90c3c7b5fd..876358cfe1b1 100644
--- a/include/linux/ring_buffer.h
+++ b/include/linux/ring_buffer.h
@@ -144,6 +144,9 @@ int ring_buffer_write(struct trace_buffer *buffer,
void ring_buffer_nest_start(struct trace_buffer *buffer);
void ring_buffer_nest_end(struct trace_buffer *buffer);
+DEFINE_GUARD(ring_buffer_nest, struct trace_buffer *,
+ ring_buffer_nest_start(_T), ring_buffer_nest_end(_T))
+
struct ring_buffer_event *
ring_buffer_peek(struct trace_buffer *buffer, int cpu, u64 *ts,
unsigned long *lost_events);
diff --git a/include/linux/rtc/ds1685.h b/include/linux/rtc/ds1685.h
index 5a41c3bbcbe3..01da4582db6d 100644
--- a/include/linux/rtc/ds1685.h
+++ b/include/linux/rtc/ds1685.h
@@ -8,7 +8,7 @@
* include larger, battery-backed NV-SRAM, burst-mode access, and an RTC
* write counter.
*
- * Copyright (C) 2011-2014 Joshua Kinard <kumba@gentoo.org>.
+ * Copyright (C) 2011-2014 Joshua Kinard <linux@kumba.dev>.
* Copyright (C) 2009 Matthias Fuchs <matthias.fuchs@esd-electronics.com>.
*
* References:
diff --git a/include/linux/shmem_fs.h b/include/linux/shmem_fs.h
index 203eebad6b38..6d0f9c599ff7 100644
--- a/include/linux/shmem_fs.h
+++ b/include/linux/shmem_fs.h
@@ -156,12 +156,12 @@ enum sgp_type {
int shmem_get_folio(struct inode *inode, pgoff_t index, loff_t write_end,
struct folio **foliop, enum sgp_type sgp);
struct folio *shmem_read_folio_gfp(struct address_space *mapping,
- pgoff_t index, loff_t end, gfp_t gfp);
+ pgoff_t index, gfp_t gfp);
static inline struct folio *shmem_read_folio(struct address_space *mapping,
pgoff_t index)
{
- return shmem_read_folio_gfp(mapping, index, 0, mapping_gfp_mask(mapping));
+ return shmem_read_folio_gfp(mapping, index, mapping_gfp_mask(mapping));
}
static inline struct page *shmem_read_mapping_page(
diff --git a/include/linux/skbuff.h b/include/linux/skbuff.h
index b8b06e71b73e..14b923ddb6df 100644
--- a/include/linux/skbuff.h
+++ b/include/linux/skbuff.h
@@ -3033,6 +3033,29 @@ static inline void skb_reset_transport_header(struct sk_buff *skb)
skb->transport_header = offset;
}
+/**
+ * skb_reset_transport_header_careful - conditionally reset transport header
+ * @skb: buffer to alter
+ *
+ * Hardened version of skb_reset_transport_header().
+ *
+ * Returns: true if the operation was a success.
+ */
+static inline bool __must_check
+skb_reset_transport_header_careful(struct sk_buff *skb)
+{
+ long offset = skb->data - skb->head;
+
+ if (unlikely(offset != (typeof(skb->transport_header))offset))
+ return false;
+
+ if (unlikely(offset == (typeof(skb->transport_header))~0U))
+ return false;
+
+ skb->transport_header = offset;
+ return true;
+}
+
static inline void skb_set_transport_header(struct sk_buff *skb,
const int offset)
{
diff --git a/include/net/dst.h b/include/net/dst.h
index 00467c1b5093..bab01363bb97 100644
--- a/include/net/dst.h
+++ b/include/net/dst.h
@@ -568,11 +568,23 @@ static inline struct net_device *dst_dev(const struct dst_entry *dst)
return READ_ONCE(dst->dev);
}
+static inline struct net_device *dst_dev_rcu(const struct dst_entry *dst)
+{
+ /* In the future, use rcu_dereference(dst->dev) */
+ WARN_ON_ONCE(!rcu_read_lock_held());
+ return READ_ONCE(dst->dev);
+}
+
static inline struct net_device *skb_dst_dev(const struct sk_buff *skb)
{
return dst_dev(skb_dst(skb));
}
+static inline struct net_device *skb_dst_dev_rcu(const struct sk_buff *skb)
+{
+ return dst_dev_rcu(skb_dst(skb));
+}
+
static inline struct net *skb_dst_dev_net(const struct sk_buff *skb)
{
return dev_net(skb_dst_dev(skb));
diff --git a/include/net/udp.h b/include/net/udp.h
index f8ae2c4ade14..e2af3bda90c9 100644
--- a/include/net/udp.h
+++ b/include/net/udp.h
@@ -586,6 +586,16 @@ static inline struct sk_buff *udp_rcv_segment(struct sock *sk,
{
netdev_features_t features = NETIF_F_SG;
struct sk_buff *segs;
+ int drop_count;
+
+ /*
+ * Segmentation in UDP receive path is only for UDP GRO, drop udp
+ * fragmentation offload (UFO) packets.
+ */
+ if (skb_shinfo(skb)->gso_type & SKB_GSO_UDP) {
+ drop_count = 1;
+ goto drop;
+ }
/* Avoid csum recalculation by skb_segment unless userspace explicitly
* asks for the final checksum values
@@ -609,16 +619,18 @@ static inline struct sk_buff *udp_rcv_segment(struct sock *sk,
*/
segs = __skb_gso_segment(skb, features, false);
if (IS_ERR_OR_NULL(segs)) {
- int segs_nr = skb_shinfo(skb)->gso_segs;
-
- atomic_add(segs_nr, &sk->sk_drops);
- SNMP_ADD_STATS(__UDPX_MIB(sk, ipv4), UDP_MIB_INERRORS, segs_nr);
- kfree_skb(skb);
- return NULL;
+ drop_count = skb_shinfo(skb)->gso_segs;
+ goto drop;
}
consume_skb(skb);
return segs;
+
+drop:
+ atomic_add(drop_count, &sk->sk_drops);
+ SNMP_ADD_STATS(__UDPX_MIB(sk, ipv4), UDP_MIB_INERRORS, drop_count);
+ kfree_skb(skb);
+ return NULL;
}
static inline void udp_post_segment_fix_csum(struct sk_buff *skb)
diff --git a/include/uapi/linux/raid/md_p.h b/include/uapi/linux/raid/md_p.h
index ff47b6f0ba0f..b13946287277 100644
--- a/include/uapi/linux/raid/md_p.h
+++ b/include/uapi/linux/raid/md_p.h
@@ -173,7 +173,7 @@ typedef struct mdp_superblock_s {
#else
#error unspecified endianness
#endif
- __u32 recovery_cp; /* 11 recovery checkpoint sector count */
+ __u32 resync_offset; /* 11 resync checkpoint sector count */
/* There are only valid for minor_version > 90 */
__u64 reshape_position; /* 12,13 next address in array-space for reshape */
__u32 new_level; /* 14 new level we are reshaping to */
diff --git a/include/uapi/linux/vhost.h b/include/uapi/linux/vhost.h
index c57674a6aa0d..283348b64af9 100644
--- a/include/uapi/linux/vhost.h
+++ b/include/uapi/linux/vhost.h
@@ -260,7 +260,7 @@
* When fork_owner is set to VHOST_FORK_OWNER_KTHREAD:
* - Vhost will create vhost workers as kernel threads.
*/
-#define VHOST_SET_FORK_FROM_OWNER _IOW(VHOST_VIRTIO, 0x84, __u8)
+#define VHOST_SET_FORK_FROM_OWNER _IOW(VHOST_VIRTIO, 0x83, __u8)
/**
* VHOST_GET_FORK_OWNER - Get the current fork_owner flag for the vhost device.
@@ -268,6 +268,6 @@
*
* @return: An 8-bit value indicating the current thread mode.
*/
-#define VHOST_GET_FORK_FROM_OWNER _IOR(VHOST_VIRTIO, 0x85, __u8)
+#define VHOST_GET_FORK_FROM_OWNER _IOR(VHOST_VIRTIO, 0x84, __u8)
#endif
diff --git a/include/uapi/linux/virtio_ids.h b/include/uapi/linux/virtio_ids.h
index b4bb0ace0b26..7aa2eb766205 100644
--- a/include/uapi/linux/virtio_ids.h
+++ b/include/uapi/linux/virtio_ids.h
@@ -68,7 +68,6 @@
#define VIRTIO_ID_AUDIO_POLICY 39 /* virtio audio policy */
#define VIRTIO_ID_BT 40 /* virtio bluetooth */
#define VIRTIO_ID_GPIO 41 /* virtio gpio */
-#define VIRTIO_ID_MEDIA 48 /* virtio media */
/*
* Virtio Transitional IDs
diff --git a/include/uapi/linux/vt.h b/include/uapi/linux/vt.h
index b60fcdfb2746..714483d68c69 100644
--- a/include/uapi/linux/vt.h
+++ b/include/uapi/linux/vt.h
@@ -14,9 +14,9 @@
/* Note: the ioctl VT_GETSTATE does not work for
consoles 16 and higher (since it returns a short) */
-/* 'V' to avoid collision with termios and kd */
+/* 0x56 is 'V', to avoid collision with termios and kd */
-#define VT_OPENQRY _IO('V', 0x00) /* find available vt */
+#define VT_OPENQRY 0x5600 /* find available vt */
struct vt_mode {
__u8 mode; /* vt mode */
@@ -25,8 +25,8 @@ struct vt_mode {
__s16 acqsig; /* signal to raise on acquisition */
__s16 frsig; /* unused (set to 0) */
};
-#define VT_GETMODE _IO('V', 0x01) /* get mode of active vt */
-#define VT_SETMODE _IO('V', 0x02) /* set mode of active vt */
+#define VT_GETMODE 0x5601 /* get mode of active vt */
+#define VT_SETMODE 0x5602 /* set mode of active vt */
#define VT_AUTO 0x00 /* auto vt switching */
#define VT_PROCESS 0x01 /* process controls switching */
#define VT_ACKACQ 0x02 /* acknowledge switch */
@@ -36,21 +36,21 @@ struct vt_stat {
__u16 v_signal; /* signal to send */
__u16 v_state; /* vt bitmask */
};
-#define VT_GETSTATE _IO('V', 0x03) /* get global vt state info */
-#define VT_SENDSIG _IO('V', 0x04) /* signal to send to bitmask of vts */
+#define VT_GETSTATE 0x5603 /* get global vt state info */
+#define VT_SENDSIG 0x5604 /* signal to send to bitmask of vts */
-#define VT_RELDISP _IO('V', 0x05) /* release display */
+#define VT_RELDISP 0x5605 /* release display */
-#define VT_ACTIVATE _IO('V', 0x06) /* make vt active */
-#define VT_WAITACTIVE _IO('V', 0x07) /* wait for vt active */
-#define VT_DISALLOCATE _IO('V', 0x08) /* free memory associated to vt */
+#define VT_ACTIVATE 0x5606 /* make vt active */
+#define VT_WAITACTIVE 0x5607 /* wait for vt active */
+#define VT_DISALLOCATE 0x5608 /* free memory associated to vt */
struct vt_sizes {
__u16 v_rows; /* number of rows */
__u16 v_cols; /* number of columns */
__u16 v_scrollsize; /* number of lines of scrollback */
};
-#define VT_RESIZE _IO('V', 0x09) /* set kernel's idea of screensize */
+#define VT_RESIZE 0x5609 /* set kernel's idea of screensize */
struct vt_consize {
__u16 v_rows; /* number of rows */
@@ -60,10 +60,10 @@ struct vt_consize {
__u16 v_vcol; /* number of pixel columns on screen */
__u16 v_ccol; /* number of pixel columns per character */
};
-#define VT_RESIZEX _IO('V', 0x0A) /* set kernel's idea of screensize + more */
-#define VT_LOCKSWITCH _IO('V', 0x0B) /* disallow vt switching */
-#define VT_UNLOCKSWITCH _IO('V', 0x0C) /* allow vt switching */
-#define VT_GETHIFONTMASK _IO('V', 0x0D) /* return hi font mask */
+#define VT_RESIZEX 0x560A /* set kernel's idea of screensize + more */
+#define VT_LOCKSWITCH 0x560B /* disallow vt switching */
+#define VT_UNLOCKSWITCH 0x560C /* allow vt switching */
+#define VT_GETHIFONTMASK 0x560D /* return hi font mask */
struct vt_event {
__u32 event;
@@ -77,14 +77,14 @@ struct vt_event {
__u32 pad[4]; /* Padding for expansion */
};
-#define VT_WAITEVENT _IO('V', 0x0E) /* Wait for an event */
+#define VT_WAITEVENT 0x560E /* Wait for an event */
struct vt_setactivate {
__u32 console;
struct vt_mode mode;
};
-#define VT_SETACTIVATE _IO('V', 0x0F) /* Activate and set the mode of a console */
+#define VT_SETACTIVATE 0x560F /* Activate and set the mode of a console */
/* get console size and cursor position */
struct vt_consizecsrpos {
diff --git a/kernel/bpf/verifier.c b/kernel/bpf/verifier.c
index 399f03e62508..c4f69a9e9af6 100644
--- a/kernel/bpf/verifier.c
+++ b/kernel/bpf/verifier.c
@@ -21445,7 +21445,7 @@ static int convert_ctx_accesses(struct bpf_verifier_env *env)
&target_size);
if (cnt == 0 || cnt >= INSN_BUF_SIZE ||
(ctx_field_size && !target_size)) {
- verifier_bug(env, "error during ctx access conversion");
+ verifier_bug(env, "error during ctx access conversion (%d)", cnt);
return -EFAULT;
}
@@ -23114,6 +23114,8 @@ static void free_states(struct bpf_verifier_env *env)
for (i = 0; i < env->scc_cnt; ++i) {
info = env->scc_info[i];
+ if (!info)
+ continue;
for (j = 0; j < info->num_visits; j++)
free_backedges(&info->visits[j]);
kvfree(info);
@@ -24554,6 +24556,7 @@ dfs_continue:
err = -ENOMEM;
goto exit;
}
+ env->scc_cnt = next_scc_id;
exit:
kvfree(stack);
kvfree(pre);
diff --git a/kernel/fork.c b/kernel/fork.c
index c4ada32598bd..af673856499d 100644
--- a/kernel/fork.c
+++ b/kernel/fork.c
@@ -689,6 +689,7 @@ void __mmdrop(struct mm_struct *mm)
mm_pasid_drop(mm);
mm_destroy_cid(mm);
percpu_counter_destroy_many(mm->rss_stat, NR_MM_COUNTERS);
+ futex_hash_free(mm);
free_mm(mm);
}
@@ -1137,7 +1138,6 @@ static inline void __mmput(struct mm_struct *mm)
if (mm->binfmt)
module_put(mm->binfmt->module);
lru_gen_del_mm(mm);
- futex_hash_free(mm);
mmdrop(mm);
}
diff --git a/kernel/hung_task.c b/kernel/hung_task.c
index 8708a1205f82..b2c1f14b8129 100644
--- a/kernel/hung_task.c
+++ b/kernel/hung_task.c
@@ -95,9 +95,41 @@ static struct notifier_block panic_block = {
.notifier_call = hung_task_panic,
};
+static bool task_is_hung(struct task_struct *t, unsigned long timeout)
+{
+ unsigned long switch_count = t->nvcsw + t->nivcsw;
+ unsigned int state = READ_ONCE(t->__state);
+
+ /*
+ * skip the TASK_KILLABLE tasks -- these can be killed
+ * skip the TASK_IDLE tasks -- those are genuinely idle
+ * skip the TASK_FROZEN task -- it reasonably stops scheduling by freezer
+ */
+ if (!(state & TASK_UNINTERRUPTIBLE) ||
+ (state & (TASK_WAKEKILL | TASK_NOLOAD | TASK_FROZEN)))
+ return false;
+
+ /*
+ * When a freshly created task is scheduled once, changes its state to
+ * TASK_UNINTERRUPTIBLE without having ever been switched out once, it
+ * musn't be checked.
+ */
+ if (unlikely(!switch_count))
+ return false;
+
+ if (switch_count != t->last_switch_count) {
+ t->last_switch_count = switch_count;
+ t->last_switch_time = jiffies;
+ return false;
+ }
+ if (time_is_after_jiffies(t->last_switch_time + timeout * HZ))
+ return false;
+
+ return true;
+}
#ifdef CONFIG_DETECT_HUNG_TASK_BLOCKER
-static void debug_show_blocker(struct task_struct *task)
+static void debug_show_blocker(struct task_struct *task, unsigned long timeout)
{
struct task_struct *g, *t;
unsigned long owner, blocker, blocker_type;
@@ -174,41 +206,21 @@ static void debug_show_blocker(struct task_struct *task)
t->pid, rwsem_blocked_by);
break;
}
- sched_show_task(t);
+ /* Avoid duplicated task dump, skip if the task is also hung. */
+ if (!task_is_hung(t, timeout))
+ sched_show_task(t);
return;
}
}
#else
-static inline void debug_show_blocker(struct task_struct *task)
+static inline void debug_show_blocker(struct task_struct *task, unsigned long timeout)
{
}
#endif
static void check_hung_task(struct task_struct *t, unsigned long timeout)
{
- unsigned long switch_count = t->nvcsw + t->nivcsw;
-
- /*
- * Ensure the task is not frozen.
- * Also, skip vfork and any other user process that freezer should skip.
- */
- if (unlikely(READ_ONCE(t->__state) & TASK_FROZEN))
- return;
-
- /*
- * When a freshly created task is scheduled once, changes its state to
- * TASK_UNINTERRUPTIBLE without having ever been switched out once, it
- * musn't be checked.
- */
- if (unlikely(!switch_count))
- return;
-
- if (switch_count != t->last_switch_count) {
- t->last_switch_count = switch_count;
- t->last_switch_time = jiffies;
- return;
- }
- if (time_is_after_jiffies(t->last_switch_time + timeout * HZ))
+ if (!task_is_hung(t, timeout))
return;
/*
@@ -243,7 +255,7 @@ static void check_hung_task(struct task_struct *t, unsigned long timeout)
pr_err("\"echo 0 > /proc/sys/kernel/hung_task_timeout_secs\""
" disables this message.\n");
sched_show_task(t);
- debug_show_blocker(t);
+ debug_show_blocker(t, timeout);
hung_task_show_lock = true;
if (sysctl_hung_task_all_cpu_backtrace)
@@ -299,7 +311,6 @@ static void check_hung_uninterruptible_tasks(unsigned long timeout)
hung_task_show_lock = false;
rcu_read_lock();
for_each_process_thread(g, t) {
- unsigned int state;
if (!max_count--)
goto unlock;
@@ -308,15 +319,8 @@ static void check_hung_uninterruptible_tasks(unsigned long timeout)
goto unlock;
last_break = jiffies;
}
- /*
- * skip the TASK_KILLABLE tasks -- these can be killed
- * skip the TASK_IDLE tasks -- those are genuinely idle
- */
- state = READ_ONCE(t->__state);
- if ((state & TASK_UNINTERRUPTIBLE) &&
- !(state & TASK_WAKEKILL) &&
- !(state & TASK_NOLOAD))
- check_hung_task(t, timeout);
+
+ check_hung_task(t, timeout);
}
unlock:
rcu_read_unlock();
diff --git a/kernel/panic.c b/kernel/panic.c
index 27747cecb1af..6255cafa06ed 100644
--- a/kernel/panic.c
+++ b/kernel/panic.c
@@ -78,12 +78,6 @@ ATOMIC_NOTIFIER_HEAD(panic_notifier_list);
EXPORT_SYMBOL(panic_notifier_list);
#ifdef CONFIG_SYSCTL
-static int sysctl_panic_print_handler(const struct ctl_table *table, int write,
- void *buffer, size_t *lenp, loff_t *ppos)
-{
- pr_info_once("Kernel: 'panic_print' sysctl interface will be obsoleted by both 'panic_sys_info' and 'panic_console_replay'\n");
- return proc_doulongvec_minmax(table, write, buffer, lenp, ppos);
-}
/*
* Taint values can only be increased
@@ -128,6 +122,13 @@ static int proc_taint(const struct ctl_table *table, int write,
return err;
}
+static int sysctl_panic_print_handler(const struct ctl_table *table, int write,
+ void *buffer, size_t *lenp, loff_t *ppos)
+{
+ pr_info_once("Kernel: 'panic_print' sysctl interface will be obsoleted by both 'panic_sys_info' and 'panic_console_replay'\n");
+ return proc_doulongvec_minmax(table, write, buffer, lenp, ppos);
+}
+
static const struct ctl_table kern_panic_table[] = {
#ifdef CONFIG_SMP
{
@@ -183,13 +184,6 @@ static const struct ctl_table kern_panic_table[] = {
.mode = 0644,
.proc_handler = proc_douintvec,
},
- {
- .procname = "panic_sys_info",
- .data = &panic_print,
- .maxlen = sizeof(panic_print),
- .mode = 0644,
- .proc_handler = sysctl_sys_info_handler,
- },
#if (defined(CONFIG_X86_32) || defined(CONFIG_PARISC)) && \
defined(CONFIG_DEBUG_STACKOVERFLOW)
{
@@ -200,6 +194,13 @@ static const struct ctl_table kern_panic_table[] = {
.proc_handler = proc_dointvec,
},
#endif
+ {
+ .procname = "panic_sys_info",
+ .data = &panic_print,
+ .maxlen = sizeof(panic_print),
+ .mode = 0644,
+ .proc_handler = sysctl_sys_info_handler,
+ },
};
static __init int kernel_panic_sysctls_init(void)
diff --git a/kernel/sched/psi.c b/kernel/sched/psi.c
index 2024c1d36402..59fdb7ebbf22 100644
--- a/kernel/sched/psi.c
+++ b/kernel/sched/psi.c
@@ -176,7 +176,7 @@ struct psi_group psi_system = {
.pcpu = &system_group_pcpu,
};
-static DEFINE_PER_CPU(seqcount_t, psi_seq);
+static DEFINE_PER_CPU(seqcount_t, psi_seq) = SEQCNT_ZERO(psi_seq);
static inline void psi_write_begin(int cpu)
{
@@ -204,11 +204,7 @@ static void poll_timer_fn(struct timer_list *t);
static void group_init(struct psi_group *group)
{
- int cpu;
-
group->enabled = true;
- for_each_possible_cpu(cpu)
- seqcount_init(per_cpu_ptr(&psi_seq, cpu));
group->avg_last_update = sched_clock();
group->avg_next_update = group->avg_last_update + psi_period;
mutex_init(&group->avgs_lock);
diff --git a/kernel/smp.c b/kernel/smp.c
index 4649fa4872ff..56f83aa58ec8 100644
--- a/kernel/smp.c
+++ b/kernel/smp.c
@@ -1018,7 +1018,7 @@ void __init smp_init(void)
* @cond_func: A callback function that is passed a cpu id and
* the info parameter. The function is called
* with preemption disabled. The function should
- * return a blooean value indicating whether to IPI
+ * return a boolean value indicating whether to IPI
* the specified CPU.
* @func: The function to run on all applicable CPUs.
* This must be fast and non-blocking.
diff --git a/kernel/trace/ring_buffer.c b/kernel/trace/ring_buffer.c
index 5176e0270f07..bb71a0dc9d69 100644
--- a/kernel/trace/ring_buffer.c
+++ b/kernel/trace/ring_buffer.c
@@ -4812,26 +4812,26 @@ int ring_buffer_write(struct trace_buffer *buffer,
int ret = -EBUSY;
int cpu;
- preempt_disable_notrace();
+ guard(preempt_notrace)();
if (atomic_read(&buffer->record_disabled))
- goto out;
+ return -EBUSY;
cpu = raw_smp_processor_id();
if (!cpumask_test_cpu(cpu, buffer->cpumask))
- goto out;
+ return -EBUSY;
cpu_buffer = buffer->buffers[cpu];
if (atomic_read(&cpu_buffer->record_disabled))
- goto out;
+ return -EBUSY;
if (length > buffer->max_data_size)
- goto out;
+ return -EBUSY;
if (unlikely(trace_recursive_lock(cpu_buffer)))
- goto out;
+ return -EBUSY;
event = rb_reserve_next_event(buffer, cpu_buffer, length);
if (!event)
@@ -4849,10 +4849,6 @@ int ring_buffer_write(struct trace_buffer *buffer,
out_unlock:
trace_recursive_unlock(cpu_buffer);
-
- out:
- preempt_enable_notrace();
-
return ret;
}
EXPORT_SYMBOL_GPL(ring_buffer_write);
diff --git a/kernel/trace/trace.c b/kernel/trace/trace.c
index 9e99000c7c3a..4283ed4e8f59 100644
--- a/kernel/trace/trace.c
+++ b/kernel/trace/trace.c
@@ -432,15 +432,13 @@ static void ftrace_exports(struct ring_buffer_event *event, int flag)
{
struct trace_export *export;
- preempt_disable_notrace();
+ guard(preempt_notrace)();
export = rcu_dereference_raw_check(ftrace_exports_list);
while (export) {
trace_process_export(export, event, flag);
export = rcu_dereference_raw_check(export->next);
}
-
- preempt_enable_notrace();
}
static inline void
@@ -497,27 +495,18 @@ int register_ftrace_export(struct trace_export *export)
if (WARN_ON_ONCE(!export->write))
return -1;
- mutex_lock(&ftrace_export_lock);
+ guard(mutex)(&ftrace_export_lock);
add_ftrace_export(&ftrace_exports_list, export);
- mutex_unlock(&ftrace_export_lock);
-
return 0;
}
EXPORT_SYMBOL_GPL(register_ftrace_export);
int unregister_ftrace_export(struct trace_export *export)
{
- int ret;
-
- mutex_lock(&ftrace_export_lock);
-
- ret = rm_ftrace_export(&ftrace_exports_list, export);
-
- mutex_unlock(&ftrace_export_lock);
-
- return ret;
+ guard(mutex)(&ftrace_export_lock);
+ return rm_ftrace_export(&ftrace_exports_list, export);
}
EXPORT_SYMBOL_GPL(unregister_ftrace_export);
@@ -640,9 +629,8 @@ void trace_array_put(struct trace_array *this_tr)
if (!this_tr)
return;
- mutex_lock(&trace_types_lock);
+ guard(mutex)(&trace_types_lock);
__trace_array_put(this_tr);
- mutex_unlock(&trace_types_lock);
}
EXPORT_SYMBOL_GPL(trace_array_put);
@@ -1160,13 +1148,11 @@ int __trace_array_puts(struct trace_array *tr, unsigned long ip,
trace_ctx = tracing_gen_ctx();
buffer = tr->array_buffer.buffer;
- ring_buffer_nest_start(buffer);
+ guard(ring_buffer_nest)(buffer);
event = __trace_buffer_lock_reserve(buffer, TRACE_PRINT, alloc,
trace_ctx);
- if (!event) {
- size = 0;
- goto out;
- }
+ if (!event)
+ return 0;
entry = ring_buffer_event_data(event);
entry->ip = ip;
@@ -1182,8 +1168,6 @@ int __trace_array_puts(struct trace_array *tr, unsigned long ip,
__buffer_unlock_commit(buffer, event);
ftrace_trace_stack(tr, buffer, trace_ctx, 4, NULL);
- out:
- ring_buffer_nest_end(buffer);
return size;
}
EXPORT_SYMBOL_GPL(__trace_array_puts);
@@ -1213,7 +1197,6 @@ int __trace_bputs(unsigned long ip, const char *str)
struct bputs_entry *entry;
unsigned int trace_ctx;
int size = sizeof(struct bputs_entry);
- int ret = 0;
if (!printk_binsafe(tr))
return __trace_puts(ip, str, strlen(str));
@@ -1227,11 +1210,11 @@ int __trace_bputs(unsigned long ip, const char *str)
trace_ctx = tracing_gen_ctx();
buffer = tr->array_buffer.buffer;
- ring_buffer_nest_start(buffer);
+ guard(ring_buffer_nest)(buffer);
event = __trace_buffer_lock_reserve(buffer, TRACE_BPUTS, size,
trace_ctx);
if (!event)
- goto out;
+ return 0;
entry = ring_buffer_event_data(event);
entry->ip = ip;
@@ -1240,10 +1223,7 @@ int __trace_bputs(unsigned long ip, const char *str)
__buffer_unlock_commit(buffer, event);
ftrace_trace_stack(tr, buffer, trace_ctx, 4, NULL);
- ret = 1;
- out:
- ring_buffer_nest_end(buffer);
- return ret;
+ return 1;
}
EXPORT_SYMBOL_GPL(__trace_bputs);
@@ -1432,13 +1412,8 @@ static int tracing_arm_snapshot_locked(struct trace_array *tr)
int tracing_arm_snapshot(struct trace_array *tr)
{
- int ret;
-
- mutex_lock(&trace_types_lock);
- ret = tracing_arm_snapshot_locked(tr);
- mutex_unlock(&trace_types_lock);
-
- return ret;
+ guard(mutex)(&trace_types_lock);
+ return tracing_arm_snapshot_locked(tr);
}
void tracing_disarm_snapshot(struct trace_array *tr)
@@ -1841,7 +1816,7 @@ int trace_get_user(struct trace_parser *parser, const char __user *ubuf,
ret = get_user(ch, ubuf++);
if (ret)
- goto out;
+ return ret;
read++;
cnt--;
@@ -1855,7 +1830,7 @@ int trace_get_user(struct trace_parser *parser, const char __user *ubuf,
while (cnt && isspace(ch)) {
ret = get_user(ch, ubuf++);
if (ret)
- goto out;
+ return ret;
read++;
cnt--;
}
@@ -1865,8 +1840,7 @@ int trace_get_user(struct trace_parser *parser, const char __user *ubuf,
/* only spaces were written */
if (isspace(ch) || !ch) {
*ppos += read;
- ret = read;
- goto out;
+ return read;
}
}
@@ -1874,13 +1848,12 @@ int trace_get_user(struct trace_parser *parser, const char __user *ubuf,
while (cnt && !isspace(ch) && ch) {
if (parser->idx < parser->size - 1)
parser->buffer[parser->idx++] = ch;
- else {
- ret = -EINVAL;
- goto out;
- }
+ else
+ return -EINVAL;
+
ret = get_user(ch, ubuf++);
if (ret)
- goto out;
+ return ret;
read++;
cnt--;
}
@@ -1895,15 +1868,11 @@ int trace_get_user(struct trace_parser *parser, const char __user *ubuf,
/* Make sure the parsed string always terminates with '\0'. */
parser->buffer[parser->idx] = 0;
} else {
- ret = -EINVAL;
- goto out;
+ return -EINVAL;
}
*ppos += read;
- ret = read;
-
-out:
- return ret;
+ return read;
}
/* TODO add a seq_buf_to_buffer() */
@@ -2405,10 +2374,10 @@ int __init register_tracer(struct tracer *type)
mutex_unlock(&trace_types_lock);
if (ret || !default_bootup_tracer)
- goto out_unlock;
+ return ret;
if (strncmp(default_bootup_tracer, type->name, MAX_TRACER_SIZE))
- goto out_unlock;
+ return 0;
printk(KERN_INFO "Starting tracer '%s'\n", type->name);
/* Do we want this tracer to start on bootup? */
@@ -2420,8 +2389,7 @@ int __init register_tracer(struct tracer *type)
/* disable other selftests, since this will break it. */
disable_tracing_selftest("running a tracer");
- out_unlock:
- return ret;
+ return 0;
}
static void tracing_reset_cpu(struct array_buffer *buf, int cpu)
@@ -2498,9 +2466,8 @@ void tracing_reset_all_online_cpus_unlocked(void)
void tracing_reset_all_online_cpus(void)
{
- mutex_lock(&trace_types_lock);
+ guard(mutex)(&trace_types_lock);
tracing_reset_all_online_cpus_unlocked();
- mutex_unlock(&trace_types_lock);
}
int is_tracing_stopped(void)
@@ -2511,18 +2478,17 @@ int is_tracing_stopped(void)
static void tracing_start_tr(struct trace_array *tr)
{
struct trace_buffer *buffer;
- unsigned long flags;
if (tracing_disabled)
return;
- raw_spin_lock_irqsave(&tr->start_lock, flags);
+ guard(raw_spinlock_irqsave)(&tr->start_lock);
if (--tr->stop_count) {
if (WARN_ON_ONCE(tr->stop_count < 0)) {
/* Someone screwed up their debugging */
tr->stop_count = 0;
}
- goto out;
+ return;
}
/* Prevent the buffers from switching */
@@ -2539,9 +2505,6 @@ static void tracing_start_tr(struct trace_array *tr)
#endif
arch_spin_unlock(&tr->max_lock);
-
- out:
- raw_spin_unlock_irqrestore(&tr->start_lock, flags);
}
/**
@@ -2559,11 +2522,10 @@ void tracing_start(void)
static void tracing_stop_tr(struct trace_array *tr)
{
struct trace_buffer *buffer;
- unsigned long flags;
- raw_spin_lock_irqsave(&tr->start_lock, flags);
+ guard(raw_spinlock_irqsave)(&tr->start_lock);
if (tr->stop_count++)
- goto out;
+ return;
/* Prevent the buffers from switching */
arch_spin_lock(&tr->max_lock);
@@ -2579,9 +2541,6 @@ static void tracing_stop_tr(struct trace_array *tr)
#endif
arch_spin_unlock(&tr->max_lock);
-
- out:
- raw_spin_unlock_irqrestore(&tr->start_lock, flags);
}
/**
@@ -2694,12 +2653,12 @@ void trace_buffered_event_enable(void)
per_cpu(trace_buffered_event, cpu) = event;
- preempt_disable();
- if (cpu == smp_processor_id() &&
- __this_cpu_read(trace_buffered_event) !=
- per_cpu(trace_buffered_event, cpu))
- WARN_ON_ONCE(1);
- preempt_enable();
+ scoped_guard(preempt,) {
+ if (cpu == smp_processor_id() &&
+ __this_cpu_read(trace_buffered_event) !=
+ per_cpu(trace_buffered_event, cpu))
+ WARN_ON_ONCE(1);
+ }
}
}
@@ -3044,7 +3003,7 @@ static void __ftrace_trace_stack(struct trace_array *tr,
skip++;
#endif
- preempt_disable_notrace();
+ guard(preempt_notrace)();
stackidx = __this_cpu_inc_return(ftrace_stack_reserve) - 1;
@@ -3102,8 +3061,6 @@ static void __ftrace_trace_stack(struct trace_array *tr,
/* Again, don't let gcc optimize things here */
barrier();
__this_cpu_dec(ftrace_stack_reserve);
- preempt_enable_notrace();
-
}
static inline void ftrace_trace_stack(struct trace_array *tr,
@@ -3186,9 +3143,9 @@ ftrace_trace_userstack(struct trace_array *tr,
* prevent recursion, since the user stack tracing may
* trigger other kernel events.
*/
- preempt_disable();
+ guard(preempt)();
if (__this_cpu_read(user_stack_count))
- goto out;
+ return;
__this_cpu_inc(user_stack_count);
@@ -3206,8 +3163,6 @@ ftrace_trace_userstack(struct trace_array *tr,
out_drop_count:
__this_cpu_dec(user_stack_count);
- out:
- preempt_enable();
}
#else /* CONFIG_USER_STACKTRACE_SUPPORT */
static void ftrace_trace_userstack(struct trace_array *tr,
@@ -3389,7 +3344,7 @@ int trace_vbprintk(unsigned long ip, const char *fmt, va_list args)
pause_graph_tracing();
trace_ctx = tracing_gen_ctx();
- preempt_disable_notrace();
+ guard(preempt_notrace)();
tbuffer = get_trace_buf();
if (!tbuffer) {
@@ -3404,26 +3359,23 @@ int trace_vbprintk(unsigned long ip, const char *fmt, va_list args)
size = sizeof(*entry) + sizeof(u32) * len;
buffer = tr->array_buffer.buffer;
- ring_buffer_nest_start(buffer);
- event = __trace_buffer_lock_reserve(buffer, TRACE_BPRINT, size,
- trace_ctx);
- if (!event)
- goto out;
- entry = ring_buffer_event_data(event);
- entry->ip = ip;
- entry->fmt = fmt;
-
- memcpy(entry->buf, tbuffer, sizeof(u32) * len);
- __buffer_unlock_commit(buffer, event);
- ftrace_trace_stack(tr, buffer, trace_ctx, 6, NULL);
+ scoped_guard(ring_buffer_nest, buffer) {
+ event = __trace_buffer_lock_reserve(buffer, TRACE_BPRINT, size,
+ trace_ctx);
+ if (!event)
+ goto out_put;
+ entry = ring_buffer_event_data(event);
+ entry->ip = ip;
+ entry->fmt = fmt;
-out:
- ring_buffer_nest_end(buffer);
+ memcpy(entry->buf, tbuffer, sizeof(u32) * len);
+ __buffer_unlock_commit(buffer, event);
+ ftrace_trace_stack(tr, buffer, trace_ctx, 6, NULL);
+ }
out_put:
put_trace_buf();
out_nobuffer:
- preempt_enable_notrace();
unpause_graph_tracing();
return len;
@@ -3447,7 +3399,7 @@ int __trace_array_vprintk(struct trace_buffer *buffer,
pause_graph_tracing();
trace_ctx = tracing_gen_ctx();
- preempt_disable_notrace();
+ guard(preempt_notrace)();
tbuffer = get_trace_buf();
@@ -3459,24 +3411,22 @@ int __trace_array_vprintk(struct trace_buffer *buffer,
len = vscnprintf(tbuffer, TRACE_BUF_SIZE, fmt, args);
size = sizeof(*entry) + len + 1;
- ring_buffer_nest_start(buffer);
- event = __trace_buffer_lock_reserve(buffer, TRACE_PRINT, size,
- trace_ctx);
- if (!event)
- goto out;
- entry = ring_buffer_event_data(event);
- entry->ip = ip;
-
- memcpy(&entry->buf, tbuffer, len + 1);
- __buffer_unlock_commit(buffer, event);
- ftrace_trace_stack(printk_trace, buffer, trace_ctx, 6, NULL);
+ scoped_guard(ring_buffer_nest, buffer) {
+ event = __trace_buffer_lock_reserve(buffer, TRACE_PRINT, size,
+ trace_ctx);
+ if (!event)
+ goto out;
+ entry = ring_buffer_event_data(event);
+ entry->ip = ip;
+ memcpy(&entry->buf, tbuffer, len + 1);
+ __buffer_unlock_commit(buffer, event);
+ ftrace_trace_stack(printk_trace, buffer, trace_ctx, 6, NULL);
+ }
out:
- ring_buffer_nest_end(buffer);
put_trace_buf();
out_nobuffer:
- preempt_enable_notrace();
unpause_graph_tracing();
return len;
@@ -4800,20 +4750,16 @@ int tracing_open_file_tr(struct inode *inode, struct file *filp)
if (ret)
return ret;
- mutex_lock(&event_mutex);
+ guard(mutex)(&event_mutex);
/* Fail if the file is marked for removal */
if (file->flags & EVENT_FILE_FL_FREED) {
trace_array_put(file->tr);
- ret = -ENODEV;
+ return -ENODEV;
} else {
event_file_get(file);
}
- mutex_unlock(&event_mutex);
- if (ret)
- return ret;
-
filp->private_data = inode->i_private;
return 0;
@@ -5090,7 +5036,7 @@ tracing_cpumask_read(struct file *filp, char __user *ubuf,
size_t count, loff_t *ppos)
{
struct trace_array *tr = file_inode(filp)->i_private;
- char *mask_str;
+ char *mask_str __free(kfree) = NULL;
int len;
len = snprintf(NULL, 0, "%*pb\n",
@@ -5101,16 +5047,10 @@ tracing_cpumask_read(struct file *filp, char __user *ubuf,
len = snprintf(mask_str, len, "%*pb\n",
cpumask_pr_args(tr->tracing_cpumask));
- if (len >= count) {
- count = -EINVAL;
- goto out_err;
- }
- count = simple_read_from_buffer(ubuf, count, ppos, mask_str, len);
-
-out_err:
- kfree(mask_str);
+ if (len >= count)
+ return -EINVAL;
- return count;
+ return simple_read_from_buffer(ubuf, count, ppos, mask_str, len);
}
int tracing_set_cpumask(struct trace_array *tr,
@@ -5957,9 +5897,9 @@ tracing_set_trace_read(struct file *filp, char __user *ubuf,
char buf[MAX_TRACER_SIZE+2];
int r;
- mutex_lock(&trace_types_lock);
- r = sprintf(buf, "%s\n", tr->current_trace->name);
- mutex_unlock(&trace_types_lock);
+ scoped_guard(mutex, &trace_types_lock) {
+ r = sprintf(buf, "%s\n", tr->current_trace->name);
+ }
return simple_read_from_buffer(ubuf, cnt, ppos, buf, r);
}
@@ -6261,15 +6201,13 @@ int tracing_update_buffers(struct trace_array *tr)
{
int ret = 0;
- mutex_lock(&trace_types_lock);
+ guard(mutex)(&trace_types_lock);
update_last_data(tr);
if (!tr->ring_buffer_expanded)
ret = __tracing_resize_ring_buffer(tr, trace_buf_size,
RING_BUFFER_ALL_CPUS);
- mutex_unlock(&trace_types_lock);
-
return ret;
}
@@ -6566,7 +6504,7 @@ static int tracing_open_pipe(struct inode *inode, struct file *filp)
if (ret)
return ret;
- mutex_lock(&trace_types_lock);
+ guard(mutex)(&trace_types_lock);
cpu = tracing_get_cpu(inode);
ret = open_pipe_on_cpu(tr, cpu);
if (ret)
@@ -6610,7 +6548,6 @@ static int tracing_open_pipe(struct inode *inode, struct file *filp)
tr->trace_ref++;
- mutex_unlock(&trace_types_lock);
return ret;
fail:
@@ -6619,7 +6556,6 @@ fail_alloc_iter:
close_pipe_on_cpu(tr, cpu);
fail_pipe_on_cpu:
__trace_array_put(tr);
- mutex_unlock(&trace_types_lock);
return ret;
}
@@ -6628,14 +6564,13 @@ static int tracing_release_pipe(struct inode *inode, struct file *file)
struct trace_iterator *iter = file->private_data;
struct trace_array *tr = inode->i_private;
- mutex_lock(&trace_types_lock);
-
- tr->trace_ref--;
+ scoped_guard(mutex, &trace_types_lock) {
+ tr->trace_ref--;
- if (iter->trace->pipe_close)
- iter->trace->pipe_close(iter);
- close_pipe_on_cpu(tr, iter->cpu_file);
- mutex_unlock(&trace_types_lock);
+ if (iter->trace->pipe_close)
+ iter->trace->pipe_close(iter);
+ close_pipe_on_cpu(tr, iter->cpu_file);
+ }
free_trace_iter_content(iter);
kfree(iter);
@@ -7438,7 +7373,7 @@ int tracing_set_clock(struct trace_array *tr, const char *clockstr)
if (i == ARRAY_SIZE(trace_clocks))
return -EINVAL;
- mutex_lock(&trace_types_lock);
+ guard(mutex)(&trace_types_lock);
tr->clock_id = i;
@@ -7462,8 +7397,6 @@ int tracing_set_clock(struct trace_array *tr, const char *clockstr)
tscratch->clock_id = i;
}
- mutex_unlock(&trace_types_lock);
-
return 0;
}
@@ -7515,15 +7448,13 @@ static int tracing_time_stamp_mode_show(struct seq_file *m, void *v)
{
struct trace_array *tr = m->private;
- mutex_lock(&trace_types_lock);
+ guard(mutex)(&trace_types_lock);
if (ring_buffer_time_stamp_abs(tr->array_buffer.buffer))
seq_puts(m, "delta [absolute]\n");
else
seq_puts(m, "[delta] absolute\n");
- mutex_unlock(&trace_types_lock);
-
return 0;
}
@@ -8111,14 +8042,14 @@ static void clear_tracing_err_log(struct trace_array *tr)
{
struct tracing_log_err *err, *next;
- mutex_lock(&tracing_err_log_lock);
+ guard(mutex)(&tracing_err_log_lock);
+
list_for_each_entry_safe(err, next, &tr->err_log, list) {
list_del(&err->list);
free_tracing_log_err(err);
}
tr->n_err_log_entries = 0;
- mutex_unlock(&tracing_err_log_lock);
}
static void *tracing_err_log_seq_start(struct seq_file *m, loff_t *pos)
@@ -8389,7 +8320,7 @@ static int tracing_buffers_release(struct inode *inode, struct file *file)
struct ftrace_buffer_info *info = file->private_data;
struct trace_iterator *iter = &info->iter;
- mutex_lock(&trace_types_lock);
+ guard(mutex)(&trace_types_lock);
iter->tr->trace_ref--;
@@ -8400,8 +8331,6 @@ static int tracing_buffers_release(struct inode *inode, struct file *file)
info->spare_cpu, info->spare);
kvfree(info);
- mutex_unlock(&trace_types_lock);
-
return 0;
}
@@ -8609,14 +8538,13 @@ static long tracing_buffers_ioctl(struct file *file, unsigned int cmd, unsigned
* An ioctl call with cmd 0 to the ring buffer file will wake up all
* waiters
*/
- mutex_lock(&trace_types_lock);
+ guard(mutex)(&trace_types_lock);
/* Make sure the waiters see the new wait_index */
(void)atomic_fetch_inc_release(&iter->wait_index);
ring_buffer_wake_waiters(iter->array_buffer->buffer, iter->cpu_file);
- mutex_unlock(&trace_types_lock);
return 0;
}
@@ -8957,12 +8885,12 @@ ftrace_trace_snapshot_callback(struct trace_array *tr, struct ftrace_hash *hash,
out_reg:
ret = tracing_arm_snapshot(tr);
if (ret < 0)
- goto out;
+ return ret;
ret = register_ftrace_function_probe(glob, tr, ops, count);
if (ret < 0)
tracing_disarm_snapshot(tr);
- out:
+
return ret < 0 ? ret : 0;
}
@@ -9106,10 +9034,9 @@ trace_options_write(struct file *filp, const char __user *ubuf, size_t cnt,
return -EINVAL;
if (!!(topt->flags->val & topt->opt->bit) != val) {
- mutex_lock(&trace_types_lock);
+ guard(mutex)(&trace_types_lock);
ret = __set_tracer_option(topt->tr, topt->flags,
topt->opt, !val);
- mutex_unlock(&trace_types_lock);
if (ret)
return ret;
}
@@ -9418,7 +9345,7 @@ rb_simple_write(struct file *filp, const char __user *ubuf,
return ret;
if (buffer) {
- mutex_lock(&trace_types_lock);
+ guard(mutex)(&trace_types_lock);
if (!!val == tracer_tracing_is_on(tr)) {
val = 0; /* do nothing */
} else if (val) {
@@ -9432,7 +9359,6 @@ rb_simple_write(struct file *filp, const char __user *ubuf,
/* Wake up any waiters */
ring_buffer_wake_waiters(buffer, RING_BUFFER_ALL_CPUS);
}
- mutex_unlock(&trace_types_lock);
}
(*ppos)++;
@@ -9816,10 +9742,9 @@ static void __update_tracer_options(struct trace_array *tr)
static void update_tracer_options(struct trace_array *tr)
{
- mutex_lock(&trace_types_lock);
+ guard(mutex)(&trace_types_lock);
tracer_options_updated = true;
__update_tracer_options(tr);
- mutex_unlock(&trace_types_lock);
}
/* Must have trace_types_lock held */
@@ -9841,11 +9766,10 @@ struct trace_array *trace_array_find_get(const char *instance)
{
struct trace_array *tr;
- mutex_lock(&trace_types_lock);
+ guard(mutex)(&trace_types_lock);
tr = trace_array_find(instance);
if (tr)
tr->ref++;
- mutex_unlock(&trace_types_lock);
return tr;
}
@@ -10803,7 +10727,8 @@ ssize_t trace_parse_run_command(struct file *file, const char __user *buffer,
size_t count, loff_t *ppos,
int (*createfn)(const char *))
{
- char *kbuf, *buf, *tmp;
+ char *kbuf __free(kfree) = NULL;
+ char *buf, *tmp;
int ret = 0;
size_t done = 0;
size_t size;
@@ -10818,10 +10743,9 @@ ssize_t trace_parse_run_command(struct file *file, const char __user *buffer,
if (size >= WRITE_BUFSIZE)
size = WRITE_BUFSIZE - 1;
- if (copy_from_user(kbuf, buffer + done, size)) {
- ret = -EFAULT;
- goto out;
- }
+ if (copy_from_user(kbuf, buffer + done, size))
+ return -EFAULT;
+
kbuf[size] = '\0';
buf = kbuf;
do {
@@ -10837,8 +10761,7 @@ ssize_t trace_parse_run_command(struct file *file, const char __user *buffer,
/* This can accept WRITE_BUFSIZE - 2 ('\n' + '\0') */
pr_warn("Line length is too long: Should be less than %d\n",
WRITE_BUFSIZE - 2);
- ret = -EINVAL;
- goto out;
+ return -EINVAL;
}
}
done += size;
@@ -10851,17 +10774,12 @@ ssize_t trace_parse_run_command(struct file *file, const char __user *buffer,
ret = createfn(buf);
if (ret)
- goto out;
+ return ret;
buf += size;
} while (done < count);
}
- ret = done;
-
-out:
- kfree(kbuf);
-
- return ret;
+ return done;
}
#ifdef CONFIG_TRACER_MAX_TRACE
@@ -11064,7 +10982,7 @@ __init static int tracer_alloc_buffers(void)
BUILD_BUG_ON(TRACE_ITER_LAST_BIT > TRACE_FLAGS_MAX_SIZE);
if (!alloc_cpumask_var(&tracing_buffer_mask, GFP_KERNEL))
- goto out;
+ return -ENOMEM;
if (!alloc_cpumask_var(&global_trace.tracing_cpumask, GFP_KERNEL))
goto out_free_buffer_mask;
@@ -11182,7 +11100,6 @@ out_free_cpumask:
free_cpumask_var(global_trace.tracing_cpumask);
out_free_buffer_mask:
free_cpumask_var(tracing_buffer_mask);
-out:
return ret;
}
diff --git a/kernel/trace/trace_events_synth.c b/kernel/trace/trace_events_synth.c
index 33cfbd4ed76d..f24ee61f8884 100644
--- a/kernel/trace/trace_events_synth.c
+++ b/kernel/trace/trace_events_synth.c
@@ -536,12 +536,12 @@ static notrace void trace_event_raw_event_synth(void *__data,
* is being performed within another event.
*/
buffer = trace_file->tr->array_buffer.buffer;
- ring_buffer_nest_start(buffer);
+ guard(ring_buffer_nest)(buffer);
entry = trace_event_buffer_reserve(&fbuffer, trace_file,
sizeof(*entry) + fields_size);
if (!entry)
- goto out;
+ return;
for (i = 0, n_u64 = 0; i < event->n_fields; i++) {
val_idx = var_ref_idx[i];
@@ -584,8 +584,6 @@ static notrace void trace_event_raw_event_synth(void *__data,
}
trace_event_buffer_commit(&fbuffer);
-out:
- ring_buffer_nest_end(buffer);
}
static void free_synth_event_print_fmt(struct trace_event_call *call)
diff --git a/kernel/trace/trace_output.c b/kernel/trace/trace_output.c
index 0b3db02030a7..97db0b0ccf3e 100644
--- a/kernel/trace/trace_output.c
+++ b/kernel/trace/trace_output.c
@@ -701,6 +701,7 @@ void print_function_args(struct trace_seq *s, unsigned long *args,
struct btf *btf;
s32 tid, nr = 0;
int a, p, x;
+ u16 encode;
trace_seq_printf(s, "(");
@@ -744,7 +745,12 @@ void print_function_args(struct trace_seq *s, unsigned long *args,
trace_seq_printf(s, "0x%lx", arg);
break;
case BTF_KIND_INT:
- trace_seq_printf(s, "%ld", arg);
+ encode = btf_int_encoding(t);
+ /* Print unsigned ints as hex */
+ if (encode & BTF_INT_SIGNED)
+ trace_seq_printf(s, "%ld", arg);
+ else
+ trace_seq_printf(s, "0x%lx", arg);
break;
case BTF_KIND_ENUM:
trace_seq_printf(s, "%ld", arg);
diff --git a/lib/Kconfig.debug b/lib/Kconfig.debug
index acee7f75600b..1cb4734e58e1 100644
--- a/lib/Kconfig.debug
+++ b/lib/Kconfig.debug
@@ -3244,7 +3244,6 @@ config TEST_KEXEC_HANDOVER
If unsure, say N.
-
config RATELIMIT_KUNIT_TEST
tristate "KUnit Test for correctness and stress of ratelimit" if !KUNIT_ALL_TESTS
depends on KUNIT
diff --git a/localversion-next b/localversion-next
new file mode 100644
index 000000000000..2eb4c4941a5f
--- /dev/null
+++ b/localversion-next
@@ -0,0 +1 @@
+-next-20250805
diff --git a/mm/debug_vm_pgtable.c b/mm/debug_vm_pgtable.c
index d19031f275a3..830107b6dd08 100644
--- a/mm/debug_vm_pgtable.c
+++ b/mm/debug_vm_pgtable.c
@@ -990,29 +990,34 @@ static void __init destroy_args(struct pgtable_debug_args *args)
/* Free page table entries */
if (args->start_ptep) {
+ pmd_clear(args->pmdp);
pte_free(args->mm, args->start_ptep);
mm_dec_nr_ptes(args->mm);
}
if (args->start_pmdp) {
+ pud_clear(args->pudp);
pmd_free(args->mm, args->start_pmdp);
mm_dec_nr_pmds(args->mm);
}
if (args->start_pudp) {
+ p4d_clear(args->p4dp);
pud_free(args->mm, args->start_pudp);
mm_dec_nr_puds(args->mm);
}
- if (args->start_p4dp)
+ if (args->start_p4dp) {
+ pgd_clear(args->pgdp);
p4d_free(args->mm, args->start_p4dp);
+ }
/* Free vma and mm struct */
if (args->vma)
vm_area_free(args->vma);
if (args->mm)
- mmdrop(args->mm);
+ mmput(args->mm);
}
static struct page * __init
diff --git a/mm/kasan/kasan_test_c.c b/mm/kasan/kasan_test_c.c
index e0968acc03aa..f4b17984b627 100644
--- a/mm/kasan/kasan_test_c.c
+++ b/mm/kasan/kasan_test_c.c
@@ -1578,9 +1578,11 @@ static void kasan_strings(struct kunit *test)
ptr = kmalloc(size, GFP_KERNEL | __GFP_ZERO);
KUNIT_ASSERT_NOT_ERR_OR_NULL(test, ptr);
+ OPTIMIZER_HIDE_VAR(ptr);
src = kmalloc(KASAN_GRANULE_SIZE, GFP_KERNEL | __GFP_ZERO);
strscpy(src, "f0cacc1a0000000", KASAN_GRANULE_SIZE);
+ OPTIMIZER_HIDE_VAR(src);
/*
* Make sure that strscpy() does not trigger KASAN if it overreads into
diff --git a/mm/kmemleak.c b/mm/kmemleak.c
index 620abd95e680..84265983f239 100644
--- a/mm/kmemleak.c
+++ b/mm/kmemleak.c
@@ -470,6 +470,7 @@ static struct kmemleak_object *mem_pool_alloc(gfp_t gfp)
{
unsigned long flags;
struct kmemleak_object *object;
+ bool warn = false;
/* try the slab allocator first */
if (object_cache) {
@@ -488,8 +489,10 @@ static struct kmemleak_object *mem_pool_alloc(gfp_t gfp)
else if (mem_pool_free_count)
object = &mem_pool[--mem_pool_free_count];
else
- pr_warn_once("Memory pool empty, consider increasing CONFIG_DEBUG_KMEMLEAK_MEM_POOL_SIZE\n");
+ warn = true;
raw_spin_unlock_irqrestore(&kmemleak_lock, flags);
+ if (warn)
+ pr_warn_once("Memory pool empty, consider increasing CONFIG_DEBUG_KMEMLEAK_MEM_POOL_SIZE\n");
return object;
}
diff --git a/mm/mempool.c b/mm/mempool.c
index 204a216b6418..1c38e873e546 100644
--- a/mm/mempool.c
+++ b/mm/mempool.c
@@ -136,7 +136,7 @@ static void kasan_unpoison_element(mempool_t *pool, void *element)
static __always_inline void add_element(mempool_t *pool, void *element)
{
- BUG_ON(pool->curr_nr >= pool->min_nr);
+ BUG_ON(pool->min_nr != 0 && pool->curr_nr >= pool->min_nr);
poison_element(pool, element);
if (kasan_poison_element(pool, element))
pool->elements[pool->curr_nr++] = element;
@@ -202,16 +202,20 @@ int mempool_init_node(mempool_t *pool, int min_nr, mempool_alloc_t *alloc_fn,
pool->alloc = alloc_fn;
pool->free = free_fn;
init_waitqueue_head(&pool->wait);
-
- pool->elements = kmalloc_array_node(min_nr, sizeof(void *),
+ /*
+ * max() used here to ensure storage for at least 1 element to support
+ * zero minimum pool
+ */
+ pool->elements = kmalloc_array_node(max(1, min_nr), sizeof(void *),
gfp_mask, node_id);
if (!pool->elements)
return -ENOMEM;
/*
- * First pre-allocate the guaranteed number of buffers.
+ * First pre-allocate the guaranteed number of buffers,
+ * also pre-allocate 1 element for zero minimum pool.
*/
- while (pool->curr_nr < pool->min_nr) {
+ while (pool->curr_nr < max(1, pool->min_nr)) {
void *element;
element = pool->alloc(gfp_mask, pool->pool_data);
@@ -555,20 +559,12 @@ void mempool_free(void *element, mempool_t *pool)
* wake-up path of previous test. This explicit check ensures the
* allocation of element when both min_nr and curr_nr are 0, and
* any active waiters are properly awakened.
- *
- * Inline the same logic as previous test, add_element() cannot be
- * directly used here since it has BUG_ON to deny if min_nr equals
- * curr_nr, so here picked rest of add_element() to use without
- * BUG_ON check.
*/
if (unlikely(pool->min_nr == 0 &&
READ_ONCE(pool->curr_nr) == 0)) {
spin_lock_irqsave(&pool->lock, flags);
if (likely(pool->curr_nr == 0)) {
- /* Inline the logic of add_element() */
- poison_element(pool, element);
- if (kasan_poison_element(pool, element))
- pool->elements[pool->curr_nr++] = element;
+ add_element(pool, element);
spin_unlock_irqrestore(&pool->lock, flags);
if (wq_has_sleeper(&pool->wait))
wake_up(&pool->wait);
diff --git a/mm/shmem.c b/mm/shmem.c
index 2b41460c316e..e2c76a30802b 100644
--- a/mm/shmem.c
+++ b/mm/shmem.c
@@ -5970,7 +5970,6 @@ int shmem_zero_setup(struct vm_area_struct *vma)
* shmem_read_folio_gfp - read into page cache, using specified page allocation flags.
* @mapping: the folio's address_space
* @index: the folio index
- * @end: end of a read if allocating a new folio
* @gfp: the page allocator flags to use if allocating
*
* This behaves as a tmpfs "read_cache_page_gfp(mapping, index, gfp)",
@@ -5983,15 +5982,15 @@ int shmem_zero_setup(struct vm_area_struct *vma)
* with the mapping_gfp_mask(), to avoid OOMing the machine unnecessarily.
*/
struct folio *shmem_read_folio_gfp(struct address_space *mapping,
- pgoff_t index, loff_t end, gfp_t gfp)
+ pgoff_t index, gfp_t gfp)
{
#ifdef CONFIG_SHMEM
struct inode *inode = mapping->host;
struct folio *folio;
int error;
- error = shmem_get_folio_gfp(inode, index, end, &folio, SGP_CACHE,
- gfp, NULL, NULL);
+ error = shmem_get_folio_gfp(inode, index, i_size_read(inode),
+ &folio, SGP_CACHE, gfp, NULL, NULL);
if (error)
return ERR_PTR(error);
@@ -6009,7 +6008,7 @@ EXPORT_SYMBOL_GPL(shmem_read_folio_gfp);
struct page *shmem_read_mapping_page_gfp(struct address_space *mapping,
pgoff_t index, gfp_t gfp)
{
- struct folio *folio = shmem_read_folio_gfp(mapping, index, 0, gfp);
+ struct folio *folio = shmem_read_folio_gfp(mapping, index, gfp);
struct page *page;
if (IS_ERR(folio))
diff --git a/mm/userfaultfd.c b/mm/userfaultfd.c
index cbed91b09640..5431c9dd7fd7 100644
--- a/mm/userfaultfd.c
+++ b/mm/userfaultfd.c
@@ -1453,10 +1453,15 @@ out:
folio_unlock(src_folio);
folio_put(src_folio);
}
- if (dst_pte)
- pte_unmap(dst_pte);
+ /*
+ * Unmap in reverse order (LIFO) to maintain proper kmap_local
+ * index ordering when CONFIG_HIGHPTE is enabled. We mapped dst_pte
+ * first, then src_pte, so we must unmap src_pte first, then dst_pte.
+ */
if (src_pte)
pte_unmap(src_pte);
+ if (dst_pte)
+ pte_unmap(dst_pte);
mmu_notifier_invalidate_range_end(&range);
if (si)
put_swap_device(si);
diff --git a/net/core/filter.c b/net/core/filter.c
index c09a85c17496..da391e2b0788 100644
--- a/net/core/filter.c
+++ b/net/core/filter.c
@@ -9458,6 +9458,9 @@ static bool flow_dissector_is_valid_access(int off, int size,
if (off < 0 || off >= sizeof(struct __sk_buff))
return false;
+ if (off % size != 0)
+ return false;
+
if (type == BPF_WRITE)
return false;
diff --git a/net/ipv4/ip_output.c b/net/ipv4/ip_output.c
index 10a1d182fd84..84e7f8a2f50f 100644
--- a/net/ipv4/ip_output.c
+++ b/net/ipv4/ip_output.c
@@ -425,15 +425,20 @@ int ip_mc_output(struct net *net, struct sock *sk, struct sk_buff *skb)
int ip_output(struct net *net, struct sock *sk, struct sk_buff *skb)
{
- struct net_device *dev = skb_dst_dev(skb), *indev = skb->dev;
+ struct net_device *dev, *indev = skb->dev;
+ int ret_val;
+ rcu_read_lock();
+ dev = skb_dst_dev_rcu(skb);
skb->dev = dev;
skb->protocol = htons(ETH_P_IP);
- return NF_HOOK_COND(NFPROTO_IPV4, NF_INET_POST_ROUTING,
- net, sk, skb, indev, dev,
- ip_finish_output,
- !(IPCB(skb)->flags & IPSKB_REROUTED));
+ ret_val = NF_HOOK_COND(NFPROTO_IPV4, NF_INET_POST_ROUTING,
+ net, sk, skb, indev, dev,
+ ip_finish_output,
+ !(IPCB(skb)->flags & IPSKB_REROUTED));
+ rcu_read_unlock();
+ return ret_val;
}
EXPORT_SYMBOL(ip_output);
diff --git a/net/ipv6/ip6_offload.c b/net/ipv6/ip6_offload.c
index 9822163428b0..fce91183797a 100644
--- a/net/ipv6/ip6_offload.c
+++ b/net/ipv6/ip6_offload.c
@@ -148,7 +148,9 @@ static struct sk_buff *ipv6_gso_segment(struct sk_buff *skb,
ops = rcu_dereference(inet6_offloads[proto]);
if (likely(ops && ops->callbacks.gso_segment)) {
- skb_reset_transport_header(skb);
+ if (!skb_reset_transport_header_careful(skb))
+ goto out;
+
segs = ops->callbacks.gso_segment(skb, features);
if (!segs)
skb->network_header = skb_mac_header(skb) + nhoff - skb->head;
diff --git a/net/netfilter/nf_bpf_link.c b/net/netfilter/nf_bpf_link.c
index 3e4fb9ddcd36..46e667a50d98 100644
--- a/net/netfilter/nf_bpf_link.c
+++ b/net/netfilter/nf_bpf_link.c
@@ -296,6 +296,9 @@ static bool nf_is_valid_access(int off, int size, enum bpf_access_type type,
if (off < 0 || off >= sizeof(struct bpf_nf_ctx))
return false;
+ if (off % size != 0)
+ return false;
+
if (type == BPF_WRITE)
return false;
diff --git a/net/sched/sch_taprio.c b/net/sched/sch_taprio.c
index e759e43ad27e..39b735386996 100644
--- a/net/sched/sch_taprio.c
+++ b/net/sched/sch_taprio.c
@@ -43,6 +43,11 @@ static struct static_key_false taprio_have_working_mqprio;
#define TAPRIO_SUPPORTED_FLAGS \
(TCA_TAPRIO_ATTR_FLAG_TXTIME_ASSIST | TCA_TAPRIO_ATTR_FLAG_FULL_OFFLOAD)
#define TAPRIO_FLAGS_INVALID U32_MAX
+/* Minimum value for picos_per_byte to ensure non-zero duration
+ * for minimum-sized Ethernet frames (ETH_ZLEN = 60).
+ * 60 * 17 > PSEC_PER_NSEC (1000)
+ */
+#define TAPRIO_PICOS_PER_BYTE_MIN 17
struct sched_entry {
/* Durations between this GCL entry and the GCL entry where the
@@ -1284,7 +1289,8 @@ static void taprio_start_sched(struct Qdisc *sch,
}
static void taprio_set_picos_per_byte(struct net_device *dev,
- struct taprio_sched *q)
+ struct taprio_sched *q,
+ struct netlink_ext_ack *extack)
{
struct ethtool_link_ksettings ecmd;
int speed = SPEED_10;
@@ -1300,6 +1306,15 @@ static void taprio_set_picos_per_byte(struct net_device *dev,
skip:
picos_per_byte = (USEC_PER_SEC * 8) / speed;
+ if (picos_per_byte < TAPRIO_PICOS_PER_BYTE_MIN) {
+ if (!extack)
+ pr_warn("Link speed %d is too high. Schedule may be inaccurate.\n",
+ speed);
+ NL_SET_ERR_MSG_FMT_MOD(extack,
+ "Link speed %d is too high. Schedule may be inaccurate.",
+ speed);
+ picos_per_byte = TAPRIO_PICOS_PER_BYTE_MIN;
+ }
atomic64_set(&q->picos_per_byte, picos_per_byte);
netdev_dbg(dev, "taprio: set %s's picos_per_byte to: %lld, linkspeed: %d\n",
@@ -1324,7 +1339,7 @@ static int taprio_dev_notifier(struct notifier_block *nb, unsigned long event,
if (dev != qdisc_dev(q->root))
continue;
- taprio_set_picos_per_byte(dev, q);
+ taprio_set_picos_per_byte(dev, q, NULL);
stab = rtnl_dereference(q->root->stab);
@@ -1844,7 +1859,7 @@ static int taprio_change(struct Qdisc *sch, struct nlattr *opt,
q->flags = taprio_flags;
/* Needed for length_to_duration() during netlink attribute parsing */
- taprio_set_picos_per_byte(dev, q);
+ taprio_set_picos_per_byte(dev, q, extack);
err = taprio_parse_mqprio_opt(dev, mqprio, extack, q->flags);
if (err < 0)
diff --git a/rust/helpers/helpers.c b/rust/helpers/helpers.c
index e0573009598a..7cf7fe95e41d 100644
--- a/rust/helpers/helpers.c
+++ b/rust/helpers/helpers.c
@@ -36,9 +36,9 @@
#include "poll.c"
#include "property.c"
#include "rbtree.c"
-#include "regulator.c"
#include "rcu.c"
#include "refcount.c"
+#include "regulator.c"
#include "security.c"
#include "signal.c"
#include "slab.c"
diff --git a/rust/kernel/device_id.rs b/rust/kernel/device_id.rs
index 70d57814ff79..62c42da12e9d 100644
--- a/rust/kernel/device_id.rs
+++ b/rust/kernel/device_id.rs
@@ -195,10 +195,10 @@ macro_rules! module_device_table {
($table_type: literal, $module_table_name:ident, $table_name:ident) => {
#[rustfmt::skip]
#[export_name =
- concat!("__mod_device_table__", $table_type,
- "__", module_path!(),
- "_", line!(),
- "_", stringify!($table_name))
+ concat!("__mod_device_table__", line!(),
+ "__kmod_", module_path!(),
+ "__", $table_type,
+ "__", stringify!($table_name))
]
static $module_table_name: [::core::mem::MaybeUninit<u8>; $table_name.raw_ids().size()] =
unsafe { ::core::mem::transmute_copy($table_name.raw_ids()) };
diff --git a/scripts/Makefile.vmlinux b/scripts/Makefile.vmlinux
index fdab5aa90215..dbbe3bf0cf23 100644
--- a/scripts/Makefile.vmlinux
+++ b/scripts/Makefile.vmlinux
@@ -53,11 +53,6 @@ endif
# vmlinux.unstripped
# ---------------------------------------------------------------------------
-ifdef CONFIG_MODULES
-targets += .vmlinux.export.o
-vmlinux.unstripped: .vmlinux.export.o
-endif
-
ifdef CONFIG_ARCH_WANTS_PRE_LINK_VMLINUX
vmlinux.unstripped: arch/$(SRCARCH)/tools/vmlinux.arch.o
@@ -72,8 +67,8 @@ cmd_link_vmlinux = \
$< "$(LD)" "$(KBUILD_LDFLAGS)" "$(LDFLAGS_vmlinux)" "$@"; \
$(if $(ARCH_POSTLINK), $(MAKE) -f $(ARCH_POSTLINK) $@, true)
-targets += vmlinux.unstripped
-vmlinux.unstripped: scripts/link-vmlinux.sh vmlinux.o $(KBUILD_LDS) FORCE
+targets += vmlinux.unstripped .vmlinux.export.o
+vmlinux.unstripped: scripts/link-vmlinux.sh vmlinux.o .vmlinux.export.o $(KBUILD_LDS) FORCE
+$(call if_changed_dep,link_vmlinux)
ifdef CONFIG_DEBUG_INFO_BTF
vmlinux.unstripped: $(RESOLVE_BTFIDS)
@@ -89,8 +84,11 @@ endif
remove-section-y := .modinfo
remove-section-$(CONFIG_ARCH_VMLINUX_NEEDS_RELOCS) += '.rel*'
+remove-symbols := -w --strip-symbol='__mod_device_table__*'
+
quiet_cmd_strip_relocs = OBJCOPY $@
- cmd_strip_relocs = $(OBJCOPY) $(addprefix --remove-section=,$(remove-section-y)) $< $@
+ cmd_strip_relocs = $(OBJCOPY) $(addprefix --remove-section=,$(remove-section-y)) \
+ $(remove-symbols) $< $@
targets += vmlinux
vmlinux: vmlinux.unstripped FORCE
diff --git a/scripts/link-vmlinux.sh b/scripts/link-vmlinux.sh
index 51367c2bfc21..433849ff7529 100755
--- a/scripts/link-vmlinux.sh
+++ b/scripts/link-vmlinux.sh
@@ -73,10 +73,7 @@ vmlinux_link()
objs="${objs} .builtin-dtbs.o"
fi
- if is_enabled CONFIG_MODULES; then
- objs="${objs} .vmlinux.export.o"
- fi
-
+ objs="${objs} .vmlinux.export.o"
objs="${objs} init/version-timestamp.o"
if [ "${SRCARCH}" = "um" ]; then
diff --git a/scripts/mksysmap b/scripts/mksysmap
index a607a0059d11..c4531eacde20 100755
--- a/scripts/mksysmap
+++ b/scripts/mksysmap
@@ -59,6 +59,9 @@
# EXPORT_SYMBOL (namespace)
/ __kstrtabns_/d
+# MODULE_DEVICE_TABLE (symbol name)
+/ __mod_device_table__/d
+
# ---------------------------------------------------------------------------
# Ignored suffixes
# (do not forget '$' after each pattern)
diff --git a/scripts/mod/file2alias.c b/scripts/mod/file2alias.c
index 00586119a25b..7da9735e7ab3 100644
--- a/scripts/mod/file2alias.c
+++ b/scripts/mod/file2alias.c
@@ -1476,8 +1476,8 @@ void handle_moddevtable(struct module *mod, struct elf_info *info,
{
void *symval;
char *zeros = NULL;
- const char *type, *name;
- size_t typelen;
+ const char *type, *name, *modname;
+ size_t typelen, modnamelen;
static const char *prefix = "__mod_device_table__";
/* We're looking for a section relative symbol */
@@ -1488,10 +1488,20 @@ void handle_moddevtable(struct module *mod, struct elf_info *info,
if (ELF_ST_TYPE(sym->st_info) != STT_OBJECT)
return;
- /* All our symbols are of form __mod_device_table__<type>__<name>. */
+ /* All our symbols are of form __mod_device_table__kmod_<modname>__<type>__<name>. */
if (!strstarts(symname, prefix))
return;
- type = symname + strlen(prefix);
+
+ modname = strstr(symname, "__kmod_");
+ if (!modname)
+ return;
+ modname += strlen("__kmod_");
+
+ type = strstr(modname, "__");
+ if (!type)
+ return;
+ modnamelen = type - modname;
+ type += strlen("__");
name = strstr(type, "__");
if (!name)
@@ -1517,5 +1527,21 @@ void handle_moddevtable(struct module *mod, struct elf_info *info,
}
}
+ if (mod->is_vmlinux) {
+ struct module_alias *alias;
+
+ /*
+ * If this is vmlinux, record the name of the builtin module.
+ * Traverse the linked list in the reverse order, and set the
+ * builtin_modname unless it has already been set in the
+ * previous call.
+ */
+ list_for_each_entry_reverse(alias, &mod->aliases, node) {
+ if (alias->builtin_modname)
+ break;
+ alias->builtin_modname = xstrndup(modname, modnamelen);
+ }
+ }
+
free(zeros);
}
diff --git a/scripts/mod/modpost.c b/scripts/mod/modpost.c
index 5ca7c268294e..47c8aa2a6939 100644
--- a/scripts/mod/modpost.c
+++ b/scripts/mod/modpost.c
@@ -2067,11 +2067,26 @@ static void write_if_changed(struct buffer *b, const char *fname)
static void write_vmlinux_export_c_file(struct module *mod)
{
struct buffer buf = { };
+ struct module_alias *alias, *next;
buf_printf(&buf,
"#include <linux/export-internal.h>\n");
add_exported_symbols(&buf, mod);
+
+ buf_printf(&buf,
+ "#include <linux/module.h>\n"
+ "#undef __MODULE_INFO_PREFIX\n"
+ "#define __MODULE_INFO_PREFIX\n");
+
+ list_for_each_entry_safe(alias, next, &mod->aliases, node) {
+ buf_printf(&buf, "MODULE_INFO(%s.alias, \"%s\");\n",
+ alias->builtin_modname, alias->str);
+ list_del(&alias->node);
+ free(alias->builtin_modname);
+ free(alias);
+ }
+
write_if_changed(&buf, ".vmlinux.export.c");
free(buf.p);
}
diff --git a/scripts/mod/modpost.h b/scripts/mod/modpost.h
index 9133e4c3803f..2aecb8f25c87 100644
--- a/scripts/mod/modpost.h
+++ b/scripts/mod/modpost.h
@@ -99,10 +99,12 @@ buf_write(struct buffer *buf, const char *s, int len);
* struct module_alias - auto-generated MODULE_ALIAS()
*
* @node: linked to module::aliases
+ * @modname: name of the builtin module (only for vmlinux)
* @str: a string for MODULE_ALIAS()
*/
struct module_alias {
struct list_head node;
+ char *builtin_modname;
char str[];
};
diff --git a/security/apparmor/policy.c b/security/apparmor/policy.c
index 261a9d3a0afe..50d5345ff5cb 100644
--- a/security/apparmor/policy.c
+++ b/security/apparmor/policy.c
@@ -243,6 +243,9 @@ static void free_ruleset(struct aa_ruleset *rules)
{
int i;
+ if (!rules)
+ return;
+
aa_put_pdb(rules->file);
aa_put_pdb(rules->policy);
aa_free_cap_rules(&rules->caps);
@@ -335,7 +338,6 @@ struct aa_profile *aa_alloc_profile(const char *hname, struct aa_proxy *proxy,
profile = kzalloc(struct_size(profile, label.rules, 1), gfp);
if (!profile)
return NULL;
- profile->n_rules = 1;
if (!aa_policy_init(&profile->base, NULL, hname, gfp))
goto fail;
@@ -346,6 +348,7 @@ struct aa_profile *aa_alloc_profile(const char *hname, struct aa_proxy *proxy,
profile->label.rules[0] = aa_alloc_ruleset(gfp);
if (!profile->label.rules[0])
goto fail;
+ profile->n_rules = 1;
/* update being set needed by fs interface */
if (!proxy) {
diff --git a/sound/hda/codecs/realtek/alc269.c b/sound/hda/codecs/realtek/alc269.c
index 2554b42eeb0f..e27a36e4e92a 100644
--- a/sound/hda/codecs/realtek/alc269.c
+++ b/sound/hda/codecs/realtek/alc269.c
@@ -7110,6 +7110,7 @@ static const struct hda_quirk alc269_fixup_tbl[] = {
SND_PCI_QUIRK(0x1854, 0x0440, "LG CQ6", ALC256_FIXUP_HEADPHONE_AMP_VOL),
SND_PCI_QUIRK(0x1854, 0x0441, "LG CQ6 AIO", ALC256_FIXUP_HEADPHONE_AMP_VOL),
SND_PCI_QUIRK(0x1854, 0x0488, "LG gram 16 (16Z90R)", ALC298_FIXUP_SAMSUNG_AMP_V2_4_AMPS),
+ SND_PCI_QUIRK(0x1854, 0x0489, "LG gram 16 (16Z90R-A)", ALC298_FIXUP_SAMSUNG_AMP_V2_4_AMPS),
SND_PCI_QUIRK(0x1854, 0x048a, "LG gram 17 (17ZD90R)", ALC298_FIXUP_SAMSUNG_AMP_V2_4_AMPS),
SND_PCI_QUIRK(0x19e5, 0x3204, "Huawei MACH-WX9", ALC256_FIXUP_HUAWEI_MACH_WX9_PINS),
SND_PCI_QUIRK(0x19e5, 0x320f, "Huawei WRT-WX9 ", ALC256_FIXUP_ASUS_MIC_NO_PRESENCE),
diff --git a/sound/usb/pcm.c b/sound/usb/pcm.c
index b24ee38fad72..bff92505e408 100644
--- a/sound/usb/pcm.c
+++ b/sound/usb/pcm.c
@@ -1336,11 +1336,10 @@ static void retire_capture_urb(struct snd_usb_substream *subs,
for (i = 0; i < urb->number_of_packets; i++) {
cp = (unsigned char *)urb->transfer_buffer + urb->iso_frame_desc[i].offset + subs->pkt_offset_adj;
- if (urb->iso_frame_desc[i].status && printk_ratelimit()) {
- dev_dbg(&subs->dev->dev, "frame %d active: %d\n",
- i, urb->iso_frame_desc[i].status);
- // continue;
- }
+ if (urb->iso_frame_desc[i].status)
+ dev_dbg_ratelimited(&subs->dev->dev,
+ "frame %d active: %d\n", i,
+ urb->iso_frame_desc[i].status);
bytes = urb->iso_frame_desc[i].actual_length;
if (subs->stream_offset_adj > 0) {
unsigned int adj = min(subs->stream_offset_adj, bytes);
diff --git a/tools/accounting/getdelays.c b/tools/accounting/getdelays.c
index 3feac0482fe9..21cb3c3d1331 100644
--- a/tools/accounting/getdelays.c
+++ b/tools/accounting/getdelays.c
@@ -194,75 +194,108 @@ static int get_family_id(int sd)
#define average_ms(t, c) (t / 1000000ULL / (c ? c : 1))
#define delay_ms(t) (t / 1000000ULL)
+/*
+ * Version compatibility note:
+ * Field availability depends on taskstats version (t->version),
+ * corresponding to TASKSTATS_VERSION in kernel headers
+ * see include/uapi/linux/taskstats.h
+ *
+ * Version feature mapping:
+ * version >= 11 - supports COMPACT statistics
+ * version >= 13 - supports WPCOPY statistics
+ * version >= 14 - supports IRQ statistics
+ * version >= 16 - supports *_max and *_min delay statistics
+ *
+ * Always verify version before accessing version-dependent fields
+ * to maintain backward compatibility.
+ */
+#define PRINT_CPU_DELAY(version, t) \
+ do { \
+ if (version >= 16) { \
+ printf("%-10s%15s%15s%15s%15s%15s%15s%15s\n", \
+ "CPU", "count", "real total", "virtual total", \
+ "delay total", "delay average", "delay max", "delay min"); \
+ printf(" %15llu%15llu%15llu%15llu%15.3fms%13.6fms%13.6fms\n", \
+ (unsigned long long)(t)->cpu_count, \
+ (unsigned long long)(t)->cpu_run_real_total, \
+ (unsigned long long)(t)->cpu_run_virtual_total, \
+ (unsigned long long)(t)->cpu_delay_total, \
+ average_ms((double)(t)->cpu_delay_total, (t)->cpu_count), \
+ delay_ms((double)(t)->cpu_delay_max), \
+ delay_ms((double)(t)->cpu_delay_min)); \
+ } else { \
+ printf("%-10s%15s%15s%15s%15s%15s\n", \
+ "CPU", "count", "real total", "virtual total", \
+ "delay total", "delay average"); \
+ printf(" %15llu%15llu%15llu%15llu%15.3fms\n", \
+ (unsigned long long)(t)->cpu_count, \
+ (unsigned long long)(t)->cpu_run_real_total, \
+ (unsigned long long)(t)->cpu_run_virtual_total, \
+ (unsigned long long)(t)->cpu_delay_total, \
+ average_ms((double)(t)->cpu_delay_total, (t)->cpu_count)); \
+ } \
+ } while (0)
+#define PRINT_FILED_DELAY(name, version, t, count, total, max, min) \
+ do { \
+ if (version >= 16) { \
+ printf("%-10s%15s%15s%15s%15s%15s\n", \
+ name, "count", "delay total", "delay average", \
+ "delay max", "delay min"); \
+ printf(" %15llu%15llu%15.3fms%13.6fms%13.6fms\n", \
+ (unsigned long long)(t)->count, \
+ (unsigned long long)(t)->total, \
+ average_ms((double)(t)->total, (t)->count), \
+ delay_ms((double)(t)->max), \
+ delay_ms((double)(t)->min)); \
+ } else { \
+ printf("%-10s%15s%15s%15s\n", \
+ name, "count", "delay total", "delay average"); \
+ printf(" %15llu%15llu%15.3fms\n", \
+ (unsigned long long)(t)->count, \
+ (unsigned long long)(t)->total, \
+ average_ms((double)(t)->total, (t)->count)); \
+ } \
+ } while (0)
+
static void print_delayacct(struct taskstats *t)
{
- printf("\n\nCPU %15s%15s%15s%15s%15s%15s%15s\n"
- " %15llu%15llu%15llu%15llu%15.3fms%13.6fms%13.6fms\n"
- "IO %15s%15s%15s%15s%15s\n"
- " %15llu%15llu%15.3fms%13.6fms%13.6fms\n"
- "SWAP %15s%15s%15s%15s%15s\n"
- " %15llu%15llu%15.3fms%13.6fms%13.6fms\n"
- "RECLAIM %12s%15s%15s%15s%15s\n"
- " %15llu%15llu%15.3fms%13.6fms%13.6fms\n"
- "THRASHING%12s%15s%15s%15s%15s\n"
- " %15llu%15llu%15.3fms%13.6fms%13.6fms\n"
- "COMPACT %12s%15s%15s%15s%15s\n"
- " %15llu%15llu%15.3fms%13.6fms%13.6fms\n"
- "WPCOPY %12s%15s%15s%15s%15s\n"
- " %15llu%15llu%15.3fms%13.6fms%13.6fms\n"
- "IRQ %15s%15s%15s%15s%15s\n"
- " %15llu%15llu%15.3fms%13.6fms%13.6fms\n",
- "count", "real total", "virtual total",
- "delay total", "delay average", "delay max", "delay min",
- (unsigned long long)t->cpu_count,
- (unsigned long long)t->cpu_run_real_total,
- (unsigned long long)t->cpu_run_virtual_total,
- (unsigned long long)t->cpu_delay_total,
- average_ms((double)t->cpu_delay_total, t->cpu_count),
- delay_ms((double)t->cpu_delay_max),
- delay_ms((double)t->cpu_delay_min),
- "count", "delay total", "delay average", "delay max", "delay min",
- (unsigned long long)t->blkio_count,
- (unsigned long long)t->blkio_delay_total,
- average_ms((double)t->blkio_delay_total, t->blkio_count),
- delay_ms((double)t->blkio_delay_max),
- delay_ms((double)t->blkio_delay_min),
- "count", "delay total", "delay average", "delay max", "delay min",
- (unsigned long long)t->swapin_count,
- (unsigned long long)t->swapin_delay_total,
- average_ms((double)t->swapin_delay_total, t->swapin_count),
- delay_ms((double)t->swapin_delay_max),
- delay_ms((double)t->swapin_delay_min),
- "count", "delay total", "delay average", "delay max", "delay min",
- (unsigned long long)t->freepages_count,
- (unsigned long long)t->freepages_delay_total,
- average_ms((double)t->freepages_delay_total, t->freepages_count),
- delay_ms((double)t->freepages_delay_max),
- delay_ms((double)t->freepages_delay_min),
- "count", "delay total", "delay average", "delay max", "delay min",
- (unsigned long long)t->thrashing_count,
- (unsigned long long)t->thrashing_delay_total,
- average_ms((double)t->thrashing_delay_total, t->thrashing_count),
- delay_ms((double)t->thrashing_delay_max),
- delay_ms((double)t->thrashing_delay_min),
- "count", "delay total", "delay average", "delay max", "delay min",
- (unsigned long long)t->compact_count,
- (unsigned long long)t->compact_delay_total,
- average_ms((double)t->compact_delay_total, t->compact_count),
- delay_ms((double)t->compact_delay_max),
- delay_ms((double)t->compact_delay_min),
- "count", "delay total", "delay average", "delay max", "delay min",
- (unsigned long long)t->wpcopy_count,
- (unsigned long long)t->wpcopy_delay_total,
- average_ms((double)t->wpcopy_delay_total, t->wpcopy_count),
- delay_ms((double)t->wpcopy_delay_max),
- delay_ms((double)t->wpcopy_delay_min),
- "count", "delay total", "delay average", "delay max", "delay min",
- (unsigned long long)t->irq_count,
- (unsigned long long)t->irq_delay_total,
- average_ms((double)t->irq_delay_total, t->irq_count),
- delay_ms((double)t->irq_delay_max),
- delay_ms((double)t->irq_delay_min));
+ printf("\n\n");
+
+ PRINT_CPU_DELAY(t->version, t);
+
+ PRINT_FILED_DELAY("IO", t->version, t,
+ blkio_count, blkio_delay_total,
+ blkio_delay_max, blkio_delay_min);
+
+ PRINT_FILED_DELAY("SWAP", t->version, t,
+ swapin_count, swapin_delay_total,
+ swapin_delay_max, swapin_delay_min);
+
+ PRINT_FILED_DELAY("RECLAIM", t->version, t,
+ freepages_count, freepages_delay_total,
+ freepages_delay_max, freepages_delay_min);
+
+ PRINT_FILED_DELAY("THRASHING", t->version, t,
+ thrashing_count, thrashing_delay_total,
+ thrashing_delay_max, thrashing_delay_min);
+
+ if (t->version >= 11) {
+ PRINT_FILED_DELAY("COMPACT", t->version, t,
+ compact_count, compact_delay_total,
+ compact_delay_max, compact_delay_min);
+ }
+
+ if (t->version >= 13) {
+ PRINT_FILED_DELAY("WPCOPY", t->version, t,
+ wpcopy_count, wpcopy_delay_total,
+ wpcopy_delay_max, wpcopy_delay_min);
+ }
+
+ if (t->version >= 14) {
+ PRINT_FILED_DELAY("IRQ", t->version, t,
+ irq_count, irq_delay_total,
+ irq_delay_max, irq_delay_min);
+ }
}
static void task_context_switch_counts(struct taskstats *t)
diff --git a/tools/perf/util/build-id.c b/tools/perf/util/build-id.c
index e2b295fe4d2f..a7018a3b0437 100644
--- a/tools/perf/util/build-id.c
+++ b/tools/perf/util/build-id.c
@@ -872,7 +872,7 @@ static int dso__cache_build_id(struct dso *dso, struct machine *machine,
char *allocated_name = NULL;
int ret = 0;
- if (!dso__has_build_id(dso))
+ if (!dso__has_build_id(dso) || !dso__hit(dso))
return 0;
if (dso__is_kcore(dso)) {
diff --git a/tools/testing/selftests/bpf/progs/verifier_ctx.c b/tools/testing/selftests/bpf/progs/verifier_ctx.c
index 0450840c92d9..424463094760 100644
--- a/tools/testing/selftests/bpf/progs/verifier_ctx.c
+++ b/tools/testing/selftests/bpf/progs/verifier_ctx.c
@@ -1,10 +1,12 @@
// SPDX-License-Identifier: GPL-2.0
/* Converted from tools/testing/selftests/bpf/verifier/ctx.c */
-#include <linux/bpf.h>
+#include "vmlinux.h"
#include <bpf/bpf_helpers.h>
#include "bpf_misc.h"
+#define sizeof_field(TYPE, MEMBER) sizeof((((TYPE *)0)->MEMBER))
+
SEC("tc")
__description("context stores via BPF_ATOMIC")
__failure __msg("BPF_ATOMIC stores into R1 ctx is not allowed")
@@ -243,4 +245,23 @@ narrow_load("sockops", bpf_sock_ops, skb_data);
narrow_load("sockops", bpf_sock_ops, skb_data_end);
narrow_load("sockops", bpf_sock_ops, skb_hwtstamp);
+#define unaligned_access(type, ctx, field) \
+ SEC(type) \
+ __description("unaligned access on field " #field " of " #ctx) \
+ __failure __msg("invalid bpf_context access") \
+ __naked void unaligned_ctx_access_##ctx##field(void) \
+ { \
+ asm volatile (" \
+ r1 = *(u%[size] *)(r1 + %[off]); \
+ r0 = 0; \
+ exit;" \
+ : \
+ : __imm_const(size, sizeof_field(struct ctx, field) * 8), \
+ __imm_const(off, offsetof(struct ctx, field) + 1) \
+ : __clobber_all); \
+ }
+
+unaligned_access("flow_dissector", __sk_buff, data);
+unaligned_access("netfilter", bpf_nf_ctx, skb);
+
char _license[] SEC("license") = "GPL";
diff --git a/tools/testing/selftests/mm/uffd-stress.c b/tools/testing/selftests/mm/uffd-stress.c
index 40af7f67c407..c0f64df5085c 100644
--- a/tools/testing/selftests/mm/uffd-stress.c
+++ b/tools/testing/selftests/mm/uffd-stress.c
@@ -51,7 +51,7 @@ static char *zeropage;
pthread_attr_t attr;
#define swap(a, b) \
- do { typeof(a) __tmp = (a); (a) = (b); (b) = __tmp; } while (0)
+ do { __auto_type __tmp = (a); (a) = (b); (b) = __tmp; } while (0)
const char *examples =
"# Run anonymous memory test on 100MiB region with 99999 bounces:\n"
diff --git a/tools/testing/selftests/net/test_neigh.sh b/tools/testing/selftests/net/test_neigh.sh
index 388056472b5b..7c594bf6ead0 100755
--- a/tools/testing/selftests/net/test_neigh.sh
+++ b/tools/testing/selftests/net/test_neigh.sh
@@ -289,11 +289,11 @@ extern_valid_common()
orig_base_reachable=$(ip -j ntable show name "$tbl_name" | jq '.[] | select(has("thresh1")) | .["base_reachable"]')
run_cmd "ip ntable change name $tbl_name thresh1 10 base_reachable 10000"
orig_gc_stale=$(ip -n "$ns1" -j ntable show name "$tbl_name" dev veth0 | jq '.[]["gc_stale"]')
- run_cmd "ip -n $ns1 ntable change name $tbl_name dev veth0 gc_stale 5000"
- # Wait orig_base_reachable/2 for the new interval to take effect.
- run_cmd "sleep $(((orig_base_reachable / 1000) / 2 + 2))"
+ run_cmd "ip -n $ns1 ntable change name $tbl_name dev veth0 gc_stale 1000"
run_cmd "ip -n $ns1 neigh add $ip_addr lladdr $mac nud stale dev veth0 extern_valid"
run_cmd "ip -n $ns1 neigh add ${subnet}3 lladdr $mac nud stale dev veth0"
+ # Wait orig_base_reachable/2 for the new interval to take effect.
+ run_cmd "sleep $(((orig_base_reachable / 1000) / 2 + 2))"
for i in {1..20}; do
run_cmd "ip -n $ns1 neigh add ${subnet}$((i + 4)) nud none dev veth0"
done
diff --git a/tools/testing/selftests/net/vlan_hw_filter.sh b/tools/testing/selftests/net/vlan_hw_filter.sh
index 0fb56baf28e4..e195d5cab6f7 100755
--- a/tools/testing/selftests/net/vlan_hw_filter.sh
+++ b/tools/testing/selftests/net/vlan_hw_filter.sh
@@ -55,10 +55,10 @@ test_vlan0_del_crash_01() {
ip netns exec ${NETNS} ip link add bond0 type bond mode 0
ip netns exec ${NETNS} ip link add link bond0 name vlan0 type vlan id 0 protocol 802.1q
ip netns exec ${NETNS} ethtool -K bond0 rx-vlan-filter off
- ip netns exec ${NETNS} ifconfig bond0 up
+ ip netns exec ${NETNS} ip link set dev bond0 up
ip netns exec ${NETNS} ethtool -K bond0 rx-vlan-filter on
- ip netns exec ${NETNS} ifconfig bond0 down
- ip netns exec ${NETNS} ifconfig bond0 up
+ ip netns exec ${NETNS} ip link set dev bond0 down
+ ip netns exec ${NETNS} ip link set dev bond0 up
ip netns exec ${NETNS} ip link del vlan0 || fail "Please check vlan HW filter function"
cleanup
}
@@ -68,11 +68,11 @@ test_vlan0_del_crash_02() {
setup
ip netns exec ${NETNS} ip link add bond0 type bond mode 0
ip netns exec ${NETNS} ethtool -K bond0 rx-vlan-filter off
- ip netns exec ${NETNS} ifconfig bond0 up
+ ip netns exec ${NETNS} ip link set dev bond0 up
ip netns exec ${NETNS} ethtool -K bond0 rx-vlan-filter on
ip netns exec ${NETNS} ip link add link bond0 name vlan0 type vlan id 0 protocol 802.1q
- ip netns exec ${NETNS} ifconfig bond0 down
- ip netns exec ${NETNS} ifconfig bond0 up
+ ip netns exec ${NETNS} ip link set dev bond0 down
+ ip netns exec ${NETNS} ip link set dev bond0 up
ip netns exec ${NETNS} ip link del vlan0 || fail "Please check vlan HW filter function"
cleanup
}
@@ -84,9 +84,9 @@ test_vlan0_del_crash_03() {
ip netns exec ${NETNS} ip link add bond0 type bond mode 0
ip netns exec ${NETNS} ip link add link bond0 name vlan0 type vlan id 0 protocol 802.1q
ip netns exec ${NETNS} ethtool -K bond0 rx-vlan-filter off
- ip netns exec ${NETNS} ifconfig bond0 up
+ ip netns exec ${NETNS} ip link set dev bond0 up
ip netns exec ${NETNS} ethtool -K bond0 rx-vlan-filter on
- ip netns exec ${NETNS} ifconfig bond0 down
+ ip netns exec ${NETNS} ip link set dev bond0 down
ip netns exec ${NETNS} ip link del vlan0 || fail "Please check vlan HW filter function"
cleanup
}