add qcom-samsung specific files

This commit is contained in:
SaschaNes
2025-08-13 08:47:43 +02:00
parent 87bde3e404
commit 1d1685d4ce
553 changed files with 71089 additions and 1859 deletions

View File

@@ -1 +1 @@
../../../../../qcom/opensource/devicetree ../../../../../sm8750-devicetrees/

View File

@@ -74,7 +74,8 @@ CONFIG_PROFILING=y
CONFIG_ARCH_SUNXI=y CONFIG_ARCH_SUNXI=y
CONFIG_ARCH_HISI=y CONFIG_ARCH_HISI=y
CONFIG_ARCH_QCOM=y CONFIG_ARCH_QCOM=y
CONFIG_ARCH_KALAMA=y # CONFIG_ARCH_KALAMA is not set
COFIG_ARCH_SUN=y
CONFIG_SCHED_MC=y CONFIG_SCHED_MC=y
CONFIG_NR_CPUS=32 CONFIG_NR_CPUS=32
CONFIG_PARAVIRT_TIME_ACCOUNTING=y CONFIG_PARAVIRT_TIME_ACCOUNTING=y

View File

@@ -80,7 +80,7 @@ config QCOM_CLK_RPM
config QCOM_CLK_SMD_RPM config QCOM_CLK_SMD_RPM
tristate "RPM over SMD based Clock Controller" tristate "RPM over SMD based Clock Controller"
depends on QCOM_SMD_RPM depends on MSM_RPM_SMD
select QCOM_RPMCC select QCOM_RPMCC
help help
The RPM (Resource Power Manager) is a dedicated hardware engine for The RPM (Resource Power Manager) is a dedicated hardware engine for
@@ -148,7 +148,7 @@ config IPQ_GCC_4019
config IPQ_GCC_5018 config IPQ_GCC_5018
tristate "IPQ5018 Global Clock Controller" tristate "IPQ5018 Global Clock Controller"
depends on ARM || ARM64 || COMPILE_TEST depends on ARM64 || COMPILE_TEST
help help
Support for global clock controller on ipq5018 devices. Support for global clock controller on ipq5018 devices.
Say Y if you want to use peripheral devices such as UART, SPI, Say Y if you want to use peripheral devices such as UART, SPI,
@@ -741,6 +741,15 @@ config SDX_GCC_75
Say Y if you want to use peripheral devices such as UART, Say Y if you want to use peripheral devices such as UART,
SPI, I2C, USB, SD/eMMC, PCIe etc. SPI, I2C, USB, SD/eMMC, PCIe etc.
config SDX_DEBUGCC_75
tristate "SDX75 Debug Clock Controller"
depends on SDX_GCC_75
help
Support for the debug clock controller on Qualcomm Technologies, Inc.
SDX75 devices.
Say Y if you want to support the debug clocks such as clock measurement
functionality.
config SM_CAMCC_6350 config SM_CAMCC_6350
tristate "SM6350 Camera Clock Controller" tristate "SM6350 Camera Clock Controller"
depends on ARM64 || COMPILE_TEST depends on ARM64 || COMPILE_TEST
@@ -835,6 +844,55 @@ config SM_DISPCC_8550
Say Y if you want to support display devices and functionality such as Say Y if you want to support display devices and functionality such as
splash screen. splash screen.
config SM_GCC_4450
tristate "SM4450 Global Clock Controller"
depends on ARM64 || COMPILE_TEST
select QCOM_GDSC
help
Support for the global clock controller on Qualcomm Technologies, Inc
SM4450 devices.
Say Y if you want to use peripheral devices such as UART, SPI, I2C,
USB, UFS, SD/eMMC, PCIe, Video, etc.
config SM_CAMCC_4450
tristate "SM4450 Camera Clock Controller"
depends on ARM64 || COMPILE_TEST
select SM_GCC_4450
help
Support for the camera clock controller on Qualcomm Technologies, Inc.
SM4450 devices.
Say Y if you want to support camera devices and functionality such as
capturing photos.
config SM_GPUCC_4450
tristate "SM4450 Graphics Clock Controller"
depends on ARM64 || COMPILE_TEST
select SM_GCC_4450
help
Support for the graphics clock controller on Qualcomm Technologies, Inc.
SM4450 devices.
Say Y if you want to support graphics controller devices and
functionality such as 3D-graphics.
config SM_DISPCC_4450
tristate "SM4450 Display Clock Controller"
depends on ARM64 || COMPILE_TEST
depends on SM_GCC_4450
help
Support for the display clock controller on Qualcomm Technologies, Inc
SM4450 devices.
Say Y if you want to support display devices and functionality such as
splash screen
config SM_DEBUGCC_4450
tristate "SM4450 Debug Clock Controller"
depends on SM_GCC_4450
help
Support for the debug clock controller on Qualcomm Technologies, Inc.
SM4450 devices.
Say Y if you want to support the debug clocks such as clock measurement
functionality.
config SM_GCC_6115 config SM_GCC_6115
tristate "SM6115 and SM4250 Global Clock Controller" tristate "SM6115 and SM4250 Global Clock Controller"
depends on ARM64 || COMPILE_TEST depends on ARM64 || COMPILE_TEST
@@ -881,7 +939,6 @@ config SM_GCC_7150
config SM_GCC_8150 config SM_GCC_8150
tristate "SM8150 Global Clock Controller" tristate "SM8150 Global Clock Controller"
depends on ARM64 || COMPILE_TEST depends on ARM64 || COMPILE_TEST
select QCOM_GDSC
help help
Support for the global clock controller on SM8150 devices. Support for the global clock controller on SM8150 devices.
Say Y if you want to use peripheral devices such as UART, Say Y if you want to use peripheral devices such as UART,
@@ -914,6 +971,12 @@ config SM_GCC_8450
Say Y if you want to use peripheral devices such as UART, Say Y if you want to use peripheral devices such as UART,
SPI, I2C, USB, SD/UFS, PCIe etc. SPI, I2C, USB, SD/UFS, PCIe etc.
config SM_GCC_SUN
tristate "SUN Global Clock Controller"
help
Support for the global clock controller on Qualcomm Technologies, Inc
Sun devices.
config SM_GCC_8550 config SM_GCC_8550
tristate "SM8550 Global Clock Controller" tristate "SM8550 Global Clock Controller"
depends on ARM64 || COMPILE_TEST depends on ARM64 || COMPILE_TEST
@@ -923,6 +986,131 @@ config SM_GCC_8550
Say Y if you want to use peripheral devices such as UART, Say Y if you want to use peripheral devices such as UART,
SPI, I2C, USB, SD/UFS, PCIe etc. SPI, I2C, USB, SD/UFS, PCIe etc.
config SM_GCC_PINEAPPLE
tristate "Pineapple Global Clock Controller"
help
Support for the global clock controller on Qualcomm Technologies, Inc
Pineapple devices.
Say Y if you want to use peripheral devices such as UART,
SPI, I2C, USB, SD/UFS, PCIe etc.
config SM_VIDEOCC_PINEAPPLE
tristate "Pineapple Video Clock Controller"
depends on SM_GCC_PINEAPPLE
help
Support for the video clock controller on Qualcomm Technologies, Inc.
Pineapple devices.
Say Y if you want to support video devices and functionality such as
video encode/decode.
config SM_CAMCC_PINEAPPLE
tristate "Pineapple Camera Clock Controller"
depends on SM_GCC_PINEAPPLE
help
Support for the camera clock controller on Qualcomm Technologies, Inc
Pineapple devices.
Say Y if you want to support camera devices and functionality such as
capturing pictures.
config SM_DISPCC_PINEAPPLE
tristate "Pineapple Display Clock Controller"
depends on SM_GCC_PINEAPPLE
help
Support for the display clock controller on Qualcomm Technologies, Inc
Pineapple devices.
Say Y if you want to support display devices and functionality such as
splash screen.
config SM_DEBUGCC_PINEAPPLE
tristate "Pineapple Debug Clock Controller"
depends on COMMON_CLK_QCOM
help
Support for the debug clock controller on Qualcomm Technologies, Inc
Pineapple devices.
Say Y if you want to support the debug clocks such as
clock measurement functionality.
config SM_GPUCC_PINEAPPLE
tristate "Pineapple Graphics Clock Controller"
depends on SM_GCC_PINEAPPLE
help
Support for the graphics clock controller on Qualcomm Technologies, Inc
Pineapple devices.
Say Y if you want to support graphics controller devices and
functionality such as 3D graphics.
config SM_TCSRCC_PINEAPPLE
tristate "Pineapple Top-Level CSR Clock Controller"
depends on SM_GCC_PINEAPPLE
help
Support for the TCSR clock controller on Qualcomm Technologies, Inc
Pineapple devices.
Say Y if you want to support miscellaneous top-level clocks
such as for the PHY references.
config SM_CAMCC_SUN
tristate "SUN Camera Clock Controller"
depends on SM_GCC_SUN
help
Support for the camera clock controller on Qualcomm Technologies, Inc
Sun devices.
Say Y if you want to support camera devices and functionality such as
capturing pictures.
config SM_EVACC_SUN
tristate "SUN EVA Clock Controller"
depends on SM_GCC_SUN
help
Support for the EVA clock controller on Qualcomm Technologies, Inc
Sun devices.
Say Y if you want to support EVA devices to get better
visual analysis.
config SM_GPUCC_SUN
tristate "SUN Graphics Clock Controller"
depends on SM_GCC_SUN
help
Support for the graphics clock controller on Qualcomm Technologies, Inc
Sun devices.
Say Y if you want to support graphics controller devices and
functionality such as 3D graphics.
config SM_DISPCC_SUN
tristate "SUN Display Clock Controller"
depends on SM_GCC_SUN
help
Support for the display clock controller on Qualcomm Technologies, Inc
Sun devices.
Say Y if you want to support display devices and functionality such as
splash screen.
config SM_CAMBISTMCLKCC_SUN
tristate "SUN CAMBISTMCLK Clock Controller"
depends on SM_GCC_SUN
help
Support for the CAMBISTMCLK clock controller on Qualcomm Technologies,
Inc Sun devices.
Say Y if you want to support camera devices for a better low-latency
clock.
config SM_TCSRCC_SUN
tristate "SUN Top-Level CSR Clock Controller"
depends on SM_GCC_SUN
help
Support for the TCSR clock controller on Qualcomm Technologies, Inc
Sun devices.
Say Y if you want to support miscellaneous top-level clocks
such as for the PHY references.
config SM_DEBUGCC_SUN
tristate "Sun Debug Clock Controller"
depends on COMMON_CLK_QCOM
help
Support for the debug clock controller on Qualcomm Technologies, Inc
Sun devices.
Say Y if you want to support the debug clocks such as clock
measurement functionality.
config SM_GPUCC_6115 config SM_GPUCC_6115
tristate "SM6115 Graphics Clock Controller" tristate "SM6115 Graphics Clock Controller"
select SM_GCC_6115 select SM_GCC_6115
@@ -1051,6 +1239,14 @@ config SM_VIDEOCC_8550
Support for the video clock controller on Qualcomm Technologies, Inc. Support for the video clock controller on Qualcomm Technologies, Inc.
SM8550 devices. SM8550 devices.
Say Y if you want to support video devices and functionality such as Say Y if you want to support video devices and functionality such as
config SM_VIDEOCC_SUN
tristate "SUN Video Clock Controller"
depends on SM_GCC_SUN
help
Support for the video clock controller on Qualcomm Technologies, Inc
SUN devices.
Say Y if you want to support video devices and functionality such as
video encode/decode. video encode/decode.
config SPMI_PMIC_CLKDIV config SPMI_PMIC_CLKDIV
@@ -1091,6 +1287,16 @@ config CLK_GFM_LPASS_SM8250
Support for the Glitch Free Mux (GFM) Low power audio Support for the Glitch Free Mux (GFM) Low power audio
subsystem (LPASS) clocks found on SM8250 SoCs. subsystem (LPASS) clocks found on SM8250 SoCs.
config QCOM_GDSC_REGULATOR
tristate "GDSC regulator driver"
depends on COMMON_CLK_QCOM
help
This driver supports globally distributed switch controller (GDSC)
devices in regulator framework.
Say Y if you want to support clients using regulator framework APIs
to control GDSCs.
config SM_VIDEOCC_8450 config SM_VIDEOCC_8450
tristate "SM8450 Video Clock Controller" tristate "SM8450 Video Clock Controller"
depends on ARM64 || COMPILE_TEST depends on ARM64 || COMPILE_TEST
@@ -1101,4 +1307,176 @@ config SM_VIDEOCC_8450
SM8450 devices. SM8450 devices.
Say Y if you want to support video devices and functionality such as Say Y if you want to support video devices and functionality such as
video encode/decode. video encode/decode.
config SM_GCC_PARROT
tristate "PARROT Global Clock Controller"
depends on COMMON_CLK_QCOM
help
Support for the global clock controller on Qualcomm Technologies, Inc
PARROT devices.
Say Y if you want to use peripheral devices such as UART, SPI, I2C,
USB, UFS, SD/eMMC, PCIe, etc.
config SM_DISPCC_PARROT
tristate "PARROT Display Clock Controller"
select SM_GCC_PARROT
help
Support for the display clock controller on Qualcomm Technologies, Inc
PARROT devices.
Say Y if you want to support display devices and functionality such as
splash screen.
config SM_GPUCC_PARROT
tristate "PARROT Graphics Clock Controller"
select SM_GCC_PARROT
help
Support for the graphics clock controller on Qualcomm Technologies, Inc.
PARROT devices.
Say Y if you want to support graphics controller devices and
functionality such as 3D graphics.
config SM_CAMCC_PARROT
tristate "PARROT Camera Clock Controller"
select SM_GCC_PARROT
help
Support for the camera clock controller on Qualcomm Technologies, Inc.
PARROT devices.
Say Y if you want to support camera devices and functionality such as
capturing pictures.
config SM_VIDEOCC_PARROT
tristate "PARROT Video Clock Controller"
select SM_GCC_PARROT
help
Support for the video clock controller on Qualcomm Technologies, Inc.
PARROT devices.
Say Y if you want to support video devices and functionality such as
video encode/decode.
config SM_DEBUGCC_PARROT
tristate "PARROT Debug Clock Controller"
depends on SM_GCC_PARROT
help
Support for the debug clock controller on Qualcomm Technologies, Inc.
PARROT devices.
Say Y if you want to support the debug clocks such as clock measurement
functionality.
config SM_GCC_TUNA
tristate "Tuna Global Clock Controller"
depends on COMMON_CLK_QCOM
help
Support for the global clock controller on Qualcomm Technologies, Inc
Tuna devices.
Say Y if you want to use peripheral devices such as UART, SPI, I2C,
USB, SD/UFS, PCIe etc.
config SM_TCSRCC_TUNA
tristate "Tuna Top-Level CSR Clock Controller"
depends on SM_GCC_TUNA || SM_GCC_KERA
help
Support for the TCSR clock controller on Qualcomm Technologies, Inc
Tuna devices.
Say Y if you want to support miscellaneous top-level clocks
such as for the PHY references.
config SDW_GCC_MONACO
tristate "MONACO Global Clock Controller"
depends on COMMON_CLK_QCOM
help
Support for the global clock controller on Qualcomm Technologies, Inc.
MONACO devices.
Say Y if you want to use peripheral devices such as UART, SPI, I2C,
USB, SD/eMMC, etc.
config SDW_GPUCC_MONACO
tristate "MONACO Graphics Clock Controller"
select SDW_GCC_MONACO
help
Support for the graphics clock controller on Qualcomm Technologies, Inc.
MONACO devices.
Say Y if you want to support graphics controller devices and
functionality such as 3D graphics.
config SDW_DISPCC_MONACO
tristate "MONACO Display Clock Controller"
depends on SDW_GCC_MONACO
help
Support for the display clock controller on Qualcomm Technologies, Inc.
MONACO devices.
Say Y if you want to support display devices and functionality such as
splash screen.
config SDW_DEBUGCC_MONACO
tristate "MONACO Debug Clock Controller"
depends on COMMON_CLK_QCOM
help
Support for the debug clock controller on Qualcomm Technologies, Inc
MONACO devices.
Say Y if you want to support the debug clocks such as
clock measurement functionality.
config SM_VIDEOCC_TUNA
tristate "TUNA Video Clock Controller"
depends on SM_GCC_TUNA
help
Support for the video clock controller on Qualcomm Technologies, Inc.
TUNA devices.
Say Y if you want to support video devices and functionality such as
video encode/decode.
config SM_EVACC_TUNA
tristate "TUNA EVA Clock Controller"
depends on SM_GCC_TUNA
help
Support for the EVA clock controller on Qualcomm Technologies, Inc
TUNA devices.
Say Y if you want to support EVA devices to get better
visual analysis.
config SM_GPUCC_TUNA
tristate "TUNA Graphics Clock Controller"
depends on SM_GCC_TUNA
help
Support for the graphics clock controller on Qualcomm Technologies, Inc
Tuna devices.
Say Y if you want to support graphics controller devices and
functionality such as 3D graphics.
config SM_GCC_KERA
tristate "Kera Global Clock Controller"
depends on COMMON_CLK_QCOM
help
Support for the global clock controller on Qualcomm Technologies, Inc
Kera devices.
Say Y if you want to use peripheral devices such as UART, SPI, I2C,
USB, SD/UFS, PCIe etc.
config SM_CAMCC_TUNA
tristate "TUNA Camera Clock Controller"
depends on SM_GCC_TUNA
help
Support for the camera clock controller on Qualcomm Technologies, Inc
Tuna devices.
Say Y if you want to support camera devices and functionality such as
capturing pictures.
config SM_CAMBISTMCLKCC_TUNA
tristate "TUNA CAMBISTMCLK Clock Controller"
depends on SM_GCC_TUNA
help
Support for the CAMBISTMCLK clock controller on Qualcomm Technologies,
Inc Tuna devices.
Say Y if you want to support camera devices for a better low-latency
clock.
config SM_DISPCC_TUNA
tristate "TUNA Display Clock Controller"
depends on SM_GCC_TUNA
help
Support for the display clock controller on Qualcomm Technologies, Inc
Tuna devices.
Say Y if you want to support display devices and functionality such as
splash screen.
endif endif

View File

@@ -2,8 +2,10 @@
obj-$(CONFIG_COMMON_CLK_QCOM) += clk-qcom.o obj-$(CONFIG_COMMON_CLK_QCOM) += clk-qcom.o
clk-qcom-y += common.o clk-qcom-y += common.o
clk-qcom-y += vdd-class.o
clk-qcom-y += clk-regmap.o clk-qcom-y += clk-regmap.o
clk-qcom-y += clk-alpha-pll.o clk-qcom-y += clk-alpha-pll.o
clk-qcom-y += clk-opp.o
clk-qcom-y += clk-pll.o clk-qcom-y += clk-pll.o
clk-qcom-y += clk-rcg.o clk-qcom-y += clk-rcg.o
clk-qcom-y += clk-rcg2.o clk-qcom-y += clk-rcg2.o
@@ -15,7 +17,12 @@ clk-qcom-y += clk-regmap-phy-mux.o
clk-qcom-$(CONFIG_KRAIT_CLOCKS) += clk-krait.o clk-qcom-$(CONFIG_KRAIT_CLOCKS) += clk-krait.o
clk-qcom-y += clk-hfpll.o clk-qcom-y += clk-hfpll.o
clk-qcom-y += reset.o clk-qcom-y += reset.o
clk-qcom-y += clk-pm.o
clk-qcom-y += clk-debug.o
clk-qcom-$(CONFIG_QCOM_GDSC) += gdsc.o clk-qcom-$(CONFIG_QCOM_GDSC) += gdsc.o
obj-$(CONFIG_COMMON_CLK_QCOM) += clk-dummy.o
obj-$(CONFIG_QCOM_GDSC_REGULATOR) += gdsc-regulator.o
# Keep alphabetically sorted by config # Keep alphabetically sorted by config
obj-$(CONFIG_APQ_GCC_8084) += gcc-apq8084.o obj-$(CONFIG_APQ_GCC_8084) += gcc-apq8084.o
@@ -96,12 +103,21 @@ obj-$(CONFIG_SDM_GCC_845) += gcc-sdm845.o
obj-$(CONFIG_SDM_GPUCC_845) += gpucc-sdm845.o obj-$(CONFIG_SDM_GPUCC_845) += gpucc-sdm845.o
obj-$(CONFIG_SDM_LPASSCC_845) += lpasscc-sdm845.o obj-$(CONFIG_SDM_LPASSCC_845) += lpasscc-sdm845.o
obj-$(CONFIG_SDM_VIDEOCC_845) += videocc-sdm845.o obj-$(CONFIG_SDM_VIDEOCC_845) += videocc-sdm845.o
obj-$(CONFIG_SDW_DEBUGCC_MONACO) += debugcc-monaco.o
obj-$(CONFIG_SDW_DISPCC_MONACO) += dispcc-monaco.o
obj-$(CONFIG_SDW_GCC_MONACO) += gcc-monaco.o
obj-$(CONFIG_SDW_GPUCC_MONACO) += gpucc-monaco.o
obj-$(CONFIG_SDX_GCC_55) += gcc-sdx55.o obj-$(CONFIG_SDX_GCC_55) += gcc-sdx55.o
obj-$(CONFIG_SDX_GCC_65) += gcc-sdx65.o obj-$(CONFIG_SDX_GCC_65) += gcc-sdx65.o
obj-$(CONFIG_SDX_DEBUGCC_75) += debugcc-sdx75.o
obj-$(CONFIG_SDX_GCC_75) += gcc-sdx75.o obj-$(CONFIG_SDX_GCC_75) += gcc-sdx75.o
obj-$(CONFIG_SM_CAMCC_4450) += camcc-sm4450.o
obj-$(CONFIG_SM_CAMCC_6350) += camcc-sm6350.o obj-$(CONFIG_SM_CAMCC_6350) += camcc-sm6350.o
obj-$(CONFIG_SM_CAMCC_8250) += camcc-sm8250.o obj-$(CONFIG_SM_CAMCC_8250) += camcc-sm8250.o
obj-$(CONFIG_SM_CAMCC_8450) += camcc-sm8450.o obj-$(CONFIG_SM_CAMCC_8450) += camcc-sm8450.o
obj-$(CONFIG_SM_DEBUGCC_4450) += debugcc-sm4450.o
obj-$(CONFIG_SM_DEBUGCC_PARROT) += debugcc-parrot.o
obj-$(CONFIG_SM_DISPCC_4450) += dispcc-sm4450.o
obj-$(CONFIG_SM_DISPCC_6115) += dispcc-sm6115.o obj-$(CONFIG_SM_DISPCC_6115) += dispcc-sm6115.o
obj-$(CONFIG_SM_DISPCC_6125) += dispcc-sm6125.o obj-$(CONFIG_SM_DISPCC_6125) += dispcc-sm6125.o
obj-$(CONFIG_SM_DISPCC_6350) += dispcc-sm6350.o obj-$(CONFIG_SM_DISPCC_6350) += dispcc-sm6350.o
@@ -109,6 +125,10 @@ obj-$(CONFIG_SM_DISPCC_6375) += dispcc-sm6375.o
obj-$(CONFIG_SM_DISPCC_8250) += dispcc-sm8250.o obj-$(CONFIG_SM_DISPCC_8250) += dispcc-sm8250.o
obj-$(CONFIG_SM_DISPCC_8450) += dispcc-sm8450.o obj-$(CONFIG_SM_DISPCC_8450) += dispcc-sm8450.o
obj-$(CONFIG_SM_DISPCC_8550) += dispcc-sm8550.o obj-$(CONFIG_SM_DISPCC_8550) += dispcc-sm8550.o
obj-$(CONFIG_SM_DISPCC_PARROT) += dispcc-parrot.o
obj-$(CONFIG_SM_DISPCC_TUNA) += dispcc-tuna.o
obj-$(CONFIG_SM_EVACC_TUNA) += evacc-tuna.o
obj-$(CONFIG_SM_GCC_4450) += gcc-sm4450.o
obj-$(CONFIG_SM_GCC_6115) += gcc-sm6115.o obj-$(CONFIG_SM_GCC_6115) += gcc-sm6115.o
obj-$(CONFIG_SM_GCC_6125) += gcc-sm6125.o obj-$(CONFIG_SM_GCC_6125) += gcc-sm6125.o
obj-$(CONFIG_SM_GCC_6350) += gcc-sm6350.o obj-$(CONFIG_SM_GCC_6350) += gcc-sm6350.o
@@ -118,7 +138,31 @@ obj-$(CONFIG_SM_GCC_8150) += gcc-sm8150.o
obj-$(CONFIG_SM_GCC_8250) += gcc-sm8250.o obj-$(CONFIG_SM_GCC_8250) += gcc-sm8250.o
obj-$(CONFIG_SM_GCC_8350) += gcc-sm8350.o obj-$(CONFIG_SM_GCC_8350) += gcc-sm8350.o
obj-$(CONFIG_SM_GCC_8450) += gcc-sm8450.o obj-$(CONFIG_SM_GCC_8450) += gcc-sm8450.o
obj-$(CONFIG_SM_GCC_SUN) += gcc-sun.o
obj-$(CONFIG_SM_GCC_8550) += gcc-sm8550.o obj-$(CONFIG_SM_GCC_8550) += gcc-sm8550.o
obj-$(CONFIG_SM_GCC_KERA) += gcc-kera.o
obj-$(CONFIG_SM_GCC_PARROT) += gcc-parrot.o
obj-$(CONFIG_SM_GCC_PINEAPPLE) += gcc-pineapple.o
obj-$(CONFIG_SM_GCC_TUNA) += gcc-tuna.o
obj-$(CONFIG_SM_GPUCC_TUNA) += gpucc-tuna.o
obj-$(CONFIG_SM_VIDEOCC_PINEAPPLE) += videocc-pineapple.o
obj-$(CONFIG_SM_CAMBISTMCLKCC_TUNA) += cambistmclkcc-tuna.o
obj-$(CONFIG_SM_CAMCC_PARROT) += camcc-parrot.o
obj-$(CONFIG_SM_CAMCC_PINEAPPLE) += camcc-pineapple.o
obj-$(CONFIG_SM_CAMCC_TUNA) += camcc-tuna.o
obj-$(CONFIG_SM_DISPCC_PINEAPPLE) += dispcc-pineapple.o
obj-$(CONFIG_SM_DEBUGCC_PINEAPPLE) += debugcc-pineapple.o
obj-$(CONFIG_SM_GPUCC_PINEAPPLE) += gpucc-pineapple.o
obj-$(CONFIG_SM_TCSRCC_PINEAPPLE) += tcsrcc-pineapple.o
obj-$(CONFIG_SM_TCSRCC_TUNA) += tcsrcc-tuna.o
obj-$(CONFIG_SM_CAMCC_SUN) += camcc-sun.o
obj-$(CONFIG_SM_EVACC_SUN) += evacc-sun.o
obj-$(CONFIG_SM_GPUCC_SUN) += gpucc-sun.o
obj-$(CONFIG_SM_DISPCC_SUN) += dispcc-sun.o
obj-$(CONFIG_SM_CAMBISTMCLKCC_SUN) += cambistmclkcc-sun.o
obj-$(CONFIG_SM_TCSRCC_SUN) += tcsrcc-sun.o
obj-$(CONFIG_SM_DEBUGCC_SUN) += debugcc-sun.o
obj-$(CONFIG_SM_GPUCC_4450) += gpucc-sm4450.o
obj-$(CONFIG_SM_GPUCC_6115) += gpucc-sm6115.o obj-$(CONFIG_SM_GPUCC_6115) += gpucc-sm6115.o
obj-$(CONFIG_SM_GPUCC_6125) += gpucc-sm6125.o obj-$(CONFIG_SM_GPUCC_6125) += gpucc-sm6125.o
obj-$(CONFIG_SM_GPUCC_6350) += gpucc-sm6350.o obj-$(CONFIG_SM_GPUCC_6350) += gpucc-sm6350.o
@@ -128,12 +172,16 @@ obj-$(CONFIG_SM_GPUCC_8250) += gpucc-sm8250.o
obj-$(CONFIG_SM_GPUCC_8350) += gpucc-sm8350.o obj-$(CONFIG_SM_GPUCC_8350) += gpucc-sm8350.o
obj-$(CONFIG_SM_GPUCC_8450) += gpucc-sm8450.o obj-$(CONFIG_SM_GPUCC_8450) += gpucc-sm8450.o
obj-$(CONFIG_SM_GPUCC_8550) += gpucc-sm8550.o obj-$(CONFIG_SM_GPUCC_8550) += gpucc-sm8550.o
obj-$(CONFIG_SM_GPUCC_PARROT) += gpucc-parrot.o
obj-$(CONFIG_SM_TCSRCC_8550) += tcsrcc-sm8550.o obj-$(CONFIG_SM_TCSRCC_8550) += tcsrcc-sm8550.o
obj-$(CONFIG_SM_VIDEOCC_8150) += videocc-sm8150.o obj-$(CONFIG_SM_VIDEOCC_8150) += videocc-sm8150.o
obj-$(CONFIG_SM_VIDEOCC_8250) += videocc-sm8250.o obj-$(CONFIG_SM_VIDEOCC_8250) += videocc-sm8250.o
obj-$(CONFIG_SM_VIDEOCC_8350) += videocc-sm8350.o obj-$(CONFIG_SM_VIDEOCC_8350) += videocc-sm8350.o
obj-$(CONFIG_SM_VIDEOCC_8450) += videocc-sm8450.o obj-$(CONFIG_SM_VIDEOCC_8450) += videocc-sm8450.o
obj-$(CONFIG_SM_VIDEOCC_8550) += videocc-sm8550.o obj-$(CONFIG_SM_VIDEOCC_8550) += videocc-sm8550.o
obj-$(CONFIG_SM_VIDEOCC_PARROT) += videocc-parrot.o
obj-$(CONFIG_SM_VIDEOCC_SUN) += videocc-sun.o
obj-$(CONFIG_SM_VIDEOCC_TUNA) += videocc-tuna.o
obj-$(CONFIG_SPMI_PMIC_CLKDIV) += clk-spmi-pmic-div.o obj-$(CONFIG_SPMI_PMIC_CLKDIV) += clk-spmi-pmic-div.o
obj-$(CONFIG_KPSS_XCC) += kpss-xcc.o obj-$(CONFIG_KPSS_XCC) += kpss-xcc.o
obj-$(CONFIG_QCOM_HFPLL) += hfpll.o obj-$(CONFIG_QCOM_HFPLL) += hfpll.o

0
drivers/clk/qcom/cambistmclkcc-sun.c Executable file → Normal file
View File

0
drivers/clk/qcom/cambistmclkcc-tuna.c Executable file → Normal file
View File

0
drivers/clk/qcom/camcc-parrot.c Executable file → Normal file
View File

0
drivers/clk/qcom/camcc-pineapple.c Executable file → Normal file
View File

View File

@@ -2260,7 +2260,6 @@ static struct gdsc cam_cc_bps_gdsc = {
.name = "cam_cc_bps_gdsc", .name = "cam_cc_bps_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.parent = &cam_cc_titan_top_gdsc.pd,
.flags = HW_CTRL | RETAIN_FF_ENABLE, .flags = HW_CTRL | RETAIN_FF_ENABLE,
}; };
@@ -2270,7 +2269,6 @@ static struct gdsc cam_cc_ife_0_gdsc = {
.name = "cam_cc_ife_0_gdsc", .name = "cam_cc_ife_0_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.parent = &cam_cc_titan_top_gdsc.pd,
.flags = RETAIN_FF_ENABLE, .flags = RETAIN_FF_ENABLE,
}; };
@@ -2280,7 +2278,6 @@ static struct gdsc cam_cc_ife_1_gdsc = {
.name = "cam_cc_ife_1_gdsc", .name = "cam_cc_ife_1_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.parent = &cam_cc_titan_top_gdsc.pd,
.flags = RETAIN_FF_ENABLE, .flags = RETAIN_FF_ENABLE,
}; };
@@ -2290,7 +2287,6 @@ static struct gdsc cam_cc_ife_2_gdsc = {
.name = "cam_cc_ife_2_gdsc", .name = "cam_cc_ife_2_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.parent = &cam_cc_titan_top_gdsc.pd,
.flags = RETAIN_FF_ENABLE, .flags = RETAIN_FF_ENABLE,
}; };
@@ -2300,7 +2296,6 @@ static struct gdsc cam_cc_ipe_0_gdsc = {
.name = "cam_cc_ipe_0_gdsc", .name = "cam_cc_ipe_0_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.parent = &cam_cc_titan_top_gdsc.pd,
.flags = HW_CTRL | RETAIN_FF_ENABLE, .flags = HW_CTRL | RETAIN_FF_ENABLE,
}; };

0
drivers/clk/qcom/camcc-sm4450.c Executable file → Normal file
View File

View File

@@ -1694,9 +1694,6 @@ static struct clk_branch camcc_sys_tmr_clk = {
static struct gdsc bps_gdsc = { static struct gdsc bps_gdsc = {
.gdscr = 0x6004, .gdscr = 0x6004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "bps_gdsc", .name = "bps_gdsc",
}, },
@@ -1706,9 +1703,6 @@ static struct gdsc bps_gdsc = {
static struct gdsc ipe_0_gdsc = { static struct gdsc ipe_0_gdsc = {
.gdscr = 0x7004, .gdscr = 0x7004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "ipe_0_gdsc", .name = "ipe_0_gdsc",
}, },
@@ -1718,9 +1712,6 @@ static struct gdsc ipe_0_gdsc = {
static struct gdsc ife_0_gdsc = { static struct gdsc ife_0_gdsc = {
.gdscr = 0x9004, .gdscr = 0x9004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "ife_0_gdsc", .name = "ife_0_gdsc",
}, },
@@ -1729,9 +1720,6 @@ static struct gdsc ife_0_gdsc = {
static struct gdsc ife_1_gdsc = { static struct gdsc ife_1_gdsc = {
.gdscr = 0xa004, .gdscr = 0xa004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "ife_1_gdsc", .name = "ife_1_gdsc",
}, },
@@ -1740,9 +1728,6 @@ static struct gdsc ife_1_gdsc = {
static struct gdsc ife_2_gdsc = { static struct gdsc ife_2_gdsc = {
.gdscr = 0xb004, .gdscr = 0xb004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "ife_2_gdsc", .name = "ife_2_gdsc",
}, },
@@ -1751,9 +1736,6 @@ static struct gdsc ife_2_gdsc = {
static struct gdsc titan_top_gdsc = { static struct gdsc titan_top_gdsc = {
.gdscr = 0x14004, .gdscr = 0x14004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "titan_top_gdsc", .name = "titan_top_gdsc",
}, },

View File

@@ -411,7 +411,7 @@ static struct clk_rcg2 cam_cc_bps_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -433,7 +433,7 @@ static struct clk_rcg2 cam_cc_camnoc_axi_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -454,7 +454,7 @@ static struct clk_rcg2 cam_cc_cci_0_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -469,7 +469,7 @@ static struct clk_rcg2 cam_cc_cci_1_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -490,7 +490,7 @@ static struct clk_rcg2 cam_cc_cphy_rx_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -511,7 +511,7 @@ static struct clk_rcg2 cam_cc_csi0phytimer_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -526,7 +526,7 @@ static struct clk_rcg2 cam_cc_csi1phytimer_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -556,7 +556,7 @@ static struct clk_rcg2 cam_cc_csi3phytimer_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -571,7 +571,7 @@ static struct clk_rcg2 cam_cc_csi4phytimer_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -586,7 +586,7 @@ static struct clk_rcg2 cam_cc_csi5phytimer_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -611,7 +611,7 @@ static struct clk_rcg2 cam_cc_fast_ahb_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -634,7 +634,7 @@ static struct clk_rcg2 cam_cc_fd_core_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -649,7 +649,7 @@ static struct clk_rcg2 cam_cc_icp_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -673,7 +673,7 @@ static struct clk_rcg2 cam_cc_ife_0_clk_src = {
.parent_data = cam_cc_parent_data_2, .parent_data = cam_cc_parent_data_2,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_2), .num_parents = ARRAY_SIZE(cam_cc_parent_data_2),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -710,7 +710,7 @@ static struct clk_rcg2 cam_cc_ife_0_csid_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -734,7 +734,7 @@ static struct clk_rcg2 cam_cc_ife_1_clk_src = {
.parent_data = cam_cc_parent_data_3, .parent_data = cam_cc_parent_data_3,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_3), .num_parents = ARRAY_SIZE(cam_cc_parent_data_3),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -749,7 +749,7 @@ static struct clk_rcg2 cam_cc_ife_1_csid_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -771,7 +771,7 @@ static struct clk_rcg2 cam_cc_ife_lite_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -786,7 +786,7 @@ static struct clk_rcg2 cam_cc_ife_lite_csid_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -810,7 +810,7 @@ static struct clk_rcg2 cam_cc_ipe_0_clk_src = {
.parent_data = cam_cc_parent_data_4, .parent_data = cam_cc_parent_data_4,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_4), .num_parents = ARRAY_SIZE(cam_cc_parent_data_4),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -825,7 +825,7 @@ static struct clk_rcg2 cam_cc_jpeg_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -847,7 +847,7 @@ static struct clk_rcg2 cam_cc_mclk0_clk_src = {
.parent_data = cam_cc_parent_data_1, .parent_data = cam_cc_parent_data_1,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_1), .num_parents = ARRAY_SIZE(cam_cc_parent_data_1),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -862,7 +862,7 @@ static struct clk_rcg2 cam_cc_mclk1_clk_src = {
.parent_data = cam_cc_parent_data_1, .parent_data = cam_cc_parent_data_1,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_1), .num_parents = ARRAY_SIZE(cam_cc_parent_data_1),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -877,7 +877,7 @@ static struct clk_rcg2 cam_cc_mclk2_clk_src = {
.parent_data = cam_cc_parent_data_1, .parent_data = cam_cc_parent_data_1,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_1), .num_parents = ARRAY_SIZE(cam_cc_parent_data_1),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -892,7 +892,7 @@ static struct clk_rcg2 cam_cc_mclk3_clk_src = {
.parent_data = cam_cc_parent_data_1, .parent_data = cam_cc_parent_data_1,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_1), .num_parents = ARRAY_SIZE(cam_cc_parent_data_1),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -907,7 +907,7 @@ static struct clk_rcg2 cam_cc_mclk4_clk_src = {
.parent_data = cam_cc_parent_data_1, .parent_data = cam_cc_parent_data_1,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_1), .num_parents = ARRAY_SIZE(cam_cc_parent_data_1),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -922,7 +922,7 @@ static struct clk_rcg2 cam_cc_mclk5_clk_src = {
.parent_data = cam_cc_parent_data_1, .parent_data = cam_cc_parent_data_1,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_1), .num_parents = ARRAY_SIZE(cam_cc_parent_data_1),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -993,7 +993,7 @@ static struct clk_rcg2 cam_cc_slow_ahb_clk_src = {
.parent_data = cam_cc_parent_data_0, .parent_data = cam_cc_parent_data_0,
.num_parents = ARRAY_SIZE(cam_cc_parent_data_0), .num_parents = ARRAY_SIZE(cam_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };

0
drivers/clk/qcom/camcc-sun.c Executable file → Normal file
View File

0
drivers/clk/qcom/camcc-tuna.c Executable file → Normal file
View File

File diff suppressed because it is too large Load Diff

View File

@@ -1,7 +1,7 @@
/* SPDX-License-Identifier: GPL-2.0 */ /* SPDX-License-Identifier: GPL-2.0 */
/* /*
* Copyright (c) 2015, 2018, 2021 The Linux Foundation. All rights reserved. * Copyright (c) 2015, 2018, 2021 The Linux Foundation. All rights reserved.
* Copyright (c) 2023 Qualcomm Innovation Center, Inc. All rights reserved. * Copyright (c) 2022-2024, Qualcomm Innovation Center, Inc. All rights reserved.
*/ */
@@ -21,19 +21,24 @@ enum {
CLK_ALPHA_PLL_TYPE_LUCID = CLK_ALPHA_PLL_TYPE_TRION, CLK_ALPHA_PLL_TYPE_LUCID = CLK_ALPHA_PLL_TYPE_TRION,
CLK_ALPHA_PLL_TYPE_AGERA, CLK_ALPHA_PLL_TYPE_AGERA,
CLK_ALPHA_PLL_TYPE_ZONDA, CLK_ALPHA_PLL_TYPE_ZONDA,
CLK_ALPHA_PLL_TYPE_ZONDA_OLE, CLK_ALPHA_PLL_TYPE_ZONDA_EVO,
CLK_ALPHA_PLL_TYPE_LUCID_EVO, CLK_ALPHA_PLL_TYPE_LUCID_EVO,
CLK_ALPHA_PLL_TYPE_LUCID_OLE, CLK_ALPHA_PLL_TYPE_LUCID_OLE,
CLK_ALPHA_PLL_TYPE_TAYCAN_ELU,
CLK_ALPHA_PLL_TYPE_PONGO_ELU,
CLK_ALPHA_PLL_TYPE_PONGO_OLE = CLK_ALPHA_PLL_TYPE_PONGO_ELU,
CLK_ALPHA_PLL_TYPE_RIVIAN_EVO, CLK_ALPHA_PLL_TYPE_RIVIAN_EVO,
CLK_ALPHA_PLL_TYPE_RIVIAN_OLE = CLK_ALPHA_PLL_TYPE_RIVIAN_EVO,
CLK_ALPHA_PLL_TYPE_RIVIAN_ELU,
CLK_ALPHA_PLL_TYPE_DEFAULT_EVO, CLK_ALPHA_PLL_TYPE_DEFAULT_EVO,
CLK_ALPHA_PLL_TYPE_BRAMMO_EVO, CLK_ALPHA_PLL_TYPE_BRAMMO_EVO,
CLK_ALPHA_PLL_TYPE_STROMER, CLK_ALPHA_PLL_TYPE_STROMER,
CLK_ALPHA_PLL_TYPE_STROMER_PLUS, CLK_ALPHA_PLL_TYPE_STROMER_PLUS,
CLK_ALPHA_PLL_TYPE_NSS_HUAYRA,
CLK_ALPHA_PLL_TYPE_MAX, CLK_ALPHA_PLL_TYPE_MAX,
}; };
enum { enum {
PLL_OFF_MODE,
PLL_OFF_L_VAL, PLL_OFF_L_VAL,
PLL_OFF_CAL_L_VAL, PLL_OFF_CAL_L_VAL,
PLL_OFF_ALPHA_VAL, PLL_OFF_ALPHA_VAL,
@@ -49,11 +54,15 @@ enum {
PLL_OFF_TEST_CTL_U, PLL_OFF_TEST_CTL_U,
PLL_OFF_TEST_CTL_U1, PLL_OFF_TEST_CTL_U1,
PLL_OFF_TEST_CTL_U2, PLL_OFF_TEST_CTL_U2,
PLL_OFF_TEST_CTL_U3,
PLL_OFF_STATE, PLL_OFF_STATE,
PLL_OFF_STATUS, PLL_OFF_STATUS,
PLL_OFF_OPMODE, PLL_OFF_OPMODE,
PLL_OFF_FRAC, PLL_OFF_FRAC,
PLL_OFF_CAL_VAL, PLL_OFF_CAL_VAL,
PLL_OFF_SSC_DELTA_ALPHA,
PLL_OFF_SSC_NUM_STEPS,
PLL_OFF_SSC_UPDATE_RATE,
PLL_OFF_MAX_REGS PLL_OFF_MAX_REGS
}; };
@@ -81,13 +90,15 @@ struct pll_vco {
struct clk_alpha_pll { struct clk_alpha_pll {
u32 offset; u32 offset;
const u8 *regs; const u8 *regs;
struct alpha_pll_config *config;
const struct pll_vco *vco_table; const struct pll_vco *vco_table;
size_t num_vco; size_t num_vco;
#define SUPPORTS_OFFLINE_REQ BIT(0) #define SUPPORTS_OFFLINE_REQ BIT(0)
#define SUPPORTS_FSM_MODE BIT(2) #define SUPPORTS_FSM_MODE BIT(2)
#define SUPPORTS_DYNAMIC_UPDATE BIT(3) #define SUPPORTS_DYNAMIC_UPDATE BIT(3)
#define SUPPORTS_FSM_LEGACY_MODE BIT(4) #define SUPPORTS_FSM_LEGACY_MODE BIT(4)
#define DISABLE_TO_OFF BIT(5)
#define ENABLE_IN_PREPARE BIT(6)
u8 flags; u8 flags;
struct clk_regmap clkr; struct clk_regmap clkr;
@@ -117,6 +128,8 @@ struct clk_alpha_pll_postdiv {
struct alpha_pll_config { struct alpha_pll_config {
u32 l; u32 l;
u32 cal_l;
u32 cal_l_ringosc;
u32 alpha; u32 alpha;
u32 alpha_hi; u32 alpha_hi;
u32 config_ctl_val; u32 config_ctl_val;
@@ -132,6 +145,7 @@ struct alpha_pll_config {
u32 test_ctl_hi_mask; u32 test_ctl_hi_mask;
u32 test_ctl_hi1_val; u32 test_ctl_hi1_val;
u32 test_ctl_hi2_val; u32 test_ctl_hi2_val;
u32 test_ctl_hi3_val;
u32 main_output_mask; u32 main_output_mask;
u32 aux_output_mask; u32 aux_output_mask;
u32 aux2_output_mask; u32 aux2_output_mask;
@@ -177,7 +191,6 @@ extern const struct clk_ops clk_alpha_pll_postdiv_lucid_5lpe_ops;
extern const struct clk_ops clk_alpha_pll_zonda_ops; extern const struct clk_ops clk_alpha_pll_zonda_ops;
#define clk_alpha_pll_postdiv_zonda_ops clk_alpha_pll_postdiv_fabia_ops #define clk_alpha_pll_postdiv_zonda_ops clk_alpha_pll_postdiv_fabia_ops
#define clk_alpha_pll_zonda_ole_ops clk_alpha_pll_zonda_ops
extern const struct clk_ops clk_alpha_pll_lucid_evo_ops; extern const struct clk_ops clk_alpha_pll_lucid_evo_ops;
extern const struct clk_ops clk_alpha_pll_reset_lucid_evo_ops; extern const struct clk_ops clk_alpha_pll_reset_lucid_evo_ops;
@@ -186,10 +199,37 @@ extern const struct clk_ops clk_alpha_pll_fixed_lucid_evo_ops;
#define clk_alpha_pll_fixed_lucid_ole_ops clk_alpha_pll_fixed_lucid_evo_ops #define clk_alpha_pll_fixed_lucid_ole_ops clk_alpha_pll_fixed_lucid_evo_ops
extern const struct clk_ops clk_alpha_pll_postdiv_lucid_evo_ops; extern const struct clk_ops clk_alpha_pll_postdiv_lucid_evo_ops;
#define clk_alpha_pll_postdiv_lucid_ole_ops clk_alpha_pll_postdiv_lucid_evo_ops #define clk_alpha_pll_postdiv_lucid_ole_ops clk_alpha_pll_postdiv_lucid_evo_ops
extern const struct clk_ops clk_alpha_pll_fixed_zonda_evo_ops;
extern const struct clk_ops clk_alpha_pll_postdiv_zonda_evo_ops;
#define clk_alpha_pll_lucid_ole_ops clk_alpha_pll_lucid_evo_ops
#define clk_alpha_pll_taycan_elu_ops clk_alpha_pll_lucid_evo_ops
#define clk_alpha_pll_fixed_taycan_elu_ops clk_alpha_pll_fixed_lucid_evo_ops
#define clk_alpha_pll_postdiv_taycan_elu_ops clk_alpha_pll_postdiv_lucid_evo_ops
extern const struct clk_ops clk_alpha_pll_crm_lucid_evo_ops;
extern const struct clk_ops clk_alpha_pll_crm_fixed_lucid_evo_ops;
extern const struct clk_ops clk_alpha_pll_crm_postdiv_lucid_evo_ops;
#define clk_alpha_pll_crm_lucid_ole_ops clk_alpha_pll_crm_lucid_evo_ops
#define clk_alpha_pll_crm_fixed_lucid_ole_ops clk_alpha_pll_crm_fixed_lucid_evo_ops
#define clk_alpha_pll_crm_postdiv_lucid_ole_ops clk_alpha_pll_crm_postdiv_lucid_evo_ops
#define clk_alpha_pll_crm_taycan_elu_ops clk_alpha_pll_crm_lucid_evo_ops
#define clk_alpha_pll_crm_fixed_taycan_elu_ops clk_alpha_pll_crm_fixed_lucid_evo_ops
#define clk_alpha_pll_crm_postdiv_taycan_elu_ops clk_alpha_pll_crm_postdiv_lucid_evo_ops
extern const struct clk_ops clk_alpha_pll_rivian_evo_ops; extern const struct clk_ops clk_alpha_pll_rivian_evo_ops;
#define clk_alpha_pll_postdiv_rivian_evo_ops clk_alpha_pll_postdiv_fabia_ops #define clk_alpha_pll_postdiv_rivian_evo_ops clk_alpha_pll_postdiv_fabia_ops
#define clk_alpha_pll_rivian_ole_ops clk_alpha_pll_rivian_evo_ops
#define clk_alpha_pll_rivian_elu_ops clk_alpha_pll_rivian_evo_ops
extern const struct clk_ops clk_alpha_pll_pongo_elu_ops;
#define clk_alpha_pll_pongo_ole_ops clk_alpha_pll_pongo_elu_ops
void clk_pongo_elu_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap,
const struct alpha_pll_config *config);
void clk_alpha_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap, void clk_alpha_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap,
const struct alpha_pll_config *config); const struct alpha_pll_config *config);
void clk_fabia_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap, void clk_fabia_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap,
@@ -200,16 +240,24 @@ void clk_agera_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap,
const struct alpha_pll_config *config); const struct alpha_pll_config *config);
#define clk_lucid_pll_configure(pll, regmap, config) \ #define clk_lucid_pll_configure(pll, regmap, config) \
clk_trion_pll_configure(pll, regmap, config) clk_trion_pll_configure(pll, regmap, config)
#define clk_pongo_ole_pll_configure(pll, regmap, config) \
clk_pongo_elu_pll_configure(pll, regmap, config)
void clk_zonda_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap, void clk_zonda_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap,
const struct alpha_pll_config *config); const struct alpha_pll_config *config);
void clk_lucid_5lpe_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap,
const struct alpha_pll_config *config);
void clk_lucid_evo_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap, void clk_lucid_evo_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap,
const struct alpha_pll_config *config); const struct alpha_pll_config *config);
#define clk_lucid_ole_pll_configure(pll, regmap, config) \
clk_lucid_evo_pll_configure(pll, regmap, config)
#define clk_taycan_elu_pll_configure(pll, regmap, config) \
clk_lucid_evo_pll_configure(pll, regmap, config)
void clk_rivian_evo_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap, void clk_rivian_evo_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap,
const struct alpha_pll_config *config); const struct alpha_pll_config *config);
#define clk_rivian_ole_pll_configure clk_rivian_evo_pll_configure
#define clk_rivian_elu_pll_configure clk_rivian_evo_pll_configure
void clk_stromer_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap, void clk_stromer_pll_configure(struct clk_alpha_pll *pll, struct regmap *regmap,
const struct alpha_pll_config *config); const struct alpha_pll_config *config);
int clk_zonda_evo_pll_configure(struct clk_alpha_pll *pll,
struct regmap *regmap,
const struct alpha_pll_config *config);
#endif #endif

View File

@@ -1,6 +1,7 @@
// SPDX-License-Identifier: GPL-2.0 // SPDX-License-Identifier: GPL-2.0-only
/* /*
* Copyright (c) 2013, The Linux Foundation. All rights reserved. * Copyright (c) 2013, 2016, 2020-2021, The Linux Foundation. All rights reserved.
* Copyright (c) 2023-2024, Qualcomm Innovation Center, Inc. All rights reserved.
*/ */
#include <linux/kernel.h> #include <linux/kernel.h>
@@ -8,10 +9,14 @@
#include <linux/err.h> #include <linux/err.h>
#include <linux/delay.h> #include <linux/delay.h>
#include <linux/export.h> #include <linux/export.h>
#include <linux/clk.h>
#include <linux/clk-provider.h> #include <linux/clk-provider.h>
#include <linux/regmap.h> #include <linux/regmap.h>
#include <linux/clk/qcom.h>
#include "clk-branch.h" #include "clk-branch.h"
#include "clk-debug.h"
#include "clk-regmap.h"
static bool clk_branch_in_hwcg_mode(const struct clk_branch *br) static bool clk_branch_in_hwcg_mode(const struct clk_branch *br)
{ {
@@ -27,7 +32,7 @@ static bool clk_branch_in_hwcg_mode(const struct clk_branch *br)
static bool clk_branch_check_halt(const struct clk_branch *br, bool enabling) static bool clk_branch_check_halt(const struct clk_branch *br, bool enabling)
{ {
bool invert = (br->halt_check & BRANCH_HALT_ENABLE); bool invert = (br->halt_check == BRANCH_HALT_ENABLE);
u32 val; u32 val;
regmap_read(br->clkr.regmap, br->halt_reg, &val); regmap_read(br->clkr.regmap, br->halt_reg, &val);
@@ -39,11 +44,13 @@ static bool clk_branch_check_halt(const struct clk_branch *br, bool enabling)
return !!val == !enabling; return !!val == !enabling;
} }
#define BRANCH_CLK_DIS_MASK BIT(22)
static bool clk_branch2_check_halt(const struct clk_branch *br, bool enabling) static bool clk_branch2_check_halt(const struct clk_branch *br, bool enabling)
{ {
u32 val; u32 val;
u32 mask; u32 mask;
bool invert = (br->halt_check & BRANCH_HALT_ENABLE); bool invert = (br->halt_check == BRANCH_HALT_ENABLE);
mask = CBCR_NOC_FSM_STATUS; mask = CBCR_NOC_FSM_STATUS;
mask |= CBCR_CLK_OFF; mask |= CBCR_CLK_OFF;
@@ -52,18 +59,36 @@ static bool clk_branch2_check_halt(const struct clk_branch *br, bool enabling)
if (enabling) { if (enabling) {
val &= mask; val &= mask;
if (br->halt_check == BRANCH_HALT_INVERT)
return (val & CBCR_CLK_OFF) == CBCR_CLK_OFF;
return (val & CBCR_CLK_OFF) == (invert ? CBCR_CLK_OFF : 0) || return (val & CBCR_CLK_OFF) == (invert ? CBCR_CLK_OFF : 0) ||
FIELD_GET(CBCR_NOC_FSM_STATUS, val) == FSM_STATUS_ON; FIELD_GET(CBCR_NOC_FSM_STATUS, val) == FSM_STATUS_ON;
} }
return (val & CBCR_CLK_OFF) == (invert ? 0 : CBCR_CLK_OFF); return (val & CBCR_CLK_OFF) == (invert ? 0 : CBCR_CLK_OFF);
} }
static int get_branch_timeout(const struct clk_branch *br)
{
int rate, period_us, timeout;
/*
* The time it takes a clock branch to toggle is roughly 3 clock cycles.
*/
rate = clk_hw_get_rate(&br->clkr.hw);
period_us = 1000000 / rate;
timeout = 3 * period_us;
return max(timeout, 200);
}
static int clk_branch_wait(const struct clk_branch *br, bool enabling, static int clk_branch_wait(const struct clk_branch *br, bool enabling,
bool (check_halt)(const struct clk_branch *, bool)) bool (check_halt)(const struct clk_branch *, bool))
{ {
bool voted = br->halt_check & BRANCH_VOTED; int timeout, count;
const char *name = clk_hw_get_name(&br->clkr.hw);
bool voted = br->halt_check & BRANCH_VOTED;
/* /*
* Skip checking halt bit if we're explicitly ignoring the bit or the * Skip checking halt bit if we're explicitly ignoring the bit or the
* clock is in hardware gated mode * clock is in hardware gated mode
@@ -76,15 +101,15 @@ static int clk_branch_wait(const struct clk_branch *br, bool enabling,
} else if (br->halt_check == BRANCH_HALT_ENABLE || } else if (br->halt_check == BRANCH_HALT_ENABLE ||
br->halt_check == BRANCH_HALT || br->halt_check == BRANCH_HALT ||
(enabling && voted)) { (enabling && voted)) {
int count = 200; timeout = get_branch_timeout(br);
while (count-- > 0) { for (count = timeout; count > 0; count--) {
if (check_halt(br, enabling)) if (check_halt(br, enabling))
return 0; return 0;
udelay(1); udelay(1);
} }
WARN(1, "%s status stuck at 'o%s'", name, WARN_CLK((struct clk_hw *)&br->clkr.hw, 1, "status stuck at 'o%s' after %d us",
enabling ? "ff" : "n"); enabling ? "ff" : "n", timeout);
return -EBUSY; return -EBUSY;
} }
return 0; return 0;
@@ -117,10 +142,17 @@ static void clk_branch_disable(struct clk_hw *hw)
clk_branch_toggle(hw, false, clk_branch_check_halt); clk_branch_toggle(hw, false, clk_branch_check_halt);
} }
static void clk_branch_debug_init(struct clk_hw *hw, struct dentry *dentry)
{
clk_common_debug_init(hw, dentry);
clk_debug_measure_add(hw, dentry);
}
const struct clk_ops clk_branch_ops = { const struct clk_ops clk_branch_ops = {
.enable = clk_branch_enable, .enable = clk_branch_enable,
.disable = clk_branch_disable, .disable = clk_branch_disable,
.is_enabled = clk_is_enabled_regmap, .is_enabled = clk_is_enabled_regmap,
.debug_init = clk_branch_debug_init,
}; };
EXPORT_SYMBOL_GPL(clk_branch_ops); EXPORT_SYMBOL_GPL(clk_branch_ops);
@@ -134,22 +166,329 @@ static void clk_branch2_disable(struct clk_hw *hw)
clk_branch_toggle(hw, false, clk_branch2_check_halt); clk_branch_toggle(hw, false, clk_branch2_check_halt);
} }
static int clk_branch2_mem_enable(struct clk_hw *hw)
{
struct clk_mem_branch *mem_br = to_clk_mem_branch(hw);
struct clk_branch branch = mem_br->branch;
u32 regval, mem_ctrl;
int ret;
mem_ctrl = mem_br->mem_enable_inverted ? 0 : mem_br->mem_enable_mask;
regmap_update_bits(branch.clkr.regmap, mem_br->mem_enable_reg,
mem_br->mem_enable_mask, mem_ctrl);
ret = regmap_read_poll_timeout(branch.clkr.regmap, mem_br->mem_ack_reg, regval,
(regval & mem_br->mem_enable_ack_mask), 0, 200);
if (ret) {
WARN(1, "%s mem enable failed ret=%d regval=0x%x\n",
clk_hw_get_name(&branch.clkr.hw), ret, regval);
return ret;
}
return clk_branch2_enable(hw);
}
static void clk_branch2_mem_disable(struct clk_hw *hw)
{
struct clk_mem_branch *mem_br = to_clk_mem_branch(hw);
struct clk_branch branch = mem_br->branch;
u32 regval, mem_ctrl;
int ret;
mem_ctrl = mem_br->mem_enable_inverted ? mem_br->mem_enable_mask : 0;
regmap_update_bits(branch.clkr.regmap, mem_br->mem_enable_reg,
mem_br->mem_enable_mask, mem_ctrl);
ret = regmap_read_poll_timeout(branch.clkr.regmap, mem_br->mem_ack_reg, regval,
!(regval & mem_br->mem_enable_ack_mask), 0, 200);
if (ret) {
WARN(1, "%s mem disable failed ret=%d regval=0x%x\n",
clk_hw_get_name(&branch.clkr.hw), ret, regval);
return;
}
clk_branch2_disable(hw);
}
static int clk_branch2_force_off_enable(struct clk_hw *hw)
{
struct clk_regmap *rclk = to_clk_regmap(hw);
regmap_update_bits(rclk->regmap, rclk->enable_reg,
BRANCH_CLK_DIS_MASK,
0x0);
return clk_branch2_enable(hw);
}
static void clk_branch2_force_off_disable(struct clk_hw *hw)
{
struct clk_regmap *rclk = to_clk_regmap(hw);
regmap_update_bits(rclk->regmap, rclk->enable_reg,
BRANCH_CLK_DIS_MASK,
BRANCH_CLK_DIS_MASK);
clk_branch2_disable(hw);
}
static void clk_branch2_list_registers(struct seq_file *f, struct clk_hw *hw)
{
struct clk_branch *br = to_clk_branch(hw);
struct clk_regmap *rclk = to_clk_regmap(hw);
int size, i, val;
static struct clk_register_data data[] = {
{"CBCR", 0x0},
};
static struct clk_register_data data1[] = {
{"APSS_VOTE", 0x0},
{"APSS_SLEEP_VOTE", 0x4},
};
size = ARRAY_SIZE(data);
for (i = 0; i < size; i++) {
regmap_read(br->clkr.regmap, br->halt_reg + data[i].offset,
&val);
clock_debug_output(f, "%20s: 0x%.8x\n", data[i].name, val);
}
if ((br->halt_check & BRANCH_HALT_VOTED) &&
!(br->halt_check & BRANCH_VOTED)) {
if (rclk->enable_reg) {
size = ARRAY_SIZE(data1);
for (i = 0; i < size; i++) {
regmap_read(br->clkr.regmap, rclk->enable_reg +
data1[i].offset, &val);
clock_debug_output(f, "%20s: 0x%.8x\n",
data1[i].name, val);
}
}
}
}
static void clk_branch2_mem_list_registers(struct seq_file *f, struct clk_hw *hw)
{
struct clk_mem_branch *mem_br = to_clk_mem_branch(hw);
struct clk_branch *br = &mem_br->branch;
u32 val;
static struct clk_register_data data[] = {
{"CBCR", 0x0},
{"MEM_ENABLE", 0x0},
{"MEM_ENABLE_ACK", 0x0},
{"MEM_ENABLE_ACK_MASK", 0x0},
};
regmap_read(br->clkr.regmap, br->halt_reg + data[0].offset,
&val);
clock_debug_output(f, "%20s: 0x%.8x\n", data[0].name, val);
if (mem_br->mem_enable_reg && mem_br->mem_ack_reg) {
regmap_read(mem_br->branch.clkr.regmap, mem_br->mem_enable_reg +
data[1].offset, &val);
clock_debug_output(f, "%20s: 0x%.8x\n", data[1].name, val);
regmap_read(mem_br->branch.clkr.regmap, mem_br->mem_ack_reg +
data[2].offset, &val);
clock_debug_output(f, "%20s: 0x%.8x\n", data[2].name, val);
clock_debug_output(f, "%20s: 0x%.8x\n", data[3].name,
mem_br->mem_enable_ack_mask);
}
}
static int clk_branch2_set_flags(struct clk_hw *hw, unsigned long flags)
{
struct clk_branch *br = to_clk_branch(hw);
u32 cbcr_val = 0, cbcr_mask;
int ret;
switch (flags) {
case CLKFLAG_PERIPH_OFF_SET:
cbcr_val = cbcr_mask = BIT(12);
break;
case CLKFLAG_PERIPH_OFF_CLEAR:
cbcr_mask = BIT(12);
break;
case CLKFLAG_RETAIN_PERIPH:
cbcr_val = cbcr_mask = BIT(13);
break;
case CLKFLAG_NORETAIN_PERIPH:
cbcr_mask = BIT(13);
break;
case CLKFLAG_RETAIN_MEM:
cbcr_val = cbcr_mask = BIT(14);
break;
case CLKFLAG_NORETAIN_MEM:
cbcr_mask = BIT(14);
break;
default:
return -EINVAL;
}
ret = regmap_update_bits(br->clkr.regmap, br->halt_reg, cbcr_mask,
cbcr_val);
/* Make sure power is enabled/disabled before returning. */
mb();
udelay(1);
return ret;
}
static struct clk_regmap_ops clk_branch2_regmap_ops = {
.list_registers = clk_branch2_list_registers,
.set_flags = clk_branch2_set_flags,
};
static struct clk_regmap_ops clk_branch2_mem_regmap_ops = {
.list_registers = clk_branch2_mem_list_registers,
.set_flags = clk_branch2_set_flags,
};
static int clk_branch2_init(struct clk_hw *hw)
{
struct clk_regmap *rclk = to_clk_regmap(hw);
if (!rclk->ops)
rclk->ops = &clk_branch2_regmap_ops;
return 0;
}
static int clk_branch2_mem_init(struct clk_hw *hw)
{
struct clk_regmap *rclk = to_clk_regmap(hw);
if (!rclk->ops)
rclk->ops = &clk_branch2_mem_regmap_ops;
return 0;
}
static void clk_branch_restore_context_aon(struct clk_hw *hw)
{
if (clk_enable_regmap(hw))
pr_err("Failed to enable %s\n", clk_hw_get_name(hw));
}
static void clk_branch_restore_context(struct clk_hw *hw)
{
if (!(clk_hw_get_flags(hw) & CLK_IS_CRITICAL))
return;
if (clk_enable_regmap(hw))
pr_err("Failed to enable %s\n", clk_hw_get_name(hw));
}
const struct clk_ops clk_branch2_ops = { const struct clk_ops clk_branch2_ops = {
.prepare = clk_prepare_regmap,
.unprepare = clk_unprepare_regmap,
.pre_rate_change = clk_pre_change_regmap,
.post_rate_change = clk_post_change_regmap,
.enable = clk_branch2_enable, .enable = clk_branch2_enable,
.disable = clk_branch2_disable, .disable = clk_branch2_disable,
.is_enabled = clk_is_enabled_regmap, .is_enabled = clk_is_enabled_regmap,
.init = clk_branch2_init,
.debug_init = clk_branch_debug_init,
.restore_context = clk_branch_restore_context,
}; };
EXPORT_SYMBOL_GPL(clk_branch2_ops); EXPORT_SYMBOL_GPL(clk_branch2_ops);
const struct clk_ops clk_branch2_crm_ops = {
.is_enabled = clk_is_enabled_regmap,
.init = clk_branch2_init,
.debug_init = clk_branch_debug_init,
};
EXPORT_SYMBOL_GPL(clk_branch2_crm_ops);
const struct clk_ops clk_branch2_aon_ops = { const struct clk_ops clk_branch2_aon_ops = {
.enable = clk_branch2_enable, .enable = clk_branch2_enable,
.restore_context = clk_branch_restore_context_aon,
.is_enabled = clk_is_enabled_regmap, .is_enabled = clk_is_enabled_regmap,
.init = clk_branch2_init,
.debug_init = clk_branch_debug_init,
}; };
EXPORT_SYMBOL_GPL(clk_branch2_aon_ops); EXPORT_SYMBOL_GPL(clk_branch2_aon_ops);
const struct clk_ops clk_branch2_force_off_ops = {
.enable = clk_branch2_force_off_enable,
.disable = clk_branch2_force_off_disable,
.is_enabled = clk_is_enabled_regmap,
.init = clk_branch2_init,
.debug_init = clk_branch_debug_init,
};
EXPORT_SYMBOL(clk_branch2_force_off_ops);
const struct clk_ops clk_branch2_mem_ops = {
.enable = clk_branch2_mem_enable,
.disable = clk_branch2_mem_disable,
.is_enabled = clk_is_enabled_regmap,
.init = clk_branch2_mem_init,
.debug_init = clk_branch_debug_init,
};
EXPORT_SYMBOL_GPL(clk_branch2_mem_ops);
static unsigned long clk_branch2_hw_ctl_recalc_rate(struct clk_hw *hw,
unsigned long parent_rate)
{
return parent_rate;
}
static int clk_branch2_hw_ctl_determine_rate(struct clk_hw *hw,
struct clk_rate_request *req)
{
struct clk_hw *clkp;
clkp = clk_hw_get_parent(hw);
if (!clkp)
return -EINVAL;
req->best_parent_hw = clkp;
req->best_parent_rate = clk_round_rate(clkp->clk, req->rate);
return 0;
}
static int clk_branch2_hw_ctl_enable(struct clk_hw *hw)
{
struct clk_hw *parent = clk_hw_get_parent(hw);
/* The parent branch clock should have been prepared prior to this. */
if (!parent || (parent && !clk_hw_is_prepared(parent)))
return -EINVAL;
return clk_enable_regmap(hw);
}
static void clk_branch2_hw_ctl_disable(struct clk_hw *hw)
{
struct clk_hw *parent = clk_hw_get_parent(hw);
if (!parent)
return;
clk_disable_regmap(hw);
}
const struct clk_ops clk_branch2_hw_ctl_ops = {
.enable = clk_branch2_hw_ctl_enable,
.disable = clk_branch2_hw_ctl_disable,
.is_enabled = clk_is_enabled_regmap,
.recalc_rate = clk_branch2_hw_ctl_recalc_rate,
.determine_rate = clk_branch2_hw_ctl_determine_rate,
.init = clk_branch2_init,
.debug_init = clk_branch_debug_init,
};
EXPORT_SYMBOL(clk_branch2_hw_ctl_ops);
const struct clk_ops clk_branch_simple_ops = { const struct clk_ops clk_branch_simple_ops = {
.enable = clk_enable_regmap, .enable = clk_enable_regmap,
.disable = clk_disable_regmap, .disable = clk_disable_regmap,
.is_enabled = clk_is_enabled_regmap, .is_enabled = clk_is_enabled_regmap,
.init = clk_branch2_init,
.debug_init = clk_branch_debug_init,
}; };
EXPORT_SYMBOL_GPL(clk_branch_simple_ops); EXPORT_SYMBOL_GPL(clk_branch_simple_ops);

View File

@@ -1,5 +1,6 @@
/* SPDX-License-Identifier: GPL-2.0 */ /* SPDX-License-Identifier: GPL-2.0-only */
/* Copyright (c) 2013, The Linux Foundation. All rights reserved. */ /* Copyright (c) 2013, 2016, 2020 The Linux Foundation. All rights reserved. */
/* Copyright (c) 2022, 2024, Qualcomm Innovation Center, Inc. All rights reserved. */
#ifndef __QCOM_CLK_BRANCH_H__ #ifndef __QCOM_CLK_BRANCH_H__
#define __QCOM_CLK_BRANCH_H__ #define __QCOM_CLK_BRANCH_H__
@@ -34,6 +35,7 @@ struct clk_branch {
#define BRANCH_HALT_ENABLE_VOTED (BRANCH_HALT_ENABLE | BRANCH_VOTED) #define BRANCH_HALT_ENABLE_VOTED (BRANCH_HALT_ENABLE | BRANCH_VOTED)
#define BRANCH_HALT_DELAY 2 /* No bit to check; just delay */ #define BRANCH_HALT_DELAY 2 /* No bit to check; just delay */
#define BRANCH_HALT_SKIP 3 /* Don't check halt bit */ #define BRANCH_HALT_SKIP 3 /* Don't check halt bit */
#define BRANCH_HALT_INVERT 4 /* Invert logic for halt bit */
struct clk_regmap clkr; struct clk_regmap clkr;
}; };
@@ -81,12 +83,40 @@ static inline void qcom_branch_set_sleep(struct regmap *regmap, struct clk_branc
FIELD_PREP(CBCR_SLEEP, val)); FIELD_PREP(CBCR_SLEEP, val));
} }
/**
* struct clk_mem_branch - gating clock which are associated with memories
*
* @mem_enable_reg: branch clock memory gating register
* @mem_ack_reg: branch clock memory ack register
* @mem_enable_mask: branch clock memory enable mask
* @mem_enable_ack_mask: branch clock memory enable and ack field in @mem_ack_reg
* @mem_enable_inverted: clock memory enable bit inverted
* @branch: branch clock gating handle
*
* Clock which can gate its memories.
*/
struct clk_mem_branch {
u32 mem_enable_reg;
u32 mem_ack_reg;
u32 mem_enable_mask;
u32 mem_enable_ack_mask;
u8 mem_enable_inverted;
struct clk_branch branch;
};
extern const struct clk_ops clk_branch_ops; extern const struct clk_ops clk_branch_ops;
extern const struct clk_ops clk_branch2_ops; extern const struct clk_ops clk_branch2_ops;
extern const struct clk_ops clk_branch2_hw_ctl_ops;
extern const struct clk_ops clk_branch_simple_ops; extern const struct clk_ops clk_branch_simple_ops;
extern const struct clk_ops clk_branch2_aon_ops; extern const struct clk_ops clk_branch2_aon_ops;
extern const struct clk_ops clk_branch2_force_off_ops;
extern const struct clk_ops clk_branch2_mem_ops;
extern const struct clk_ops clk_branch2_crm_ops;
#define to_clk_branch(_hw) \ #define to_clk_branch(_hw) \
container_of(to_clk_regmap(_hw), struct clk_branch, clkr) container_of(to_clk_regmap(_hw), struct clk_branch, clkr)
#define to_clk_mem_branch(_hw) \
container_of(to_clk_branch(_hw), struct clk_mem_branch, branch)
#endif #endif

0
drivers/clk/qcom/clk-debug.c Executable file → Normal file
View File

0
drivers/clk/qcom/clk-debug.h Executable file → Normal file
View File

0
drivers/clk/qcom/clk-dummy.c Executable file → Normal file
View File

0
drivers/clk/qcom/clk-opp.c Executable file → Normal file
View File

0
drivers/clk/qcom/clk-opp.h Executable file → Normal file
View File

0
drivers/clk/qcom/clk-pm.c Executable file → Normal file
View File

0
drivers/clk/qcom/clk-pm.h Executable file → Normal file
View File

View File

@@ -1,6 +1,6 @@
// SPDX-License-Identifier: GPL-2.0-only // SPDX-License-Identifier: GPL-2.0-only
/* /*
* Copyright (c) 2013, The Linux Foundation. All rights reserved. * Copyright (c) 2013, 2019, The Linux Foundation. All rights reserved.
*/ */
#include <linux/kernel.h> #include <linux/kernel.h>
@@ -414,6 +414,8 @@ static int _freq_tbl_determine_rate(struct clk_hw *hw, const struct freq_tbl *f,
clk_flags = clk_hw_get_flags(hw); clk_flags = clk_hw_get_flags(hw);
p = clk_hw_get_parent_by_index(hw, index); p = clk_hw_get_parent_by_index(hw, index);
if (!p)
return -EINVAL;
if (clk_flags & CLK_SET_RATE_PARENT) { if (clk_flags & CLK_SET_RATE_PARENT) {
rate = rate * f->pre_div; rate = rate * f->pre_div;
if (f->n) { if (f->n) {
@@ -465,6 +467,8 @@ static int clk_rcg_bypass_determine_rate(struct clk_hw *hw,
int index = qcom_find_src_index(hw, rcg->s.parent_map, f->src); int index = qcom_find_src_index(hw, rcg->s.parent_map, f->src);
req->best_parent_hw = p = clk_hw_get_parent_by_index(hw, index); req->best_parent_hw = p = clk_hw_get_parent_by_index(hw, index);
if (!p)
return -EINVAL;
req->best_parent_rate = clk_hw_round_rate(p, req->rate); req->best_parent_rate = clk_hw_round_rate(p, req->rate);
req->rate = req->best_parent_rate; req->rate = req->best_parent_rate;

View File

@@ -1,5 +1,6 @@
/* SPDX-License-Identifier: GPL-2.0 */ /* SPDX-License-Identifier: GPL-2.0-only */
/* Copyright (c) 2013, 2018, The Linux Foundation. All rights reserved. */ /* Copyright (c) 2013, 2016-2018, 2020 The Linux Foundation. All rights reserved. */
/* Copyright (c) 2022, Qualcomm Innovation Center, Inc. All rights reserved. */
#ifndef __QCOM_CLK_RCG_H__ #ifndef __QCOM_CLK_RCG_H__
#define __QCOM_CLK_RCG_H__ #define __QCOM_CLK_RCG_H__
@@ -15,6 +16,8 @@ struct freq_tbl {
u8 pre_div; u8 pre_div;
u16 m; u16 m;
u16 n; u16 n;
unsigned long src_freq;
#define FIXED_FREQ_SRC 0
}; };
/** /**
@@ -138,9 +141,12 @@ extern const struct clk_ops clk_dyn_rcg_ops;
* @safe_src_index: safe src index value * @safe_src_index: safe src index value
* @parent_map: map from software's parent index to hardware's src_sel field * @parent_map: map from software's parent index to hardware's src_sel field
* @freq_tbl: frequency table * @freq_tbl: frequency table
* @current_freq: last cached frequency when using branches with shared RCGs
* @enable_safe_config: When set, the RCG is parked at CXO when it's disabled
* @clkr: regmap clock handle * @clkr: regmap clock handle
* @cfg_off: defines the cfg register offset from the CMD_RCGR + CFG_REG * @cfg_off: defines the cfg register offset from the CMD_RCGR + CFG_REG
* @parked_cfg: cached value of the CFG register for parked RCGs * @parked_cfg: cached value of the CFG register for parked RCGs
* @flags: additional flag parameters for the RCG
* @hw_clk_ctrl: whether to enable hardware clock control * @hw_clk_ctrl: whether to enable hardware clock control
*/ */
struct clk_rcg2 { struct clk_rcg2 {
@@ -150,9 +156,17 @@ struct clk_rcg2 {
u8 safe_src_index; u8 safe_src_index;
const struct parent_map *parent_map; const struct parent_map *parent_map;
const struct freq_tbl *freq_tbl; const struct freq_tbl *freq_tbl;
unsigned long configured_freq;
unsigned long current_freq;
bool enable_safe_config;
struct clk_regmap clkr; struct clk_regmap clkr;
u8 cfg_off; u8 cfg_off;
u32 parked_cfg; u32 parked_cfg;
u8 flags;
#define FORCE_ENABLE_RCG BIT(0)
#define HW_CLK_CTRL_MODE BIT(1)
#define DFS_SUPPORT BIT(2)
bool freq_populated;
bool hw_clk_ctrl; bool hw_clk_ctrl;
}; };
@@ -176,9 +190,9 @@ extern const struct clk_ops clk_byte2_ops;
extern const struct clk_ops clk_pixel_ops; extern const struct clk_ops clk_pixel_ops;
extern const struct clk_ops clk_gfx3d_ops; extern const struct clk_ops clk_gfx3d_ops;
extern const struct clk_ops clk_rcg2_shared_ops; extern const struct clk_ops clk_rcg2_shared_ops;
extern const struct clk_ops clk_rcg2_shared_floor_ops;
extern const struct clk_ops clk_rcg2_shared_no_init_park_ops;
extern const struct clk_ops clk_dp_ops; extern const struct clk_ops clk_dp_ops;
extern const struct clk_ops clk_rcg2_crmc_ops;
extern const struct clk_ops clk_rcg2_crmb_ops;
struct clk_rcg_dfs_data { struct clk_rcg_dfs_data {
struct clk_rcg2 *rcg; struct clk_rcg2 *rcg;

File diff suppressed because it is too large Load Diff

View File

@@ -1,6 +1,6 @@
// SPDX-License-Identifier: GPL-2.0-only // SPDX-License-Identifier: GPL-2.0-only
/* /*
* Copyright (c) 2014, The Linux Foundation. All rights reserved. * Copyright (c) 2014, 2017, 2020-2021, The Linux Foundation. All rights reserved.
*/ */
#include <linux/kernel.h> #include <linux/kernel.h>
@@ -9,6 +9,7 @@
#include <linux/export.h> #include <linux/export.h>
#include "clk-regmap-divider.h" #include "clk-regmap-divider.h"
#include "clk-debug.h"
static inline struct clk_regmap_div *to_clk_regmap_div(struct clk_hw *hw) static inline struct clk_regmap_div *to_clk_regmap_div(struct clk_hw *hw)
{ {
@@ -21,11 +22,18 @@ static long div_round_ro_rate(struct clk_hw *hw, unsigned long rate,
struct clk_regmap_div *divider = to_clk_regmap_div(hw); struct clk_regmap_div *divider = to_clk_regmap_div(hw);
struct clk_regmap *clkr = &divider->clkr; struct clk_regmap *clkr = &divider->clkr;
u32 val; u32 val;
int ret;
ret = clk_runtime_get_regmap(clkr);
if (ret)
return ret;
regmap_read(clkr->regmap, divider->reg, &val); regmap_read(clkr->regmap, divider->reg, &val);
val >>= divider->shift; val >>= divider->shift;
val &= BIT(divider->width) - 1; val &= BIT(divider->width) - 1;
clk_runtime_put_regmap(clkr);
return divider_ro_round_rate(hw, rate, prate, NULL, divider->width, return divider_ro_round_rate(hw, rate, prate, NULL, divider->width,
CLK_DIVIDER_ROUND_CLOSEST, val); CLK_DIVIDER_ROUND_CLOSEST, val);
} }
@@ -35,8 +43,10 @@ static long div_round_rate(struct clk_hw *hw, unsigned long rate,
{ {
struct clk_regmap_div *divider = to_clk_regmap_div(hw); struct clk_regmap_div *divider = to_clk_regmap_div(hw);
return divider_round_rate(hw, rate, prate, NULL, divider->width, return divider_round_rate(hw, rate, prate, divider->table,
CLK_DIVIDER_ROUND_CLOSEST); divider->width,
CLK_DIVIDER_ROUND_CLOSEST |
divider->flags);
} }
static int div_set_rate(struct clk_hw *hw, unsigned long rate, static int div_set_rate(struct clk_hw *hw, unsigned long rate,
@@ -46,8 +56,9 @@ static int div_set_rate(struct clk_hw *hw, unsigned long rate,
struct clk_regmap *clkr = &divider->clkr; struct clk_regmap *clkr = &divider->clkr;
u32 div; u32 div;
div = divider_get_val(rate, parent_rate, NULL, divider->width, div = divider_get_val(rate, parent_rate, divider->table,
CLK_DIVIDER_ROUND_CLOSEST); divider->width, CLK_DIVIDER_ROUND_CLOSEST |
divider->flags);
return regmap_update_bits(clkr->regmap, divider->reg, return regmap_update_bits(clkr->regmap, divider->reg,
(BIT(divider->width) - 1) << divider->shift, (BIT(divider->width) - 1) << divider->shift,
@@ -65,8 +76,51 @@ static unsigned long div_recalc_rate(struct clk_hw *hw,
div >>= divider->shift; div >>= divider->shift;
div &= BIT(divider->width) - 1; div &= BIT(divider->width) - 1;
return divider_recalc_rate(hw, parent_rate, div, NULL, return divider_recalc_rate(hw, parent_rate, div, divider->table,
CLK_DIVIDER_ROUND_CLOSEST, divider->width); CLK_DIVIDER_ROUND_CLOSEST | divider->flags,
divider->width);
}
static long clk_regmap_div_list_rate(struct clk_hw *hw, unsigned int n,
unsigned long fmax)
{
struct clk_regmap_div *divider = to_clk_regmap_div(hw);
struct clk_hw *parent_hw = clk_hw_get_parent(hw);
struct clk_regmap *clkr = &divider->clkr;
struct clk_regmap *parent_clkr = to_clk_regmap(parent_hw);
u32 div;
int ret;
ret = clk_runtime_get_regmap(clkr);
if (ret)
return ret;
regmap_read(clkr->regmap, divider->reg, &div);
div >>= divider->shift;
div &= BIT(divider->width) - 1;
div += 1;
clk_runtime_put_regmap(clkr);
if (parent_clkr && parent_clkr->ops && parent_clkr->ops->list_rate)
return (parent_clkr->ops->list_rate(parent_hw, n, fmax) / div);
return -EINVAL;
}
static struct clk_regmap_ops clk_regmap_div_regmap_ops = {
.list_rate = clk_regmap_div_list_rate,
};
static int clk_regmap_div_init(struct clk_hw *hw)
{
struct clk_regmap_div *divider = to_clk_regmap_div(hw);
struct clk_regmap *clkr = &divider->clkr;
if (!clkr->ops)
clkr->ops = &clk_regmap_div_regmap_ops;
return 0;
} }
const struct clk_ops clk_regmap_div_ops = { const struct clk_ops clk_regmap_div_ops = {
@@ -79,5 +133,7 @@ EXPORT_SYMBOL_GPL(clk_regmap_div_ops);
const struct clk_ops clk_regmap_div_ro_ops = { const struct clk_ops clk_regmap_div_ro_ops = {
.round_rate = div_round_ro_rate, .round_rate = div_round_ro_rate,
.recalc_rate = div_recalc_rate, .recalc_rate = div_recalc_rate,
.init = clk_regmap_div_init,
.debug_init = clk_common_debug_init,
}; };
EXPORT_SYMBOL_GPL(clk_regmap_div_ro_ops); EXPORT_SYMBOL_GPL(clk_regmap_div_ro_ops);

View File

@@ -1,6 +1,6 @@
/* SPDX-License-Identifier: GPL-2.0-only */ /* SPDX-License-Identifier: GPL-2.0-only */
/* /*
* Copyright (c) 2014, The Linux Foundation. All rights reserved. * Copyright (c) 2014, 2017, The Linux Foundation. All rights reserved.
*/ */
#ifndef __QCOM_CLK_REGMAP_DIVIDER_H__ #ifndef __QCOM_CLK_REGMAP_DIVIDER_H__
@@ -13,6 +13,8 @@ struct clk_regmap_div {
u32 reg; u32 reg;
u32 shift; u32 shift;
u32 width; u32 width;
u32 flags;
const struct clk_div_table *table;
struct clk_regmap clkr; struct clk_regmap clkr;
}; };

View File

@@ -2,6 +2,7 @@
/* /*
* Copyright (c) 2017, Linaro Limited * Copyright (c) 2017, Linaro Limited
* Author: Georgi Djakov <georgi.djakov@linaro.org> * Author: Georgi Djakov <georgi.djakov@linaro.org>
* Copyright (c) 2024, Qualcomm Innovation Center, Inc. All rights reserved.
*/ */
#include <linux/bitops.h> #include <linux/bitops.h>
@@ -220,7 +221,23 @@ static unsigned long mux_div_recalc_rate(struct clk_hw *hw, unsigned long prate)
return 0; return 0;
} }
static int mux_div_enable(struct clk_hw *hw)
{
struct clk_regmap_mux_div *md = to_clk_regmap_mux_div(hw);
return mux_div_set_src_div(md, md->src, md->div);
}
static void mux_div_disable(struct clk_hw *hw)
{
struct clk_regmap_mux_div *md = to_clk_regmap_mux_div(hw);
mux_div_set_src_div(md, md->safe_src, md->safe_div);
}
const struct clk_ops clk_regmap_mux_div_ops = { const struct clk_ops clk_regmap_mux_div_ops = {
.enable = mux_div_enable,
.disable = mux_div_disable,
.get_parent = mux_div_get_parent, .get_parent = mux_div_get_parent,
.set_parent = mux_div_set_parent, .set_parent = mux_div_set_parent,
.set_rate = mux_div_set_rate, .set_rate = mux_div_set_rate,

View File

@@ -2,6 +2,7 @@
/* /*
* Copyright (c) 2017, Linaro Limited * Copyright (c) 2017, Linaro Limited
* Author: Georgi Djakov <georgi.djakov@linaro.org> * Author: Georgi Djakov <georgi.djakov@linaro.org>
* Copyright (c) 2024, Qualcomm Innovation Center, Inc. All rights reserved.
*/ */
#ifndef __QCOM_CLK_REGMAP_MUX_DIV_H__ #ifndef __QCOM_CLK_REGMAP_MUX_DIV_H__
@@ -19,7 +20,19 @@
* @src_shift: lowest bit of source select field * @src_shift: lowest bit of source select field
* @div: the divider raw configuration value * @div: the divider raw configuration value
* @src: the mux index which will be used if the clock is enabled * @src: the mux index which will be used if the clock is enabled
* @parent_map: map from parent_names index to src_sel field * @safe_src: the safe source mux value we switch to, while the main PLL is
* reconfigured
* @safe_div: the safe divider value that we set, while the main PLL is
* reconfigured
* @safe_freq: When switching rates from A to B, the mux div clock will
* instead switch from A -> safe_freq -> B. This allows the
* mux_div clock to change rates while enabled, even if this
* behavior is not supported by the parent clocks.
* If changing the rate of parent A also causes the rate of
* parent B to change, then safe_freq must be defined.
* safe_freq is expected to have a source clock which is always
* on and runs at only one rate.
* @parent_map: pointer to parent_map struct
* @clkr: handle between common and hardware-specific interfaces * @clkr: handle between common and hardware-specific interfaces
* @pclk: the input PLL clock * @pclk: the input PLL clock
* @clk_nb: clock notifier for rate changes of the input PLL * @clk_nb: clock notifier for rate changes of the input PLL
@@ -32,6 +45,9 @@ struct clk_regmap_mux_div {
u32 src_shift; u32 src_shift;
u32 div; u32 div;
u32 src; u32 src;
u32 safe_src;
u32 safe_div;
unsigned long safe_freq;
const u32 *parent_map; const u32 *parent_map;
struct clk_regmap clkr; struct clk_regmap clkr;
struct clk *pclk; struct clk *pclk;

View File

@@ -9,6 +9,7 @@
#include <linux/export.h> #include <linux/export.h>
#include "clk-regmap-mux.h" #include "clk-regmap-mux.h"
#include "clk-debug.h"
static inline struct clk_regmap_mux *to_clk_regmap_mux(struct clk_hw *hw) static inline struct clk_regmap_mux *to_clk_regmap_mux(struct clk_hw *hw)
{ {
@@ -49,9 +50,34 @@ static int mux_set_parent(struct clk_hw *hw, u8 index)
return regmap_update_bits(clkr->regmap, mux->reg, mask, val); return regmap_update_bits(clkr->regmap, mux->reg, mask, val);
} }
static void clk_regmap_mux_list_registers(struct seq_file *f, struct clk_hw *hw)
{
struct clk_regmap_mux *mux = to_clk_regmap_mux(hw);
int val;
regmap_read(mux->clkr.regmap, mux->reg, &val);
clock_debug_output(f, "%20s: 0x%.8x\n", "MUXR", val);
}
static struct clk_regmap_ops clk_regmap_mux_regmap_ops = {
.list_registers = clk_regmap_mux_list_registers,
};
static int clk_regmap_mux_init(struct clk_hw *hw)
{
struct clk_regmap *rclk = to_clk_regmap(hw);
if (!rclk->ops)
rclk->ops = &clk_regmap_mux_regmap_ops;
return 0;
}
const struct clk_ops clk_regmap_mux_closest_ops = { const struct clk_ops clk_regmap_mux_closest_ops = {
.get_parent = mux_get_parent, .get_parent = mux_get_parent,
.set_parent = mux_set_parent, .set_parent = mux_set_parent,
.determine_rate = __clk_mux_determine_rate_closest, .determine_rate = __clk_mux_determine_rate_closest,
.init = clk_regmap_mux_init,
.debug_init = clk_common_debug_init,
}; };
EXPORT_SYMBOL_GPL(clk_regmap_mux_closest_ops); EXPORT_SYMBOL_GPL(clk_regmap_mux_closest_ops);

View File

@@ -1,14 +1,20 @@
// SPDX-License-Identifier: GPL-2.0 // SPDX-License-Identifier: GPL-2.0
/* /*
* Copyright (c) 2014, The Linux Foundation. All rights reserved. * Copyright (c) 2014, 2019-2021 The Linux Foundation. All rights reserved.
* Copyright (c) 2022-2024, Qualcomm Innovation Center, Inc. All rights reserved.
*/ */
#include <linux/device.h> #include <linux/device.h>
#include <linux/clk-provider.h> #include <linux/clk-provider.h>
#include <linux/regmap.h> #include <linux/regmap.h>
#include <linux/export.h> #include <linux/export.h>
#include <linux/pm_runtime.h>
#include "clk-regmap.h" #include "clk-regmap.h"
#include "clk-debug.h"
static LIST_HEAD(clk_regmap_list);
static DEFINE_SPINLOCK(clk_regmap_lock);
/** /**
* clk_is_enabled_regmap - standard is_enabled() for regmap users * clk_is_enabled_regmap - standard is_enabled() for regmap users
@@ -84,6 +90,182 @@ void clk_disable_regmap(struct clk_hw *hw)
} }
EXPORT_SYMBOL_GPL(clk_disable_regmap); EXPORT_SYMBOL_GPL(clk_disable_regmap);
/**
* clk_pre_change_regmap() - standard pre_change call back for regmap clks
*
* @hw: clk to operate on
* @cur_rate: current rate of the clk
* @new_rate: new rate about to be set for the clk
*
* Finds new vdd level corresponding to new rate and update vdd_level
* cache if new_vdd_level is greater than vdd_level. If clock is prepared
* then update existing vdd vote.
*
* Returns 0 on success, -EERROR otherwise.
*/
int clk_pre_change_regmap(struct clk_hw *hw, unsigned long cur_rate,
unsigned long new_rate)
{
struct clk_regmap *rclk = to_clk_regmap(hw);
int vdd_level = rclk->vdd_data.vdd_level;
int new_vdd_level;
int ret = 0;
if (!rclk->vdd_data.rate_max)
return 0;
new_vdd_level = clk_find_vdd_level(hw, &rclk->vdd_data, new_rate);
if (new_vdd_level < 0)
return new_vdd_level;
if (new_vdd_level <= vdd_level)
return 0;
if (clk_hw_is_prepared(hw)) {
ret = clk_vote_vdd_level(&rclk->vdd_data, new_vdd_level);
if (ret)
return ret;
clk_unvote_vdd_level(&rclk->vdd_data, vdd_level);
}
rclk->vdd_data.vdd_level = new_vdd_level;
return 0;
}
EXPORT_SYMBOL_GPL(clk_pre_change_regmap);
/**
* clk_post_change_regmap() - standard post_change call back for regmap clks
*
* @hw: clk to operate on
* @old_rate: previous rate of the clk
* @cur_rate: current rate of the recently changed clk
*
* Finds new vdd level corresponding to current rate and update vdd_level
* cache if cur_vdd_level is less than vdd_level. If clock is prepared
* then update existing vdd vote.
*
* Returns 0 on success, -EERROR otherwise.
*/
int clk_post_change_regmap(struct clk_hw *hw, unsigned long old_rate,
unsigned long cur_rate)
{
struct clk_regmap *rclk = to_clk_regmap(hw);
int vdd_level = rclk->vdd_data.vdd_level;
int cur_vdd_level;
int ret = 0;
if (!rclk->vdd_data.rate_max)
return 0;
cur_vdd_level = clk_find_vdd_level(hw, &rclk->vdd_data, cur_rate);
if (cur_vdd_level < 0)
return cur_vdd_level;
if (cur_vdd_level >= vdd_level)
return 0;
if (clk_hw_is_prepared(hw)) {
ret = clk_vote_vdd_level(&rclk->vdd_data, cur_vdd_level);
if (ret)
return ret;
clk_unvote_vdd_level(&rclk->vdd_data, vdd_level);
}
rclk->vdd_data.vdd_level = cur_vdd_level;
return 0;
}
EXPORT_SYMBOL_GPL(clk_post_change_regmap);
/**
* clk_prepare_regmap() - standard prepare call back for regmap clks
*
* @hw: clk to operate on
*
* Prepare the clock by updating the vdd_level to level required by
* the current rate of the clock if it hasn't been initialized before.
* Vdd_level and level required by current clock rate mismatches can
* occur due to error cases and upon initial clock registration
* if the clock becomes an orphan and is later reparented.
*
* Returns 0 on success, -EERROR otherwise.
*/
int clk_prepare_regmap(struct clk_hw *hw)
{
struct clk_regmap *rclk = to_clk_regmap(hw);
unsigned long rate = clk_hw_get_rate(hw);
int vdd_level;
if (!rclk->vdd_data.rate_max)
return 0;
vdd_level = clk_find_vdd_level(hw, &rclk->vdd_data, rate);
if (vdd_level < 0)
return vdd_level;
if (rclk->vdd_data.vdd_level == 0)
rclk->vdd_data.vdd_level = vdd_level;
WARN(vdd_level > rclk->vdd_data.vdd_level,
"%s level:%d > vdd_level:%d\n", clk_hw_get_name(hw),
vdd_level, rclk->vdd_data.vdd_level);
return clk_vote_vdd_level(&rclk->vdd_data, rclk->vdd_data.vdd_level);
}
EXPORT_SYMBOL_GPL(clk_prepare_regmap);
/**
* clk_prepare_regmap() - standard prepare call back for regmap clks
*
* @hw: clk to operate on
*
* Unprepare the clock by removing the outstanding vdd_level vote.
*
*/
void clk_unprepare_regmap(struct clk_hw *hw)
{
struct clk_regmap *rclk = to_clk_regmap(hw);
if (!rclk->vdd_data.rate_max)
return;
clk_unvote_vdd_level(&rclk->vdd_data, rclk->vdd_data.vdd_level);
}
EXPORT_SYMBOL_GPL(clk_unprepare_regmap);
/**
* clk_is_regmap_clk - Checks if clk is a regmap clk
*
* @hw: clk to check on
*
* Iterate over maintained clk regmap list to know
* if concern clk is regmap
*
* Returns true on success, false otherwise.
*/
bool clk_is_regmap_clk(struct clk_hw *hw)
{
struct clk_regmap *rclk;
bool is_regmap_clk = false;
if (hw) {
spin_lock(&clk_regmap_lock);
list_for_each_entry(rclk, &clk_regmap_list, list_node) {
if (&rclk->hw == hw) {
is_regmap_clk = true;
break;
}
}
spin_unlock(&clk_regmap_lock);
}
return is_regmap_clk;
}
EXPORT_SYMBOL_GPL(clk_is_regmap_clk);
/** /**
* devm_clk_register_regmap - register a clk_regmap clock * devm_clk_register_regmap - register a clk_regmap clock
* *
@@ -93,14 +275,97 @@ EXPORT_SYMBOL_GPL(clk_disable_regmap);
* Clocks that use regmap for their register I/O should register their * Clocks that use regmap for their register I/O should register their
* clk_regmap struct via this function so that the regmap is initialized * clk_regmap struct via this function so that the regmap is initialized
* and so that the clock is registered with the common clock framework. * and so that the clock is registered with the common clock framework.
* Also maintain clk-regmap clks list for providers use.
*/ */
int devm_clk_register_regmap(struct device *dev, struct clk_regmap *rclk) int devm_clk_register_regmap(struct device *dev, struct clk_regmap *rclk)
{ {
const struct clk_ops *ops;
int ret;
rclk->dev = dev;
if (dev && dev_get_regmap(dev, NULL)) if (dev && dev_get_regmap(dev, NULL))
rclk->regmap = dev_get_regmap(dev, NULL); rclk->regmap = dev_get_regmap(dev, NULL);
else if (dev && dev->parent) else if (dev && dev->parent)
rclk->regmap = dev_get_regmap(dev->parent, NULL); rclk->regmap = dev_get_regmap(dev->parent, NULL);
return devm_clk_hw_register(dev, &rclk->hw); if (rclk->flags & QCOM_CLK_IS_CRITICAL || rclk->flags & QCOM_CLK_BOOT_CRITICAL) {
ops = rclk->hw.init->ops;
if (ops && ops->enable)
ops->enable(&rclk->hw);
if (rclk->flags & QCOM_CLK_IS_CRITICAL)
return 0;
}
ret = devm_clk_hw_register(dev, &rclk->hw);
if (!ret) {
spin_lock(&clk_regmap_lock);
list_add(&rclk->list_node, &clk_regmap_list);
spin_unlock(&clk_regmap_lock);
ret = clk_hw_debug_register(dev, &rclk->hw);
}
return ret;
} }
EXPORT_SYMBOL_GPL(devm_clk_register_regmap); EXPORT_SYMBOL_GPL(devm_clk_register_regmap);
/**
* devm_clk_regmap_list_node - Add a clk-regmap clock list for providers
*
* @rclk: clk to operate on
*
* Maintain clk-regmap clks list for providers use.
*/
void devm_clk_regmap_list_node(struct device *dev, struct clk_regmap *rclk)
{
list_add(&rclk->list_node, &clk_regmap_list);
}
EXPORT_SYMBOL_GPL(devm_clk_regmap_list_node);
int clk_runtime_get_regmap(struct clk_regmap *rclk)
{
int ret;
if(rclk->dev->parent && pm_runtime_enabled(rclk->dev->parent)) {
ret = pm_runtime_get_sync(rclk->dev->parent);
if (ret < 0)
return ret;
}
if (pm_runtime_enabled(rclk->dev)) {
ret = pm_runtime_get_sync(rclk->dev);
if (ret < 0)
return ret;
}
return 0;
}
EXPORT_SYMBOL_GPL(clk_runtime_get_regmap);
void clk_runtime_put_regmap(struct clk_regmap *rclk)
{
if (pm_runtime_enabled(rclk->dev))
pm_runtime_put_sync(rclk->dev);
if(rclk->dev->parent && pm_runtime_enabled(rclk->dev->parent))
pm_runtime_put_sync(rclk->dev->parent);
}
EXPORT_SYMBOL_GPL(clk_runtime_put_regmap);
void clk_restore_critical_clocks(struct device *dev)
{
struct qcom_cc_desc *desc = dev_get_drvdata(dev);
struct regmap *regmap = dev_get_regmap(dev, NULL);
struct critical_clk_offset *cclks = desc->critical_clk_en;
int i;
if (!regmap)
return;
for (i = 0; i < desc->num_critical_clk; i++)
regmap_update_bits(regmap, cclks[i].offset, cclks[i].mask,
cclks[i].mask);
}
EXPORT_SYMBOL_GPL(clk_restore_critical_clocks);

View File

@@ -1,13 +1,51 @@
/* SPDX-License-Identifier: GPL-2.0 */ /* SPDX-License-Identifier: GPL-2.0-only */
/* Copyright (c) 2014, The Linux Foundation. All rights reserved. */ /* Copyright (c) 2014, 2019-2021, The Linux Foundation. All rights reserved. */
/* Copyright (c) 2022-2024, Qualcomm Innovation Center, Inc. All rights reserved. */
#ifndef __QCOM_CLK_REGMAP_H__ #ifndef __QCOM_CLK_REGMAP_H__
#define __QCOM_CLK_REGMAP_H__ #define __QCOM_CLK_REGMAP_H__
#include <linux/clk-provider.h> #include <linux/clk-provider.h>
#include <linux/debugfs.h>
#include "vdd-class.h"
#include <soc/qcom/crm.h>
struct regmap; struct regmap;
/**
* struct clk_regmap_ops - Operations for clk_regmap.
*
* @list_registers: Queries the hardware to get the current register contents.
* This callback is optional.
*
* @list_rate: On success, return the nth supported frequency for a given
* clock that is below rate_max. Return -ENXIO in case there is
* no frequency table.
*
* @set_flags: Set custom flags which deal with hardware specifics. Returns 0
* on success, error otherwise.
*
* @calc_pll: On success returns pll output frequency. Returns 0
* on success, error otherwise.
* @set_crm_rate: Set crmc/crmb clk frequency. Returns 0
* on success, error otherwise.
* @set_crmb_rate: Set crmb clk frequency in ab, ib terms. Returns 0
* on success, error otherwise.
*/
struct clk_regmap_ops {
void (*list_registers)(struct seq_file *f,
struct clk_hw *hw);
long (*list_rate)(struct clk_hw *hw, unsigned int n,
unsigned long rate_max);
int (*set_flags)(struct clk_hw *clk, unsigned long flags);
unsigned long (*calc_pll)(struct clk_hw *hw, u32 l, u64 a);
unsigned long (*set_crm_rate)(struct clk_hw *hw, enum crm_drv_type client_type,
u32 client_idx, u32 pwr_st, unsigned long rate);
unsigned long (*set_crmb_rate)(struct clk_hw *hw, enum crm_drv_type client_type,
u32 client_idx, u32 resource_idx, u32 pwr_st,
u32 ab_rate, u32 ib_rate);
};
/** /**
* struct clk_regmap - regmap supporting clock * struct clk_regmap - regmap supporting clock
* @hw: handle between common and hardware-specific interfaces * @hw: handle between common and hardware-specific interfaces
@@ -16,13 +54,28 @@ struct regmap;
* @enable_mask: mask when using regmap enable/disable ops * @enable_mask: mask when using regmap enable/disable ops
* @enable_is_inverted: flag to indicate set enable_mask bits to disable * @enable_is_inverted: flag to indicate set enable_mask bits to disable
* when using clock_enable_regmap and friends APIs. * when using clock_enable_regmap and friends APIs.
* @vdd_data: struct containing vdd-class data for this clock
* @ops: operations this clk_regmap supports
* @crm: clk crm regmap
*/ */
struct clk_regmap { struct clk_regmap {
struct clk_hw hw; struct clk_hw hw;
struct regmap *regmap; struct regmap *regmap;
unsigned int enable_reg; unsigned int enable_reg;
unsigned int enable_mask; unsigned int enable_mask;
bool enable_is_inverted; bool enable_is_inverted;
struct clk_vdd_class_data vdd_data;
struct clk_regmap_ops *ops;
struct list_head list_node;
struct device *dev;
struct clk_crm *crm;
u8 crm_vcd;
u8 crm_base_node;
u8 crm_num_node;
#define QCOM_CLK_IS_CRITICAL BIT(0)
#define QCOM_CLK_BOOT_CRITICAL BIT(1)
unsigned long flags;
}; };
static inline struct clk_regmap *to_clk_regmap(struct clk_hw *hw) static inline struct clk_regmap *to_clk_regmap(struct clk_hw *hw)
@@ -33,6 +86,24 @@ static inline struct clk_regmap *to_clk_regmap(struct clk_hw *hw)
int clk_is_enabled_regmap(struct clk_hw *hw); int clk_is_enabled_regmap(struct clk_hw *hw);
int clk_enable_regmap(struct clk_hw *hw); int clk_enable_regmap(struct clk_hw *hw);
void clk_disable_regmap(struct clk_hw *hw); void clk_disable_regmap(struct clk_hw *hw);
int clk_prepare_regmap(struct clk_hw *hw);
void clk_unprepare_regmap(struct clk_hw *hw);
int clk_pre_change_regmap(struct clk_hw *hw, unsigned long cur_rate,
unsigned long new_rate);
int clk_post_change_regmap(struct clk_hw *hw, unsigned long old_rate,
unsigned long cur_rate);
int devm_clk_register_regmap(struct device *dev, struct clk_regmap *rclk); int devm_clk_register_regmap(struct device *dev, struct clk_regmap *rclk);
void devm_clk_regmap_list_node(struct device *dev, struct clk_regmap *rclk);
bool clk_is_regmap_clk(struct clk_hw *hw);
int clk_runtime_get_regmap(struct clk_regmap *rclk);
void clk_runtime_put_regmap(struct clk_regmap *rclk);
void clk_restore_critical_clocks(struct device *dev);
struct clk_register_data {
char *name;
u32 offset;
};
#endif #endif

View File

@@ -1,6 +1,7 @@
// SPDX-License-Identifier: GPL-2.0 // SPDX-License-Identifier: GPL-2.0
/* /*
* Copyright (c) 2018-2021, The Linux Foundation. All rights reserved. * Copyright (c) 2018-2021, The Linux Foundation. All rights reserved.
* Copyright (c) 2023-2024, Qualcomm Innovation Center, Inc. All rights reserved.
*/ */
#include <linux/clk-provider.h> #include <linux/clk-provider.h>
@@ -51,6 +52,7 @@ struct clk_rpmh {
struct clk_hw hw; struct clk_hw hw;
const char *res_name; const char *res_name;
u8 div; u8 div;
bool optional;
u32 res_addr; u32 res_addr;
u32 res_on_val; u32 res_on_val;
u32 state; u32 state;
@@ -70,13 +72,14 @@ struct clk_rpmh_desc {
static DEFINE_MUTEX(rpmh_clk_lock); static DEFINE_MUTEX(rpmh_clk_lock);
#define __DEFINE_CLK_RPMH(_name, _clk_name, _res_name, \ #define __DEFINE_CLK_RPMH(_name, _clk_name, _res_name, \
_res_en_offset, _res_on, _div) \ _res_en_offset, _res_on, _div, _optional) \
static struct clk_rpmh clk_rpmh_##_clk_name##_ao; \ static struct clk_rpmh clk_rpmh_##_clk_name##_ao; \
static struct clk_rpmh clk_rpmh_##_clk_name = { \ static struct clk_rpmh clk_rpmh_##_clk_name = { \
.res_name = _res_name, \ .res_name = _res_name, \
.res_addr = _res_en_offset, \ .res_addr = _res_en_offset, \
.res_on_val = _res_on, \ .res_on_val = _res_on, \
.div = _div, \ .div = _div, \
.optional = _optional, \
.peer = &clk_rpmh_##_clk_name##_ao, \ .peer = &clk_rpmh_##_clk_name##_ao, \
.valid_state_mask = (BIT(RPMH_WAKE_ONLY_STATE) | \ .valid_state_mask = (BIT(RPMH_WAKE_ONLY_STATE) | \
BIT(RPMH_ACTIVE_ONLY_STATE) | \ BIT(RPMH_ACTIVE_ONLY_STATE) | \
@@ -96,6 +99,7 @@ static DEFINE_MUTEX(rpmh_clk_lock);
.res_addr = _res_en_offset, \ .res_addr = _res_en_offset, \
.res_on_val = _res_on, \ .res_on_val = _res_on, \
.div = _div, \ .div = _div, \
.optional = _optional, \
.peer = &clk_rpmh_##_clk_name, \ .peer = &clk_rpmh_##_clk_name, \
.valid_state_mask = (BIT(RPMH_WAKE_ONLY_STATE) | \ .valid_state_mask = (BIT(RPMH_WAKE_ONLY_STATE) | \
BIT(RPMH_ACTIVE_ONLY_STATE)), \ BIT(RPMH_ACTIVE_ONLY_STATE)), \
@@ -110,13 +114,43 @@ static DEFINE_MUTEX(rpmh_clk_lock);
}, \ }, \
} }
#define DEFINE_CLK_RPMH_FIXED(_platform, _name, _name_active, \
_parent_name, _name_active_parent, \
_div) \
static struct clk_fixed_factor _platform##_##_name = { \
.mult = 1, \
.div = _div, \
.hw.init = &(struct clk_init_data){ \
.ops = &clk_fixed_factor_ops, \
.name = #_name, \
.parent_data = &(const struct clk_parent_data){ \
.fw_name = #_parent_name, \
.name = #_parent_name, \
}, \
.num_parents = 1, \
}, \
}; \
static struct clk_fixed_factor _platform##_##_name_active = { \
.mult = 1, \
.div = _div, \
.hw.init = &(struct clk_init_data){ \
.ops = &clk_fixed_factor_ops, \
.name = #_name_active, \
.parent_data = &(const struct clk_parent_data){ \
.fw_name = #_name_active_parent,\
.name = #_name_active_parent, \
}, \
.num_parents = 1, \
}, \
}
#define DEFINE_CLK_RPMH_ARC(_name, _res_name, _res_on, _div) \ #define DEFINE_CLK_RPMH_ARC(_name, _res_name, _res_on, _div) \
__DEFINE_CLK_RPMH(_name, _name##_##div##_div, _res_name, \ __DEFINE_CLK_RPMH(_name, _name##_##div##_div, _res_name, \
CLK_RPMH_ARC_EN_OFFSET, _res_on, _div) CLK_RPMH_ARC_EN_OFFSET, _res_on, _div, false)
#define DEFINE_CLK_RPMH_VRM(_name, _suffix, _res_name, _div) \ #define DEFINE_CLK_RPMH_VRM(_name, _suffix, _res_name, _div) \
__DEFINE_CLK_RPMH(_name, _name##_suffix, _res_name, \ __DEFINE_CLK_RPMH(_name, _name##_suffix, _res_name, \
CLK_RPMH_VRM_EN_OFFSET, 1, _div) CLK_RPMH_VRM_EN_OFFSET, 1, _div, true)
#define DEFINE_CLK_RPMH_BCM(_name, _res_name) \ #define DEFINE_CLK_RPMH_BCM(_name, _res_name) \
static struct clk_rpmh clk_rpmh_##_name = { \ static struct clk_rpmh clk_rpmh_##_name = { \
@@ -263,7 +297,8 @@ static int clk_rpmh_bcm_send_cmd(struct clk_rpmh *c, bool enable)
cmd_state = 0; cmd_state = 0;
} }
cmd_state = min(cmd_state, BCM_TCS_CMD_VOTE_MASK); if (cmd_state > BCM_TCS_CMD_VOTE_MASK)
cmd_state = BCM_TCS_CMD_VOTE_MASK;
if (c->last_sent_aggr_state != cmd_state) { if (c->last_sent_aggr_state != cmd_state) {
cmd.addr = c->res_addr; cmd.addr = c->res_addr;
@@ -329,7 +364,7 @@ static unsigned long clk_rpmh_bcm_recalc_rate(struct clk_hw *hw,
{ {
struct clk_rpmh *c = to_clk_rpmh(hw); struct clk_rpmh *c = to_clk_rpmh(hw);
return (unsigned long)c->aggr_state * c->unit; return c->aggr_state * c->unit;
} }
static const struct clk_ops clk_rpmh_bcm_ops = { static const struct clk_ops clk_rpmh_bcm_ops = {
@@ -345,6 +380,7 @@ DEFINE_CLK_RPMH_ARC(bi_tcxo, "xo.lvl", 0x3, 1);
DEFINE_CLK_RPMH_ARC(bi_tcxo, "xo.lvl", 0x3, 2); DEFINE_CLK_RPMH_ARC(bi_tcxo, "xo.lvl", 0x3, 2);
DEFINE_CLK_RPMH_ARC(bi_tcxo, "xo.lvl", 0x3, 4); DEFINE_CLK_RPMH_ARC(bi_tcxo, "xo.lvl", 0x3, 4);
DEFINE_CLK_RPMH_ARC(qlink, "qphy.lvl", 0x1, 4); DEFINE_CLK_RPMH_ARC(qlink, "qphy.lvl", 0x1, 4);
DEFINE_CLK_RPMH_ARC(xo_pad, "xo.lvl", 0x03, 2);
DEFINE_CLK_RPMH_VRM(ln_bb_clk1, _a2, "lnbclka1", 2); DEFINE_CLK_RPMH_VRM(ln_bb_clk1, _a2, "lnbclka1", 2);
DEFINE_CLK_RPMH_VRM(ln_bb_clk2, _a2, "lnbclka2", 2); DEFINE_CLK_RPMH_VRM(ln_bb_clk2, _a2, "lnbclka2", 2);
@@ -352,6 +388,7 @@ DEFINE_CLK_RPMH_VRM(ln_bb_clk3, _a2, "lnbclka3", 2);
DEFINE_CLK_RPMH_VRM(ln_bb_clk1, _a4, "lnbclka1", 4); DEFINE_CLK_RPMH_VRM(ln_bb_clk1, _a4, "lnbclka1", 4);
DEFINE_CLK_RPMH_VRM(ln_bb_clk2, _a4, "lnbclka2", 4); DEFINE_CLK_RPMH_VRM(ln_bb_clk2, _a4, "lnbclka2", 4);
DEFINE_CLK_RPMH_VRM(ln_bb_clk3, _a4, "lnbclka3", 4);
DEFINE_CLK_RPMH_VRM(ln_bb_clk2, _g4, "lnbclkg2", 4); DEFINE_CLK_RPMH_VRM(ln_bb_clk2, _g4, "lnbclkg2", 4);
DEFINE_CLK_RPMH_VRM(ln_bb_clk3, _g4, "lnbclkg3", 4); DEFINE_CLK_RPMH_VRM(ln_bb_clk3, _g4, "lnbclkg3", 4);
@@ -362,6 +399,10 @@ DEFINE_CLK_RPMH_VRM(rf_clk3, _a, "rfclka3", 1);
DEFINE_CLK_RPMH_VRM(rf_clk4, _a, "rfclka4", 1); DEFINE_CLK_RPMH_VRM(rf_clk4, _a, "rfclka4", 1);
DEFINE_CLK_RPMH_VRM(rf_clk5, _a, "rfclka5", 1); DEFINE_CLK_RPMH_VRM(rf_clk5, _a, "rfclka5", 1);
DEFINE_CLK_RPMH_VRM(rf_clk3, _a2, "rfclka3", 2);
DEFINE_CLK_RPMH_VRM(rf_clk4, _a2, "rfclka4", 2);
DEFINE_CLK_RPMH_VRM(rf_clk5, _a2, "rfclka5", 2);
DEFINE_CLK_RPMH_VRM(rf_clk1, _d, "rfclkd1", 1); DEFINE_CLK_RPMH_VRM(rf_clk1, _d, "rfclkd1", 1);
DEFINE_CLK_RPMH_VRM(rf_clk2, _d, "rfclkd2", 1); DEFINE_CLK_RPMH_VRM(rf_clk2, _d, "rfclkd2", 1);
DEFINE_CLK_RPMH_VRM(rf_clk3, _d, "rfclkd3", 1); DEFINE_CLK_RPMH_VRM(rf_clk3, _d, "rfclkd3", 1);
@@ -385,18 +426,6 @@ DEFINE_CLK_RPMH_BCM(ipa, "IP0");
DEFINE_CLK_RPMH_BCM(pka, "PKA0"); DEFINE_CLK_RPMH_BCM(pka, "PKA0");
DEFINE_CLK_RPMH_BCM(qpic_clk, "QP0"); DEFINE_CLK_RPMH_BCM(qpic_clk, "QP0");
static struct clk_hw *sar2130p_rpmh_clocks[] = {
[RPMH_CXO_CLK] = &clk_rpmh_bi_tcxo_div1.hw,
[RPMH_CXO_CLK_A] = &clk_rpmh_bi_tcxo_div1_ao.hw,
[RPMH_RF_CLK1] = &clk_rpmh_rf_clk1_a.hw,
[RPMH_RF_CLK1_A] = &clk_rpmh_rf_clk1_a_ao.hw,
};
static const struct clk_rpmh_desc clk_rpmh_sar2130p = {
.clks = sar2130p_rpmh_clocks,
.num_clks = ARRAY_SIZE(sar2130p_rpmh_clocks),
};
static struct clk_hw *sdm845_rpmh_clocks[] = { static struct clk_hw *sdm845_rpmh_clocks[] = {
[RPMH_CXO_CLK] = &clk_rpmh_bi_tcxo_div2.hw, [RPMH_CXO_CLK] = &clk_rpmh_bi_tcxo_div2.hw,
[RPMH_CXO_CLK_A] = &clk_rpmh_bi_tcxo_div2_ao.hw, [RPMH_CXO_CLK_A] = &clk_rpmh_bi_tcxo_div2_ao.hw,
@@ -731,6 +760,25 @@ static const struct clk_rpmh_desc clk_rpmh_sdx75 = {
.num_clks = ARRAY_SIZE(sdx75_rpmh_clocks), .num_clks = ARRAY_SIZE(sdx75_rpmh_clocks),
}; };
static struct clk_hw *sm4450_rpmh_clocks[] = {
[RPMH_CXO_CLK] = &clk_rpmh_bi_tcxo_div4.hw,
[RPMH_CXO_CLK_A] = &clk_rpmh_bi_tcxo_div4_ao.hw,
[RPMH_LN_BB_CLK2] = &clk_rpmh_ln_bb_clk2_a4.hw,
[RPMH_LN_BB_CLK2_A] = &clk_rpmh_ln_bb_clk2_a4_ao.hw,
[RPMH_LN_BB_CLK3] = &clk_rpmh_ln_bb_clk3_a4.hw,
[RPMH_LN_BB_CLK3_A] = &clk_rpmh_ln_bb_clk3_a4_ao.hw,
[RPMH_RF_CLK1] = &clk_rpmh_rf_clk1_a.hw,
[RPMH_RF_CLK1_A] = &clk_rpmh_rf_clk1_a_ao.hw,
[RPMH_RF_CLK5] = &clk_rpmh_rf_clk5_a.hw,
[RPMH_RF_CLK5_A] = &clk_rpmh_rf_clk5_a_ao.hw,
[RPMH_IPA_CLK] = &clk_rpmh_ipa.hw,
};
static const struct clk_rpmh_desc clk_rpmh_sm4450 = {
.clks = sm4450_rpmh_clocks,
.num_clks = ARRAY_SIZE(sm4450_rpmh_clocks),
};
static struct clk_hw *of_clk_rpmh_hw_get(struct of_phandle_args *clkspec, static struct clk_hw *of_clk_rpmh_hw_get(struct of_phandle_args *clkspec,
void *data) void *data)
{ {
@@ -742,9 +790,64 @@ static struct clk_hw *of_clk_rpmh_hw_get(struct of_phandle_args *clkspec,
return ERR_PTR(-EINVAL); return ERR_PTR(-EINVAL);
} }
if (!rpmh->clks[idx])
return ERR_PTR(-ENOENT);
return rpmh->clks[idx]; return rpmh->clks[idx];
} }
DEFINE_CLK_RPMH_FIXED(pineapple, bi_tcxo, bi_tcxo_ao, xo_pad, xo_pad_ao, 2);
static struct clk_hw *pineapple_rpmh_clocks[] = {
[RPMH_CXO_PAD_CLK] = &clk_rpmh_xo_pad_div2.hw,
[RPMH_CXO_PAD_CLK_A] = &clk_rpmh_xo_pad_div2_ao.hw,
[RPMH_CXO_CLK] = &pineapple_bi_tcxo.hw,
[RPMH_CXO_CLK_A] = &pineapple_bi_tcxo_ao.hw,
[RPMH_LN_BB_CLK1] = &clk_rpmh_clk6_a2.hw,
[RPMH_LN_BB_CLK1_A] = &clk_rpmh_clk6_a2_ao.hw,
[RPMH_LN_BB_CLK2] = &clk_rpmh_clk7_a2.hw,
[RPMH_LN_BB_CLK2_A] = &clk_rpmh_clk7_a2_ao.hw,
[RPMH_LN_BB_CLK3] = &clk_rpmh_clk8_a2.hw,
[RPMH_LN_BB_CLK3_A] = &clk_rpmh_clk8_a2_ao.hw,
[RPMH_RF_CLK1] = &clk_rpmh_rf_clk1_a.hw,
[RPMH_RF_CLK1_A] = &clk_rpmh_rf_clk1_a_ao.hw,
[RPMH_RF_CLK2] = &clk_rpmh_rf_clk2_a.hw,
[RPMH_RF_CLK2_A] = &clk_rpmh_rf_clk2_a_ao.hw,
[RPMH_RF_CLK3] = &clk_rpmh_rf_clk3_a2.hw,
[RPMH_RF_CLK3_A] = &clk_rpmh_rf_clk3_a2_ao.hw,
[RPMH_RF_CLK4] = &clk_rpmh_rf_clk4_a2.hw,
[RPMH_RF_CLK4_A] = &clk_rpmh_rf_clk4_a2_ao.hw,
[RPMH_RF_CLK5] = &clk_rpmh_rf_clk5_a2.hw,
[RPMH_RF_CLK5_A] = &clk_rpmh_rf_clk5_a2_ao.hw,
[RPMH_IPA_CLK] = &clk_rpmh_ipa.hw,
};
static const struct clk_rpmh_desc clk_rpmh_pineapple = {
.clks = pineapple_rpmh_clocks,
.num_clks = ARRAY_SIZE(pineapple_rpmh_clocks),
};
static struct clk_hw *parrot_rpmh_clocks[] = {
[RPMH_CXO_CLK] = &clk_rpmh_bi_tcxo_div4.hw,
[RPMH_CXO_CLK_A] = &clk_rpmh_bi_tcxo_div4_ao.hw,
[RPMH_LN_BB_CLK2] = &clk_rpmh_ln_bb_clk2_a4.hw,
[RPMH_LN_BB_CLK2_A] = &clk_rpmh_ln_bb_clk2_a4_ao.hw,
[RPMH_LN_BB_CLK3] = &clk_rpmh_ln_bb_clk3_a2.hw,
[RPMH_LN_BB_CLK3_A] = &clk_rpmh_ln_bb_clk3_a2_ao.hw,
[RPMH_RF_CLK1] = &clk_rpmh_rf_clk1_a.hw,
[RPMH_RF_CLK1_A] = &clk_rpmh_rf_clk1_a_ao.hw,
[RPMH_RF_CLK2] = &clk_rpmh_rf_clk2_a.hw,
[RPMH_RF_CLK2_A] = &clk_rpmh_rf_clk2_a_ao.hw,
[RPMH_RF_CLK5] = &clk_rpmh_rf_clk5_a.hw,
[RPMH_RF_CLK5_A] = &clk_rpmh_rf_clk5_a_ao.hw,
[RPMH_IPA_CLK] = &clk_rpmh_ipa.hw,
};
static const struct clk_rpmh_desc clk_rpmh_parrot = {
.clks = parrot_rpmh_clocks,
.num_clks = ARRAY_SIZE(parrot_rpmh_clocks),
};
static int clk_rpmh_probe(struct platform_device *pdev) static int clk_rpmh_probe(struct platform_device *pdev)
{ {
struct clk_hw **hw_clks; struct clk_hw **hw_clks;
@@ -769,10 +872,16 @@ static int clk_rpmh_probe(struct platform_device *pdev)
name = hw_clks[i]->init->name; name = hw_clks[i]->init->name;
if (hw_clks[i]->init->ops != &clk_fixed_factor_ops) {
rpmh_clk = to_clk_rpmh(hw_clks[i]); rpmh_clk = to_clk_rpmh(hw_clks[i]);
res_addr = cmd_db_read_addr(rpmh_clk->res_name); res_addr = cmd_db_read_addr(rpmh_clk->res_name);
if (!res_addr) { if (!res_addr) {
dev_err(&pdev->dev, "missing RPMh resource address for %s\n", hw_clks[i] = NULL;
if (rpmh_clk->optional)
continue;
WARN(1, "clk-rpmh: Missing RPMh resource address for %s\n",
rpmh_clk->res_name); rpmh_clk->res_name);
return -ENODEV; return -ENODEV;
} }
@@ -780,8 +889,7 @@ static int clk_rpmh_probe(struct platform_device *pdev)
data = cmd_db_read_aux_data(rpmh_clk->res_name, &aux_data_len); data = cmd_db_read_aux_data(rpmh_clk->res_name, &aux_data_len);
if (IS_ERR(data)) { if (IS_ERR(data)) {
ret = PTR_ERR(data); ret = PTR_ERR(data);
dev_err(&pdev->dev, WARN(1, "clk-rpmh: error reading RPMh aux data for %s (%d)\n",
"error reading RPMh aux data for %s (%d)\n",
rpmh_clk->res_name, ret); rpmh_clk->res_name, ret);
return ret; return ret;
} }
@@ -792,6 +900,7 @@ static int clk_rpmh_probe(struct platform_device *pdev)
rpmh_clk->res_addr += res_addr; rpmh_clk->res_addr += res_addr;
rpmh_clk->dev = &pdev->dev; rpmh_clk->dev = &pdev->dev;
}
ret = devm_clk_hw_register(&pdev->dev, hw_clks[i]); ret = devm_clk_hw_register(&pdev->dev, hw_clks[i]);
if (ret) { if (ret) {
@@ -816,7 +925,6 @@ static int clk_rpmh_probe(struct platform_device *pdev)
static const struct of_device_id clk_rpmh_match_table[] = { static const struct of_device_id clk_rpmh_match_table[] = {
{ .compatible = "qcom,qdu1000-rpmh-clk", .data = &clk_rpmh_qdu1000}, { .compatible = "qcom,qdu1000-rpmh-clk", .data = &clk_rpmh_qdu1000},
{ .compatible = "qcom,sa8775p-rpmh-clk", .data = &clk_rpmh_sa8775p}, { .compatible = "qcom,sa8775p-rpmh-clk", .data = &clk_rpmh_sa8775p},
{ .compatible = "qcom,sar2130p-rpmh-clk", .data = &clk_rpmh_sar2130p},
{ .compatible = "qcom,sc7180-rpmh-clk", .data = &clk_rpmh_sc7180}, { .compatible = "qcom,sc7180-rpmh-clk", .data = &clk_rpmh_sc7180},
{ .compatible = "qcom,sc8180x-rpmh-clk", .data = &clk_rpmh_sc8180x}, { .compatible = "qcom,sc8180x-rpmh-clk", .data = &clk_rpmh_sc8180x},
{ .compatible = "qcom,sc8280xp-rpmh-clk", .data = &clk_rpmh_sc8280xp}, { .compatible = "qcom,sc8280xp-rpmh-clk", .data = &clk_rpmh_sc8280xp},
@@ -825,6 +933,7 @@ static const struct of_device_id clk_rpmh_match_table[] = {
{ .compatible = "qcom,sdx55-rpmh-clk", .data = &clk_rpmh_sdx55}, { .compatible = "qcom,sdx55-rpmh-clk", .data = &clk_rpmh_sdx55},
{ .compatible = "qcom,sdx65-rpmh-clk", .data = &clk_rpmh_sdx65}, { .compatible = "qcom,sdx65-rpmh-clk", .data = &clk_rpmh_sdx65},
{ .compatible = "qcom,sdx75-rpmh-clk", .data = &clk_rpmh_sdx75}, { .compatible = "qcom,sdx75-rpmh-clk", .data = &clk_rpmh_sdx75},
{ .compatible = "qcom,sm4450-rpmh-clk", .data = &clk_rpmh_sm4450},
{ .compatible = "qcom,sm6350-rpmh-clk", .data = &clk_rpmh_sm6350}, { .compatible = "qcom,sm6350-rpmh-clk", .data = &clk_rpmh_sm6350},
{ .compatible = "qcom,sm8150-rpmh-clk", .data = &clk_rpmh_sm8150}, { .compatible = "qcom,sm8150-rpmh-clk", .data = &clk_rpmh_sm8150},
{ .compatible = "qcom,sm8250-rpmh-clk", .data = &clk_rpmh_sm8250}, { .compatible = "qcom,sm8250-rpmh-clk", .data = &clk_rpmh_sm8250},
@@ -832,6 +941,9 @@ static const struct of_device_id clk_rpmh_match_table[] = {
{ .compatible = "qcom,sm8450-rpmh-clk", .data = &clk_rpmh_sm8450}, { .compatible = "qcom,sm8450-rpmh-clk", .data = &clk_rpmh_sm8450},
{ .compatible = "qcom,sm8550-rpmh-clk", .data = &clk_rpmh_sm8550}, { .compatible = "qcom,sm8550-rpmh-clk", .data = &clk_rpmh_sm8550},
{ .compatible = "qcom,sc7280-rpmh-clk", .data = &clk_rpmh_sc7280}, { .compatible = "qcom,sc7280-rpmh-clk", .data = &clk_rpmh_sc7280},
{ .compatible = "qcom,pineapple-rpmh-clk", .data = &clk_rpmh_pineapple},
{ .compatible = "qcom,sun-rpmh-clk", .data = &clk_rpmh_pineapple},
{ .compatible = "qcom,parrot-rpmh-clk", .data = &clk_rpmh_parrot},
{ } { }
}; };
MODULE_DEVICE_TABLE(of, clk_rpmh_match_table); MODULE_DEVICE_TABLE(of, clk_rpmh_match_table);
@@ -857,4 +969,4 @@ static void __exit clk_rpmh_exit(void)
module_exit(clk_rpmh_exit); module_exit(clk_rpmh_exit);
MODULE_DESCRIPTION("QCOM RPMh Clock Driver"); MODULE_DESCRIPTION("QCOM RPMh Clock Driver");
MODULE_LICENSE("GPL v2"); MODULE_LICENSE("GPL");

File diff suppressed because it is too large Load Diff

View File

@@ -1,6 +1,5 @@
// SPDX-License-Identifier: GPL-2.0-only // SPDX-License-Identifier: GPL-2.0-only
/* Copyright (c) 2017, The Linux Foundation. All rights reserved. /* Copyright (c) 2017-2018, The Linux Foundation. All rights reserved. */
*/
#include <linux/bitops.h> #include <linux/bitops.h>
#include <linux/clk.h> #include <linux/clk.h>
@@ -204,6 +203,7 @@ static int spmi_pmic_clkdiv_probe(struct platform_device *pdev)
struct regmap *regmap; struct regmap *regmap;
struct device *dev = &pdev->dev; struct device *dev = &pdev->dev;
struct device_node *of_node = dev->of_node; struct device_node *of_node = dev->of_node;
bool use_dt_name = false;
struct clk_parent_data parent_data = { .index = 0, }; struct clk_parent_data parent_data = { .index = 0, };
int nclks, i, ret, cxo_hz; int nclks, i, ret, cxo_hz;
char name[20]; char name[20];
@@ -245,6 +245,13 @@ static int spmi_pmic_clkdiv_probe(struct platform_device *pdev)
} }
cxo_hz = clk_get_rate(cxo); cxo_hz = clk_get_rate(cxo);
clk_put(cxo); clk_put(cxo);
if (cxo_hz <= 0) {
dev_err(dev, "invalid CXO rate: %d\n", cxo_hz);
return -EINVAL;
}
if (of_find_property(of_node, "clock-output-names", NULL))
use_dt_name = true;
init.name = name; init.name = name;
init.parent_data = &parent_data; init.parent_data = &parent_data;
@@ -252,7 +259,17 @@ static int spmi_pmic_clkdiv_probe(struct platform_device *pdev)
init.ops = &clk_spmi_pmic_div_ops; init.ops = &clk_spmi_pmic_div_ops;
for (i = 0, clkdiv = cc->clks; i < nclks; i++) { for (i = 0, clkdiv = cc->clks; i < nclks; i++) {
if (use_dt_name) {
ret = of_property_read_string_index(of_node,
"clock-output-names", i, &init.name);
if (ret) {
dev_err(dev, "could not read clock-output-names %d, ret=%d\n",
i, ret);
return ret;
}
} else {
snprintf(name, sizeof(name), "div_clk%d", i + 1); snprintf(name, sizeof(name), "div_clk%d", i + 1);
}
spin_lock_init(&clkdiv[i].lock); spin_lock_init(&clkdiv[i].lock);
clkdiv[i].base = start + i * 0x100; clkdiv[i].base = start + i * 0x100;

View File

@@ -1,6 +1,7 @@
// SPDX-License-Identifier: GPL-2.0 // SPDX-License-Identifier: GPL-2.0-only
/* /*
* Copyright (c) 2013-2014, The Linux Foundation. All rights reserved. * Copyright (c) 2013-2014, 2017-2021, The Linux Foundation. All rights reserved.
* Copyright (c) 2022-2024, Qualcomm Innovation Center, Inc. All rights reserved.
*/ */
#include <linux/export.h> #include <linux/export.h>
@@ -10,19 +11,104 @@
#include <linux/clk-provider.h> #include <linux/clk-provider.h>
#include <linux/reset-controller.h> #include <linux/reset-controller.h>
#include <linux/of.h> #include <linux/of.h>
#include <linux/clk/qcom.h>
#include <linux/clk.h>
#include <linux/interconnect.h>
#include <linux/pm_clock.h>
#include <linux/pm_runtime.h>
#include <linux/mfd/syscon.h>
#include "common.h" #include "common.h"
#include "clk-opp.h"
#include "clk-rcg.h" #include "clk-rcg.h"
#include "clk-regmap.h" #include "clk-regmap.h"
#include "reset.h" #include "reset.h"
#include "gdsc.h" #include "gdsc.h"
#include "vdd-level.h"
#include "clk-debug.h"
struct qcom_cc { struct qcom_cc {
struct qcom_reset_controller reset; struct qcom_reset_controller reset;
struct clk_regmap **rclks; struct clk_regmap **rclks;
size_t num_rclks; size_t num_rclks;
struct clk_hw **clk_hws;
size_t num_clk_hws;
}; };
int qcom_clk_crm_init(struct device *dev, struct clk_crm *crm)
{
char prop_name[32];
if (!crm)
return -EINVAL;
if (!crm->initialized) {
snprintf(prop_name, sizeof(prop_name), "qcom,%s-crmc", crm->name);
if (of_find_property(dev->of_node, prop_name, NULL)) {
crm->regmap_crmc =
syscon_regmap_lookup_by_phandle(dev->of_node,
prop_name);
if (IS_ERR(crm->regmap_crmc)) {
dev_err(dev, "%s regmap error\n", prop_name);
return PTR_ERR(crm->regmap_crmc);
}
}
if (crm->name) {
crm->dev = crm_get_device(crm->name);
if (IS_ERR(crm->dev)) {
pr_err("%s Failed to get crm dev=%s, ret=%ld\n",
__func__, crm->name, PTR_ERR(crm->dev));
return PTR_ERR(crm->dev);
}
}
/*
* Until all targets and instances have updated to explicitly
* specify this, use the most common default value by default.
*/
if (!crm->num_perf_ol)
crm->num_perf_ol = 8;
crm->initialized = true;
}
return 0;
}
EXPORT_SYMBOL(qcom_clk_crm_init);
static int qcom_find_freq_index(const struct freq_tbl *f, unsigned long rate)
{
int index;
for (index = 0; f->freq; f++, index++) {
if (rate <= f->freq)
return index;
}
return index - 1;
}
int qcom_find_crm_freq_index(const struct freq_tbl *f, unsigned long rate)
{
if (!f || !f->freq)
return -EINVAL;
/*
* If rate is 0 return PERF_OL 0 index
*/
if (!rate)
return 0;
/*
* Return PERF_OL index + 1 as PERF_OL 0 is
* treated as CLK OFF as per LUT population
*/
return qcom_find_freq_index(f, rate) + 1;
}
EXPORT_SYMBOL(qcom_find_crm_freq_index);
const const
struct freq_tbl *qcom_find_freq(const struct freq_tbl *f, unsigned long rate) struct freq_tbl *qcom_find_freq(const struct freq_tbl *f, unsigned long rate)
{ {
@@ -220,12 +306,61 @@ static void qcom_cc_drop_protected(struct device *dev, struct qcom_cc *cc)
} }
} }
/* Set QCOM_CLK_IS_CRITICAL on clocks specified in dt */
static void qcom_cc_set_critical(struct device *dev, struct qcom_cc *cc)
{
struct of_phandle_args args;
struct device_node *np;
struct property *prop;
const __be32 *p;
u32 clock_idx;
u32 i;
int cnt;
of_property_for_each_u32(dev->of_node, "qcom,critical-clocks", prop, p, i) {
if (i >= cc->num_rclks)
continue;
if (cc->rclks[i])
cc->rclks[i]->flags |= QCOM_CLK_IS_CRITICAL;
}
of_property_for_each_u32(dev->of_node, "qcom,critical-devices", prop, p, i) {
for (np = of_find_node_by_phandle(i); np; np = of_get_parent(np)) {
if (!of_property_read_bool(np, "clocks")) {
of_node_put(np);
continue;
}
cnt = of_count_phandle_with_args(np, "clocks", "#clock-cells");
for (i = 0; i < cnt; i++) {
of_parse_phandle_with_args(np, "clocks", "#clock-cells",
i, &args);
clock_idx = args.args[0];
if (args.np != dev->of_node || clock_idx >= cc->num_rclks)
continue;
if (cc->rclks[clock_idx])
cc->rclks[clock_idx]->flags |= QCOM_CLK_IS_CRITICAL;
of_node_put(args.np);
}
of_node_put(np);
}
}
}
static struct clk_hw *qcom_cc_clk_hw_get(struct of_phandle_args *clkspec, static struct clk_hw *qcom_cc_clk_hw_get(struct of_phandle_args *clkspec,
void *data) void *data)
{ {
struct qcom_cc *cc = data; struct qcom_cc *cc = data;
unsigned int idx = clkspec->args[0]; unsigned int idx = clkspec->args[0];
if (idx < cc->num_clk_hws && cc->clk_hws[idx])
return cc->clk_hws[idx];
if (idx >= cc->num_rclks) { if (idx >= cc->num_rclks) {
pr_err("%s: invalid index %u\n", __func__, idx); pr_err("%s: invalid index %u\n", __func__, idx);
return ERR_PTR(-EINVAL); return ERR_PTR(-EINVAL);
@@ -252,6 +387,7 @@ int qcom_cc_really_probe(struct platform_device *pdev,
return -ENOMEM; return -ENOMEM;
reset = &cc->reset; reset = &cc->reset;
reset->dev = dev;
reset->rcdev.of_node = dev->of_node; reset->rcdev.of_node = dev->of_node;
reset->rcdev.ops = &qcom_reset_ops; reset->rcdev.ops = &qcom_reset_ops;
reset->rcdev.owner = dev->driver->owner; reset->rcdev.owner = dev->driver->owner;
@@ -259,35 +395,53 @@ int qcom_cc_really_probe(struct platform_device *pdev,
reset->regmap = regmap; reset->regmap = regmap;
reset->reset_map = desc->resets; reset->reset_map = desc->resets;
ret = devm_reset_controller_register(dev, &reset->rcdev); ret = clk_regulator_init(&pdev->dev, desc);
if (ret) if (ret)
return ret; return ret;
ret = clk_vdd_proxy_vote(&pdev->dev, desc);
if (ret)
goto deinit_clk_regulator;
if (desc->num_resets) {
ret = devm_reset_controller_register(dev, &reset->rcdev);
if (ret)
goto proxy_unvote;
}
if (desc->gdscs && desc->num_gdscs) { if (desc->gdscs && desc->num_gdscs) {
scd = devm_kzalloc(dev, sizeof(*scd), GFP_KERNEL); scd = devm_kzalloc(dev, sizeof(*scd), GFP_KERNEL);
if (!scd) if (!scd) {
return -ENOMEM; ret = -ENOMEM;
goto proxy_unvote;
}
scd->dev = dev; scd->dev = dev;
scd->scs = desc->gdscs; scd->scs = desc->gdscs;
scd->num = desc->num_gdscs; scd->num = desc->num_gdscs;
ret = gdsc_register(scd, &reset->rcdev, regmap); ret = gdsc_register(scd, &reset->rcdev, regmap);
if (ret) if (ret)
return ret; goto proxy_unvote;
ret = devm_add_action_or_reset(dev, qcom_cc_gdsc_unregister, ret = devm_add_action_or_reset(dev, qcom_cc_gdsc_unregister,
scd); scd);
if (ret) if (ret)
return ret; goto proxy_unvote;
} }
cc->rclks = rclks; cc->rclks = rclks;
cc->num_rclks = num_clks; cc->num_rclks = num_clks;
cc->clk_hws = clk_hws;
cc->num_clk_hws = num_clk_hws;
qcom_cc_drop_protected(dev, cc); qcom_cc_drop_protected(dev, cc);
qcom_cc_set_critical(dev, cc);
for (i = 0; i < num_clk_hws; i++) { for (i = 0; i < num_clk_hws; i++) {
if (!clk_hws[i])
continue;
ret = devm_clk_hw_register(dev, clk_hws[i]); ret = devm_clk_hw_register(dev, clk_hws[i]);
if (ret) if (ret)
return ret; goto proxy_unvote;
} }
for (i = 0; i < num_clks; i++) { for (i = 0; i < num_clks; i++) {
@@ -296,14 +450,30 @@ int qcom_cc_really_probe(struct platform_device *pdev,
ret = devm_clk_register_regmap(dev, rclks[i]); ret = devm_clk_register_regmap(dev, rclks[i]);
if (ret) if (ret)
return ret; goto proxy_unvote;
clk_hw_populate_clock_opp_table(dev->of_node, &rclks[i]->hw);
/*
* Critical clocks are enabled by devm_clk_register_regmap()
* and registration skipped. So remove from rclks so that the
* get() callback returns NULL and client requests are stubbed.
*/
if (rclks[i]->flags & QCOM_CLK_IS_CRITICAL)
rclks[i] = NULL;
} }
ret = devm_of_clk_add_hw_provider(dev, qcom_cc_clk_hw_get, cc); ret = devm_of_clk_add_hw_provider(dev, qcom_cc_clk_hw_get, cc);
if (ret) if (ret)
return ret; goto proxy_unvote;
return 0; return 0;
proxy_unvote:
clk_vdd_proxy_unvote(dev, desc);
deinit_clk_regulator:
clk_regulator_deinit(desc);
return ret;
} }
EXPORT_SYMBOL_GPL(qcom_cc_really_probe); EXPORT_SYMBOL_GPL(qcom_cc_really_probe);
@@ -337,4 +507,242 @@ int qcom_cc_probe_by_index(struct platform_device *pdev, int index,
} }
EXPORT_SYMBOL_GPL(qcom_cc_probe_by_index); EXPORT_SYMBOL_GPL(qcom_cc_probe_by_index);
void qcom_cc_sync_state(struct device *dev, const struct qcom_cc_desc *desc)
{
dev_info(dev, "sync_state\n");
clk_sync_state(dev);
clk_vdd_proxy_unvote(dev, desc);
}
EXPORT_SYMBOL(qcom_cc_sync_state);
int qcom_clk_crm_set_rate(struct clk *clk,
enum crm_drv_type client_type, u32 client_idx,
u32 pwr_st, unsigned long rate)
{
struct clk_hw *hw;
int ret;
if (!clk)
return -EINVAL;
do {
hw = __clk_get_hw(clk);
if (clk_is_regmap_clk(hw)) {
struct clk_regmap *rclk = to_clk_regmap(hw);
if (rclk->ops && rclk->ops->set_crm_rate) {
ret = rclk->ops->set_crm_rate(hw, client_type,
client_idx, pwr_st, rate);
return ret;
}
}
} while ((clk = clk_get_parent(hw->clk)));
return -EINVAL;
}
EXPORT_SYMBOL(qcom_clk_crm_set_rate);
int qcom_clk_crmb_set_rate(struct clk *clk,
enum crm_drv_type client_type, u32 client_idx,
u32 resource_idx, u32 pwr_st, u32 ab_rate, u32 ib_rate)
{
struct clk_hw *hw;
int ret;
if (!clk)
return -EINVAL;
do {
hw = __clk_get_hw(clk);
if (clk_is_regmap_clk(hw)) {
struct clk_regmap *rclk = to_clk_regmap(hw);
if (rclk->ops && rclk->ops->set_crmb_rate) {
ret = rclk->ops->set_crmb_rate(hw, client_type,
client_idx, resource_idx, pwr_st,
ab_rate, ib_rate);
return ret;
}
}
} while ((clk = clk_get_parent(hw->clk)));
return -EINVAL;
}
EXPORT_SYMBOL_GPL(qcom_clk_crmb_set_rate);
int qcom_clk_get_voltage(struct clk *clk, unsigned long rate)
{
struct clk_regmap *rclk;
struct clk_hw *hw = __clk_get_hw(clk);
int vdd_level;
if (!clk_is_regmap_clk(hw))
return -EINVAL;
rclk = to_clk_regmap(hw);
vdd_level = clk_find_vdd_level(hw, &rclk->vdd_data, rate);
if (vdd_level < 0)
return vdd_level;
return clk_get_vdd_voltage(&rclk->vdd_data, vdd_level);
}
EXPORT_SYMBOL(qcom_clk_get_voltage);
int qcom_clk_set_flags(struct clk *clk, unsigned long flags)
{
struct clk_regmap *rclk;
struct clk_hw *hw;
if (IS_ERR_OR_NULL(clk))
return 0;
hw = __clk_get_hw(clk);
if (IS_ERR_OR_NULL(hw))
return -EINVAL;
if (!clk_is_regmap_clk(hw))
return -EINVAL;
rclk = to_clk_regmap(hw);
if (rclk->ops && rclk->ops->set_flags)
return rclk->ops->set_flags(hw, flags);
return 0;
}
EXPORT_SYMBOL(qcom_clk_set_flags);
int qcom_cc_runtime_init(struct platform_device *pdev,
struct qcom_cc_desc *desc)
{
struct device *dev = &pdev->dev;
struct clk *clk;
int ret;
clk = clk_get_optional(dev, "iface");
if (IS_ERR(clk)) {
if (PTR_ERR(clk) != -EPROBE_DEFER)
dev_err(dev, "unable to get iface clock\n");
return PTR_ERR(clk);
}
clk_put(clk);
ret = clk_regulator_init(dev, desc);
if (ret)
return ret;
desc->path = of_icc_get(dev, NULL);
if (IS_ERR(desc->path)) {
if (PTR_ERR(desc->path) != -EPROBE_DEFER)
dev_err(dev, "error getting path\n");
ret = PTR_ERR(desc->path);
goto deinit_clk_regulator;
}
platform_set_drvdata(pdev, desc);
pm_runtime_enable(dev);
ret = pm_clk_create(dev);
if (ret)
goto disable_pm_runtime;
ret = pm_clk_add(dev, "iface");
if (ret < 0) {
dev_err(dev, "failed to acquire iface clock\n");
goto destroy_pm_clk;
}
return 0;
destroy_pm_clk:
pm_clk_destroy(dev);
disable_pm_runtime:
pm_runtime_disable(dev);
icc_put(desc->path);
deinit_clk_regulator:
clk_regulator_deinit(desc);
return ret;
}
EXPORT_SYMBOL(qcom_cc_runtime_init);
int qcom_cc_runtime_resume(struct device *dev)
{
struct qcom_cc_desc *desc = dev_get_drvdata(dev);
struct clk_vdd_class_data vdd_data = {0};
int ret;
int i;
for (i = 0; i < desc->num_clk_regulators; i++) {
vdd_data.vdd_class = desc->clk_regulators[i];
if (!vdd_data.vdd_class)
continue;
ret = clk_vote_vdd_level(&vdd_data, 1);
if (ret) {
dev_warn(dev, "%s: failed to vote voltage\n", __func__);
return ret;
}
}
if (desc->path) {
ret = icc_set_bw(desc->path, 0, 1);
if (ret) {
dev_warn(dev, "%s: failed to vote bw\n", __func__);
return ret;
}
}
ret = pm_clk_resume(dev);
if (ret)
dev_warn(dev, "%s: failed to enable clocks\n", __func__);
return ret;
}
EXPORT_SYMBOL(qcom_cc_runtime_resume);
int qcom_cc_runtime_suspend(struct device *dev)
{
struct qcom_cc_desc *desc = dev_get_drvdata(dev);
struct clk_vdd_class_data vdd_data = {0};
int ret;
int i;
ret = pm_clk_suspend(dev);
if (ret)
dev_warn(dev, "%s: failed to disable clocks\n", __func__);
if (desc->path) {
ret = icc_set_bw(desc->path, 0, 0);
if (ret)
dev_warn(dev, "%s: failed to unvote bw\n", __func__);
}
for (i = 0; i < desc->num_clk_regulators; i++) {
vdd_data.vdd_class = desc->clk_regulators[i];
if (!vdd_data.vdd_class)
continue;
ret = clk_unvote_vdd_level(&vdd_data, 1);
if (ret)
dev_warn(dev, "%s: failed to unvote voltage\n",
__func__);
}
return 0;
}
EXPORT_SYMBOL(qcom_cc_runtime_suspend);
static void __exit qcom_clk_exit(void)
{
clk_debug_exit();
}
module_exit(qcom_clk_exit);
MODULE_DESCRIPTION("Common QCOM clock control library");
MODULE_LICENSE("GPL v2"); MODULE_LICENSE("GPL v2");

View File

@@ -1,9 +1,12 @@
/* SPDX-License-Identifier: GPL-2.0 */ /* SPDX-License-Identifier: GPL-2.0-only */
/* Copyright (c) 2014, The Linux Foundation. All rights reserved. */ /* Copyright (c) 2014, 2018-2020, The Linux Foundation. All rights reserved. */
/* Copyright (c) 2022-2024, Qualcomm Innovation Center, Inc. All rights reserved. */
#ifndef __QCOM_CLK_COMMON_H__ #ifndef __QCOM_CLK_COMMON_H__
#define __QCOM_CLK_COMMON_H__ #define __QCOM_CLK_COMMON_H__
#include <linux/reset-controller.h>
struct platform_device; struct platform_device;
struct regmap_config; struct regmap_config;
struct clk_regmap; struct clk_regmap;
@@ -19,9 +22,21 @@ struct clk_hw;
#define PLL_VOTE_FSM_ENA BIT(20) #define PLL_VOTE_FSM_ENA BIT(20)
#define PLL_VOTE_FSM_RESET BIT(21) #define PLL_VOTE_FSM_RESET BIT(21)
/**
* struct critical_clk_offset - list the critical clks for each clk controller
* @offset: offset address for critical clk
* @mask: enable mask for critical clk
*/
struct critical_clk_offset {
unsigned int offset;
unsigned int mask;
};
struct qcom_cc_desc { struct qcom_cc_desc {
const struct regmap_config *config; const struct regmap_config *config;
struct clk_regmap **clks; struct clk_regmap **clks;
struct critical_clk_offset *critical_clk_en;
size_t num_critical_clk;
size_t num_clks; size_t num_clks;
const struct qcom_reset_map *resets; const struct qcom_reset_map *resets;
size_t num_resets; size_t num_resets;
@@ -29,6 +44,9 @@ struct qcom_cc_desc {
size_t num_gdscs; size_t num_gdscs;
struct clk_hw **clk_hws; struct clk_hw **clk_hws;
size_t num_clk_hws; size_t num_clk_hws;
struct clk_vdd_class **clk_regulators;
size_t num_clk_regulators;
struct icc_path *path;
}; };
/** /**
@@ -41,10 +59,46 @@ struct parent_map {
u8 cfg; u8 cfg;
}; };
struct clk_dummy {
struct clk_hw hw;
struct reset_controller_dev reset;
unsigned long rrate;
};
struct crm_regs {
u32 cfg_rcgr;
u32 l_val;
u32 curr_perf;
};
struct crm_offsets {
u32 vcd;
u32 level;
};
/**
* struct clk_crm - clk crm
*
* @crm_name: crm instance name
* @regmap_crmc: corresponds to crmc instance
* @crm_dev: crm dev
* @crm_initialized: crm init flag
*/
struct clk_crm {
const char *name;
struct regmap *regmap_crmc;
const struct device *dev;
struct crm_regs regs;
struct crm_offsets offsets;
bool initialized;
u8 num_perf_ol;
};
extern const struct freq_tbl *qcom_find_freq(const struct freq_tbl *f, extern const struct freq_tbl *qcom_find_freq(const struct freq_tbl *f,
unsigned long rate); unsigned long rate);
extern const struct freq_tbl *qcom_find_freq_floor(const struct freq_tbl *f, extern const struct freq_tbl *qcom_find_freq_floor(const struct freq_tbl *f,
unsigned long rate); unsigned long rate);
int qcom_find_crm_freq_index(const struct freq_tbl *f, unsigned long rate);
extern void extern void
qcom_pll_set_fsm_mode(struct regmap *m, u32 reg, u8 bias_count, u8 lock_count); qcom_pll_set_fsm_mode(struct regmap *m, u32 reg, u8 bias_count, u8 lock_count);
extern int qcom_find_src_index(struct clk_hw *hw, const struct parent_map *map, extern int qcom_find_src_index(struct clk_hw *hw, const struct parent_map *map,
@@ -65,5 +119,17 @@ extern int qcom_cc_probe(struct platform_device *pdev,
const struct qcom_cc_desc *desc); const struct qcom_cc_desc *desc);
extern int qcom_cc_probe_by_index(struct platform_device *pdev, int index, extern int qcom_cc_probe_by_index(struct platform_device *pdev, int index,
const struct qcom_cc_desc *desc); const struct qcom_cc_desc *desc);
extern const struct clk_ops clk_dummy_ops;
void qcom_cc_sync_state(struct device *dev, const struct qcom_cc_desc *desc);
int qcom_cc_runtime_init(struct platform_device *pdev,
struct qcom_cc_desc *desc);
int qcom_cc_runtime_suspend(struct device *dev);
int qcom_cc_runtime_resume(struct device *dev);
int qcom_clk_crm_init(struct device *dev, struct clk_crm *crm);
static inline const char *qcom_clk_hw_get_name(const struct clk_hw *hw)
{
return hw->init ? hw->init->name : clk_hw_get_name(hw);
}
#endif #endif

0
drivers/clk/qcom/debugcc-monaco.c Executable file → Normal file
View File

0
drivers/clk/qcom/debugcc-parrot.c Executable file → Normal file
View File

0
drivers/clk/qcom/debugcc-pineapple.c Executable file → Normal file
View File

0
drivers/clk/qcom/debugcc-sdx75.c Executable file → Normal file
View File

0
drivers/clk/qcom/debugcc-sm4450.c Executable file → Normal file
View File

0
drivers/clk/qcom/debugcc-sun.c Executable file → Normal file
View File

0
drivers/clk/qcom/dispcc-monaco.c Executable file → Normal file
View File

0
drivers/clk/qcom/dispcc-parrot.c Executable file → Normal file
View File

0
drivers/clk/qcom/dispcc-pineapple.c Executable file → Normal file
View File

View File

@@ -3,6 +3,7 @@
* Copyright (c) 2018-2019, The Linux Foundation. All rights reserved. * Copyright (c) 2018-2019, The Linux Foundation. All rights reserved.
*/ */
#include <linux/clk.h>
#include <linux/clk-provider.h> #include <linux/clk-provider.h>
#include <linux/module.h> #include <linux/module.h>
#include <linux/platform_device.h> #include <linux/platform_device.h>
@@ -871,6 +872,7 @@ static struct platform_driver disp_cc_sdm845_driver = {
.driver = { .driver = {
.name = "disp_cc-sdm845", .name = "disp_cc-sdm845",
.of_match_table = disp_cc_sdm845_match_table, .of_match_table = disp_cc_sdm845_match_table,
.sync_state = clk_sync_state,
}, },
}; };

0
drivers/clk/qcom/dispcc-sm4450.c Executable file → Normal file
View File

View File

@@ -187,12 +187,13 @@ static struct clk_rcg2 disp_cc_mdss_dp_aux_clk_src = {
.cmd_rcgr = 0x1144, .cmd_rcgr = 0x1144,
.mnd_width = 0, .mnd_width = 0,
.hid_width = 5, .hid_width = 5,
.parent_map = disp_cc_parent_map_6,
.freq_tbl = ftbl_disp_cc_mdss_dp_aux_clk_src, .freq_tbl = ftbl_disp_cc_mdss_dp_aux_clk_src,
.clkr.hw.init = &(struct clk_init_data){ .clkr.hw.init = &(struct clk_init_data){
.name = "disp_cc_mdss_dp_aux_clk_src", .name = "disp_cc_mdss_dp_aux_clk_src",
.parent_data = disp_cc_parent_data_6, .parent_data = &(const struct clk_parent_data){
.num_parents = ARRAY_SIZE(disp_cc_parent_data_6), .fw_name = "bi_tcxo",
},
.num_parents = 1,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -220,17 +221,26 @@ static struct clk_rcg2 disp_cc_mdss_dp_crypto_clk_src = {
}, },
}; };
static const struct freq_tbl ftbl_disp_cc_mdss_dp_link_clk_src[] = {
F(162000, P_DP_PHY_PLL_LINK_CLK, 1, 0, 0),
F(270000, P_DP_PHY_PLL_LINK_CLK, 1, 0, 0),
F(540000, P_DP_PHY_PLL_LINK_CLK, 1, 0, 0),
F(810000, P_DP_PHY_PLL_LINK_CLK, 1, 0, 0),
{ }
};
static struct clk_rcg2 disp_cc_mdss_dp_link_clk_src = { static struct clk_rcg2 disp_cc_mdss_dp_link_clk_src = {
.cmd_rcgr = 0x10f8, .cmd_rcgr = 0x10f8,
.mnd_width = 0, .mnd_width = 0,
.hid_width = 5, .hid_width = 5,
.parent_map = disp_cc_parent_map_0, .parent_map = disp_cc_parent_map_0,
.freq_tbl = ftbl_disp_cc_mdss_dp_link_clk_src,
.clkr.hw.init = &(struct clk_init_data){ .clkr.hw.init = &(struct clk_init_data){
.name = "disp_cc_mdss_dp_link_clk_src", .name = "disp_cc_mdss_dp_link_clk_src",
.parent_data = disp_cc_parent_data_0, .parent_data = disp_cc_parent_data_0,
.num_parents = ARRAY_SIZE(disp_cc_parent_data_0), .num_parents = ARRAY_SIZE(disp_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT | CLK_GET_RATE_NOCACHE, .flags = CLK_SET_RATE_PARENT | CLK_GET_RATE_NOCACHE,
.ops = &clk_byte2_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -680,9 +690,6 @@ static struct clk_branch disp_cc_xo_clk = {
static struct gdsc mdss_gdsc = { static struct gdsc mdss_gdsc = {
.gdscr = 0x1004, .gdscr = 0x1004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "mdss_gdsc", .name = "mdss_gdsc",
}, },

View File

@@ -851,7 +851,6 @@ static struct clk_branch disp_cc_mdss_dp_link1_intf_clk = {
&disp_cc_mdss_dp_link1_div_clk_src.clkr.hw, &disp_cc_mdss_dp_link1_div_clk_src.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.flags = CLK_SET_RATE_PARENT,
.ops = &clk_branch2_ops, .ops = &clk_branch2_ops,
}, },
}, },
@@ -887,7 +886,6 @@ static struct clk_branch disp_cc_mdss_dp_link_intf_clk = {
&disp_cc_mdss_dp_link_div_clk_src.clkr.hw, &disp_cc_mdss_dp_link_div_clk_src.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.flags = CLK_SET_RATE_PARENT,
.ops = &clk_branch2_ops, .ops = &clk_branch2_ops,
}, },
}, },
@@ -1013,7 +1011,6 @@ static struct clk_branch disp_cc_mdss_mdp_lut_clk = {
&disp_cc_mdss_mdp_clk_src.clkr.hw, &disp_cc_mdss_mdp_clk_src.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.flags = CLK_SET_RATE_PARENT,
.ops = &clk_branch2_ops, .ops = &clk_branch2_ops,
}, },
}, },
@@ -1362,13 +1359,8 @@ static int disp_cc_sm8250_probe(struct platform_device *pdev)
disp_cc_sm8250_clocks[DISP_CC_MDSS_EDP_GTC_CLK_SRC] = NULL; disp_cc_sm8250_clocks[DISP_CC_MDSS_EDP_GTC_CLK_SRC] = NULL;
} }
if (of_device_is_compatible(pdev->dev.of_node, "qcom,sm8350-dispcc")) {
clk_lucid_5lpe_pll_configure(&disp_cc_pll0, regmap, &disp_cc_pll0_config);
clk_lucid_5lpe_pll_configure(&disp_cc_pll1, regmap, &disp_cc_pll1_config);
} else {
clk_lucid_pll_configure(&disp_cc_pll0, regmap, &disp_cc_pll0_config); clk_lucid_pll_configure(&disp_cc_pll0, regmap, &disp_cc_pll0_config);
clk_lucid_pll_configure(&disp_cc_pll1, regmap, &disp_cc_pll1_config); clk_lucid_pll_configure(&disp_cc_pll1, regmap, &disp_cc_pll1_config);
}
/* Enable clock gating for MDP clocks */ /* Enable clock gating for MDP clocks */
regmap_update_bits(regmap, 0x8000, 0x10, 0x10); regmap_update_bits(regmap, 0x8000, 0x10, 0x10);

View File

@@ -309,17 +309,26 @@ static struct clk_rcg2 disp_cc_mdss_dptx0_aux_clk_src = {
}, },
}; };
static const struct freq_tbl ftbl_disp_cc_mdss_dptx0_link_clk_src[] = {
F(162000, P_DP0_PHY_PLL_LINK_CLK, 1, 0, 0),
F(270000, P_DP0_PHY_PLL_LINK_CLK, 1, 0, 0),
F(540000, P_DP0_PHY_PLL_LINK_CLK, 1, 0, 0),
F(810000, P_DP0_PHY_PLL_LINK_CLK, 1, 0, 0),
{ }
};
static struct clk_rcg2 disp_cc_mdss_dptx0_link_clk_src = { static struct clk_rcg2 disp_cc_mdss_dptx0_link_clk_src = {
.cmd_rcgr = 0x819c, .cmd_rcgr = 0x819c,
.mnd_width = 0, .mnd_width = 0,
.hid_width = 5, .hid_width = 5,
.parent_map = disp_cc_parent_map_3, .parent_map = disp_cc_parent_map_3,
.freq_tbl = ftbl_disp_cc_mdss_dptx0_link_clk_src,
.clkr.hw.init = &(struct clk_init_data) { .clkr.hw.init = &(struct clk_init_data) {
.name = "disp_cc_mdss_dptx0_link_clk_src", .name = "disp_cc_mdss_dptx0_link_clk_src",
.parent_data = disp_cc_parent_data_3, .parent_data = disp_cc_parent_data_3,
.num_parents = ARRAY_SIZE(disp_cc_parent_data_3), .num_parents = ARRAY_SIZE(disp_cc_parent_data_3),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_byte2_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -373,12 +382,13 @@ static struct clk_rcg2 disp_cc_mdss_dptx1_link_clk_src = {
.mnd_width = 0, .mnd_width = 0,
.hid_width = 5, .hid_width = 5,
.parent_map = disp_cc_parent_map_3, .parent_map = disp_cc_parent_map_3,
.freq_tbl = ftbl_disp_cc_mdss_dptx0_link_clk_src,
.clkr.hw.init = &(struct clk_init_data) { .clkr.hw.init = &(struct clk_init_data) {
.name = "disp_cc_mdss_dptx1_link_clk_src", .name = "disp_cc_mdss_dptx1_link_clk_src",
.parent_data = disp_cc_parent_data_3, .parent_data = disp_cc_parent_data_3,
.num_parents = ARRAY_SIZE(disp_cc_parent_data_3), .num_parents = ARRAY_SIZE(disp_cc_parent_data_3),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_byte2_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -432,12 +442,13 @@ static struct clk_rcg2 disp_cc_mdss_dptx2_link_clk_src = {
.mnd_width = 0, .mnd_width = 0,
.hid_width = 5, .hid_width = 5,
.parent_map = disp_cc_parent_map_3, .parent_map = disp_cc_parent_map_3,
.freq_tbl = ftbl_disp_cc_mdss_dptx0_link_clk_src,
.clkr.hw.init = &(struct clk_init_data) { .clkr.hw.init = &(struct clk_init_data) {
.name = "disp_cc_mdss_dptx2_link_clk_src", .name = "disp_cc_mdss_dptx2_link_clk_src",
.parent_data = disp_cc_parent_data_3, .parent_data = disp_cc_parent_data_3,
.num_parents = ARRAY_SIZE(disp_cc_parent_data_3), .num_parents = ARRAY_SIZE(disp_cc_parent_data_3),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_byte2_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -491,12 +502,13 @@ static struct clk_rcg2 disp_cc_mdss_dptx3_link_clk_src = {
.mnd_width = 0, .mnd_width = 0,
.hid_width = 5, .hid_width = 5,
.parent_map = disp_cc_parent_map_3, .parent_map = disp_cc_parent_map_3,
.freq_tbl = ftbl_disp_cc_mdss_dptx0_link_clk_src,
.clkr.hw.init = &(struct clk_init_data) { .clkr.hw.init = &(struct clk_init_data) {
.name = "disp_cc_mdss_dptx3_link_clk_src", .name = "disp_cc_mdss_dptx3_link_clk_src",
.parent_data = disp_cc_parent_data_3, .parent_data = disp_cc_parent_data_3,
.num_parents = ARRAY_SIZE(disp_cc_parent_data_3), .num_parents = ARRAY_SIZE(disp_cc_parent_data_3),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_byte2_ops, .ops = &clk_rcg2_ops,
}, },
}; };

View File

@@ -196,7 +196,7 @@ static const struct clk_parent_data disp_cc_parent_data_3[] = {
static const struct parent_map disp_cc_parent_map_4[] = { static const struct parent_map disp_cc_parent_map_4[] = {
{ P_BI_TCXO, 0 }, { P_BI_TCXO, 0 },
{ P_DP0_PHY_PLL_LINK_CLK, 1 }, { P_DP0_PHY_PLL_LINK_CLK, 1 },
{ P_DP0_PHY_PLL_VCO_DIV_CLK, 2 }, { P_DP1_PHY_PLL_VCO_DIV_CLK, 2 },
{ P_DP3_PHY_PLL_VCO_DIV_CLK, 3 }, { P_DP3_PHY_PLL_VCO_DIV_CLK, 3 },
{ P_DP1_PHY_PLL_VCO_DIV_CLK, 4 }, { P_DP1_PHY_PLL_VCO_DIV_CLK, 4 },
{ P_DP2_PHY_PLL_VCO_DIV_CLK, 6 }, { P_DP2_PHY_PLL_VCO_DIV_CLK, 6 },
@@ -213,7 +213,7 @@ static const struct clk_parent_data disp_cc_parent_data_4[] = {
static const struct parent_map disp_cc_parent_map_5[] = { static const struct parent_map disp_cc_parent_map_5[] = {
{ P_BI_TCXO, 0 }, { P_BI_TCXO, 0 },
{ P_DSI0_PHY_PLL_OUT_BYTECLK, 2 }, { P_DSI0_PHY_PLL_OUT_BYTECLK, 4 },
{ P_DSI1_PHY_PLL_OUT_BYTECLK, 4 }, { P_DSI1_PHY_PLL_OUT_BYTECLK, 4 },
}; };
@@ -345,17 +345,26 @@ static struct clk_rcg2 disp_cc_mdss_dptx0_aux_clk_src = {
}, },
}; };
static const struct freq_tbl ftbl_disp_cc_mdss_dptx0_link_clk_src[] = {
F(162000, P_DP0_PHY_PLL_LINK_CLK, 1, 0, 0),
F(270000, P_DP0_PHY_PLL_LINK_CLK, 1, 0, 0),
F(540000, P_DP0_PHY_PLL_LINK_CLK, 1, 0, 0),
F(810000, P_DP0_PHY_PLL_LINK_CLK, 1, 0, 0),
{ }
};
static struct clk_rcg2 disp_cc_mdss_dptx0_link_clk_src = { static struct clk_rcg2 disp_cc_mdss_dptx0_link_clk_src = {
.cmd_rcgr = 0x8170, .cmd_rcgr = 0x8170,
.mnd_width = 0, .mnd_width = 0,
.hid_width = 5, .hid_width = 5,
.parent_map = disp_cc_parent_map_7, .parent_map = disp_cc_parent_map_7,
.freq_tbl = ftbl_disp_cc_mdss_dptx0_link_clk_src,
.clkr.hw.init = &(struct clk_init_data) { .clkr.hw.init = &(struct clk_init_data) {
.name = "disp_cc_mdss_dptx0_link_clk_src", .name = "disp_cc_mdss_dptx0_link_clk_src",
.parent_data = disp_cc_parent_data_7, .parent_data = disp_cc_parent_data_7,
.num_parents = ARRAY_SIZE(disp_cc_parent_data_7), .num_parents = ARRAY_SIZE(disp_cc_parent_data_7),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_byte2_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -400,7 +409,7 @@ static struct clk_rcg2 disp_cc_mdss_dptx1_aux_clk_src = {
.parent_data = disp_cc_parent_data_0, .parent_data = disp_cc_parent_data_0,
.num_parents = ARRAY_SIZE(disp_cc_parent_data_0), .num_parents = ARRAY_SIZE(disp_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_dp_ops,
}, },
}; };
@@ -409,12 +418,13 @@ static struct clk_rcg2 disp_cc_mdss_dptx1_link_clk_src = {
.mnd_width = 0, .mnd_width = 0,
.hid_width = 5, .hid_width = 5,
.parent_map = disp_cc_parent_map_3, .parent_map = disp_cc_parent_map_3,
.freq_tbl = ftbl_disp_cc_mdss_dptx0_link_clk_src,
.clkr.hw.init = &(struct clk_init_data) { .clkr.hw.init = &(struct clk_init_data) {
.name = "disp_cc_mdss_dptx1_link_clk_src", .name = "disp_cc_mdss_dptx1_link_clk_src",
.parent_data = disp_cc_parent_data_3, .parent_data = disp_cc_parent_data_3,
.num_parents = ARRAY_SIZE(disp_cc_parent_data_3), .num_parents = ARRAY_SIZE(disp_cc_parent_data_3),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_byte2_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -468,12 +478,13 @@ static struct clk_rcg2 disp_cc_mdss_dptx2_link_clk_src = {
.mnd_width = 0, .mnd_width = 0,
.hid_width = 5, .hid_width = 5,
.parent_map = disp_cc_parent_map_3, .parent_map = disp_cc_parent_map_3,
.freq_tbl = ftbl_disp_cc_mdss_dptx0_link_clk_src,
.clkr.hw.init = &(struct clk_init_data) { .clkr.hw.init = &(struct clk_init_data) {
.name = "disp_cc_mdss_dptx2_link_clk_src", .name = "disp_cc_mdss_dptx2_link_clk_src",
.parent_data = disp_cc_parent_data_3, .parent_data = disp_cc_parent_data_3,
.num_parents = ARRAY_SIZE(disp_cc_parent_data_3), .num_parents = ARRAY_SIZE(disp_cc_parent_data_3),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_byte2_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -527,12 +538,13 @@ static struct clk_rcg2 disp_cc_mdss_dptx3_link_clk_src = {
.mnd_width = 0, .mnd_width = 0,
.hid_width = 5, .hid_width = 5,
.parent_map = disp_cc_parent_map_3, .parent_map = disp_cc_parent_map_3,
.freq_tbl = ftbl_disp_cc_mdss_dptx0_link_clk_src,
.clkr.hw.init = &(struct clk_init_data) { .clkr.hw.init = &(struct clk_init_data) {
.name = "disp_cc_mdss_dptx3_link_clk_src", .name = "disp_cc_mdss_dptx3_link_clk_src",
.parent_data = disp_cc_parent_data_3, .parent_data = disp_cc_parent_data_3,
.num_parents = ARRAY_SIZE(disp_cc_parent_data_3), .num_parents = ARRAY_SIZE(disp_cc_parent_data_3),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_byte2_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -562,7 +574,7 @@ static struct clk_rcg2 disp_cc_mdss_esc0_clk_src = {
.parent_data = disp_cc_parent_data_5, .parent_data = disp_cc_parent_data_5,
.num_parents = ARRAY_SIZE(disp_cc_parent_data_5), .num_parents = ARRAY_SIZE(disp_cc_parent_data_5),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -577,7 +589,7 @@ static struct clk_rcg2 disp_cc_mdss_esc1_clk_src = {
.parent_data = disp_cc_parent_data_5, .parent_data = disp_cc_parent_data_5,
.num_parents = ARRAY_SIZE(disp_cc_parent_data_5), .num_parents = ARRAY_SIZE(disp_cc_parent_data_5),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -1611,7 +1623,7 @@ static struct gdsc mdss_gdsc = {
.name = "mdss_gdsc", .name = "mdss_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = POLL_CFG_GDSCR | HW_CTRL | RETAIN_FF_ENABLE, .flags = HW_CTRL | RETAIN_FF_ENABLE,
}; };
static struct gdsc mdss_int2_gdsc = { static struct gdsc mdss_int2_gdsc = {
@@ -1620,7 +1632,7 @@ static struct gdsc mdss_int2_gdsc = {
.name = "mdss_int2_gdsc", .name = "mdss_int2_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = POLL_CFG_GDSCR | HW_CTRL | RETAIN_FF_ENABLE, .flags = HW_CTRL | RETAIN_FF_ENABLE,
}; };
static struct clk_regmap *disp_cc_sm8550_clocks[] = { static struct clk_regmap *disp_cc_sm8550_clocks[] = {

0
drivers/clk/qcom/dispcc-sun.c Executable file → Normal file
View File

0
drivers/clk/qcom/dispcc-tuna.c Executable file → Normal file
View File

0
drivers/clk/qcom/evacc-sun.c Executable file → Normal file
View File

0
drivers/clk/qcom/evacc-tuna.c Executable file → Normal file
View File

View File

@@ -3388,7 +3388,6 @@ static struct clk_regmap *gcc_ipq5332_clocks[] = {
[GCC_QDSS_DAP_DIV_CLK_SRC] = &gcc_qdss_dap_div_clk_src.clkr, [GCC_QDSS_DAP_DIV_CLK_SRC] = &gcc_qdss_dap_div_clk_src.clkr,
[GCC_QDSS_ETR_USB_CLK] = &gcc_qdss_etr_usb_clk.clkr, [GCC_QDSS_ETR_USB_CLK] = &gcc_qdss_etr_usb_clk.clkr,
[GCC_QDSS_EUD_AT_CLK] = &gcc_qdss_eud_at_clk.clkr, [GCC_QDSS_EUD_AT_CLK] = &gcc_qdss_eud_at_clk.clkr,
[GCC_QDSS_TSCTR_CLK_SRC] = &gcc_qdss_tsctr_clk_src.clkr,
[GCC_QPIC_AHB_CLK] = &gcc_qpic_ahb_clk.clkr, [GCC_QPIC_AHB_CLK] = &gcc_qpic_ahb_clk.clkr,
[GCC_QPIC_CLK] = &gcc_qpic_clk.clkr, [GCC_QPIC_CLK] = &gcc_qpic_clk.clkr,
[GCC_QPIC_IO_MACRO_CLK] = &gcc_qpic_io_macro_clk.clkr, [GCC_QPIC_IO_MACRO_CLK] = &gcc_qpic_io_macro_clk.clkr,

View File

@@ -65,7 +65,7 @@ static const struct clk_parent_data gcc_sleep_clk_data[] = {
static struct clk_alpha_pll gpll0_main = { static struct clk_alpha_pll gpll0_main = {
.offset = 0x20000, .offset = 0x20000,
.regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT_EVO], .regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT],
.clkr = { .clkr = {
.enable_reg = 0x0b000, .enable_reg = 0x0b000,
.enable_mask = BIT(0), .enable_mask = BIT(0),
@@ -93,7 +93,7 @@ static struct clk_fixed_factor gpll0_out_main_div2 = {
static struct clk_alpha_pll_postdiv gpll0 = { static struct clk_alpha_pll_postdiv gpll0 = {
.offset = 0x20000, .offset = 0x20000,
.regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT_EVO], .regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT],
.width = 4, .width = 4,
.clkr.hw.init = &(const struct clk_init_data) { .clkr.hw.init = &(const struct clk_init_data) {
.name = "gpll0", .name = "gpll0",
@@ -107,7 +107,7 @@ static struct clk_alpha_pll_postdiv gpll0 = {
static struct clk_alpha_pll gpll4_main = { static struct clk_alpha_pll gpll4_main = {
.offset = 0x22000, .offset = 0x22000,
.regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT_EVO], .regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT],
.clkr = { .clkr = {
.enable_reg = 0x0b000, .enable_reg = 0x0b000,
.enable_mask = BIT(2), .enable_mask = BIT(2),
@@ -122,7 +122,7 @@ static struct clk_alpha_pll gpll4_main = {
static struct clk_alpha_pll_postdiv gpll4 = { static struct clk_alpha_pll_postdiv gpll4 = {
.offset = 0x22000, .offset = 0x22000,
.regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT_EVO], .regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT],
.width = 4, .width = 4,
.clkr.hw.init = &(const struct clk_init_data) { .clkr.hw.init = &(const struct clk_init_data) {
.name = "gpll4", .name = "gpll4",
@@ -136,7 +136,7 @@ static struct clk_alpha_pll_postdiv gpll4 = {
static struct clk_alpha_pll gpll2_main = { static struct clk_alpha_pll gpll2_main = {
.offset = 0x21000, .offset = 0x21000,
.regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT_EVO], .regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT],
.clkr = { .clkr = {
.enable_reg = 0x0b000, .enable_reg = 0x0b000,
.enable_mask = BIT(1), .enable_mask = BIT(1),
@@ -151,7 +151,7 @@ static struct clk_alpha_pll gpll2_main = {
static struct clk_alpha_pll_postdiv gpll2 = { static struct clk_alpha_pll_postdiv gpll2 = {
.offset = 0x21000, .offset = 0x21000,
.regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT_EVO], .regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_DEFAULT],
.width = 4, .width = 4,
.clkr.hw.init = &(const struct clk_init_data) { .clkr.hw.init = &(const struct clk_init_data) {
.name = "gpll2", .name = "gpll2",
@@ -2140,10 +2140,9 @@ static struct clk_rcg2 pcnoc_bfdcd_clk_src = {
static struct clk_branch gcc_crypto_axi_clk = { static struct clk_branch gcc_crypto_axi_clk = {
.halt_reg = 0x16010, .halt_reg = 0x16010,
.halt_check = BRANCH_HALT_VOTED,
.clkr = { .clkr = {
.enable_reg = 0xb004, .enable_reg = 0x16010,
.enable_mask = BIT(15), .enable_mask = BIT(0),
.hw.init = &(const struct clk_init_data) { .hw.init = &(const struct clk_init_data) {
.name = "gcc_crypto_axi_clk", .name = "gcc_crypto_axi_clk",
.parent_hws = (const struct clk_hw *[]) { .parent_hws = (const struct clk_hw *[]) {
@@ -2157,10 +2156,9 @@ static struct clk_branch gcc_crypto_axi_clk = {
static struct clk_branch gcc_crypto_ahb_clk = { static struct clk_branch gcc_crypto_ahb_clk = {
.halt_reg = 0x16014, .halt_reg = 0x16014,
.halt_check = BRANCH_HALT_VOTED,
.clkr = { .clkr = {
.enable_reg = 0xb004, .enable_reg = 0x16014,
.enable_mask = BIT(16), .enable_mask = BIT(0),
.hw.init = &(const struct clk_init_data) { .hw.init = &(const struct clk_init_data) {
.name = "gcc_crypto_ahb_clk", .name = "gcc_crypto_ahb_clk",
.parent_hws = (const struct clk_hw *[]) { .parent_hws = (const struct clk_hw *[]) {

0
drivers/clk/qcom/gcc-kera.c Executable file → Normal file
View File

View File

@@ -535,7 +535,7 @@ static struct clk_rcg2 blsp1_uart5_apps_clk_src = {
}; };
static struct clk_rcg2 blsp1_uart6_apps_clk_src = { static struct clk_rcg2 blsp1_uart6_apps_clk_src = {
.cmd_rcgr = 0x7044, .cmd_rcgr = 0x6044,
.mnd_width = 16, .mnd_width = 16,
.hid_width = 5, .hid_width = 5,
.parent_map = gcc_xo_gpll0_map, .parent_map = gcc_xo_gpll0_map,

0
drivers/clk/qcom/gcc-monaco.c Executable file → Normal file
View File

View File

@@ -432,7 +432,7 @@ static const struct parent_map gcc_xo_gpll0_gpll1a_gpll6_sleep_map[] = {
{ P_XO, 0 }, { P_XO, 0 },
{ P_GPLL0, 1 }, { P_GPLL0, 1 },
{ P_GPLL1_AUX, 2 }, { P_GPLL1_AUX, 2 },
{ P_GPLL6, 3 }, { P_GPLL6, 2 },
{ P_SLEEP_CLK, 6 }, { P_SLEEP_CLK, 6 },
}; };
@@ -1100,7 +1100,7 @@ static struct clk_rcg2 jpeg0_clk_src = {
}; };
static const struct freq_tbl ftbl_gcc_camss_mclk0_1_clk[] = { static const struct freq_tbl ftbl_gcc_camss_mclk0_1_clk[] = {
F(24000000, P_GPLL6, 1, 1, 45), F(24000000, P_GPLL0, 1, 1, 45),
F(66670000, P_GPLL0, 12, 0, 0), F(66670000, P_GPLL0, 12, 0, 0),
{ } { }
}; };

View File

@@ -3770,7 +3770,7 @@ static struct clk_branch gcc_venus0_axi_clk = {
static struct clk_branch gcc_venus0_core0_vcodec0_clk = { static struct clk_branch gcc_venus0_core0_vcodec0_clk = {
.halt_reg = 0x4c02c, .halt_reg = 0x4c02c,
.halt_check = BRANCH_HALT_SKIP, .halt_check = BRANCH_HALT,
.clkr = { .clkr = {
.enable_reg = 0x4c02c, .enable_reg = 0x4c02c,
.enable_mask = BIT(0), .enable_mask = BIT(0),

View File

@@ -3306,6 +3306,7 @@ static struct platform_driver gcc_msm8998_driver = {
.driver = { .driver = {
.name = "gcc-msm8998", .name = "gcc-msm8998",
.of_match_table = gcc_msm8998_match_table, .of_match_table = gcc_msm8998_match_table,
.sync_state = clk_sync_state,
}, },
}; };

0
drivers/clk/qcom/gcc-parrot.c Executable file → Normal file
View File

0
drivers/clk/qcom/gcc-pineapple.c Executable file → Normal file
View File

View File

@@ -131,7 +131,6 @@ static struct clk_alpha_pll gpll1_out_main = {
/* 930MHz configuration */ /* 930MHz configuration */
static const struct alpha_pll_config gpll3_config = { static const struct alpha_pll_config gpll3_config = {
.l = 48, .l = 48,
.alpha_hi = 0x70,
.alpha = 0x0, .alpha = 0x0,
.alpha_en_mask = BIT(24), .alpha_en_mask = BIT(24),
.post_div_mask = 0xf << 8, .post_div_mask = 0xf << 8,

View File

@@ -4305,114 +4305,74 @@ static struct clk_branch gcc_video_axi1_clk = {
static struct gdsc pcie_0_gdsc = { static struct gdsc pcie_0_gdsc = {
.gdscr = 0xa9004, .gdscr = 0xa9004,
.collapse_ctrl = 0x4b104,
.collapse_mask = BIT(0),
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "pcie_0_gdsc", .name = "pcie_0_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = VOTABLE | RETAIN_FF_ENABLE | POLL_CFG_GDSCR,
}; };
static struct gdsc pcie_1_gdsc = { static struct gdsc pcie_1_gdsc = {
.gdscr = 0x77004, .gdscr = 0x77004,
.collapse_ctrl = 0x4b104,
.collapse_mask = BIT(1),
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "pcie_1_gdsc", .name = "pcie_1_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = VOTABLE | RETAIN_FF_ENABLE | POLL_CFG_GDSCR,
}; };
static struct gdsc ufs_card_gdsc = { static struct gdsc ufs_card_gdsc = {
.gdscr = 0x81004, .gdscr = 0x81004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "ufs_card_gdsc", .name = "ufs_card_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = RETAIN_FF_ENABLE | POLL_CFG_GDSCR,
}; };
static struct gdsc ufs_phy_gdsc = { static struct gdsc ufs_phy_gdsc = {
.gdscr = 0x83004, .gdscr = 0x83004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "ufs_phy_gdsc", .name = "ufs_phy_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = RETAIN_FF_ENABLE | POLL_CFG_GDSCR,
}; };
static struct gdsc usb20_prim_gdsc = { static struct gdsc usb20_prim_gdsc = {
.gdscr = 0x1c004, .gdscr = 0x1c004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "usb20_prim_gdsc", .name = "usb20_prim_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = RETAIN_FF_ENABLE | POLL_CFG_GDSCR,
}; };
static struct gdsc usb30_prim_gdsc = { static struct gdsc usb30_prim_gdsc = {
.gdscr = 0x1b004, .gdscr = 0x1b004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "usb30_prim_gdsc", .name = "usb30_prim_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = RETAIN_FF_ENABLE | POLL_CFG_GDSCR,
}; };
static struct gdsc usb30_sec_gdsc = { static struct gdsc usb30_sec_gdsc = {
.gdscr = 0x2f004, .gdscr = 0x2f004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "usb30_sec_gdsc", .name = "usb30_sec_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = RETAIN_FF_ENABLE | POLL_CFG_GDSCR,
}; };
static struct gdsc emac0_gdsc = { static struct gdsc emac0_gdsc = {
.gdscr = 0xb6004, .gdscr = 0xb6004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "emac0_gdsc", .name = "emac0_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = RETAIN_FF_ENABLE | POLL_CFG_GDSCR,
}; };
static struct gdsc emac1_gdsc = { static struct gdsc emac1_gdsc = {
.gdscr = 0xb4004, .gdscr = 0xb4004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "emac1_gdsc", .name = "emac1_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = RETAIN_FF_ENABLE | POLL_CFG_GDSCR,
}; };
static struct clk_regmap *gcc_sa8775p_clocks[] = { static struct clk_regmap *gcc_sa8775p_clocks[] = {

View File

@@ -3467,9 +3467,6 @@ static int gcc_sc7280_probe(struct platform_device *pdev)
regmap_update_bits(regmap, 0x71004, BIT(0), BIT(0)); regmap_update_bits(regmap, 0x71004, BIT(0), BIT(0));
regmap_update_bits(regmap, 0x7100C, BIT(13), BIT(13)); regmap_update_bits(regmap, 0x7100C, BIT(13), BIT(13));
/* FORCE_MEM_CORE_ON for ufs phy ice core clocks */
qcom_branch_set_force_mem_core(regmap, gcc_ufs_phy_ice_core_clk, true);
ret = qcom_cc_register_rcg_dfs(regmap, gcc_dfs_clocks, ret = qcom_cc_register_rcg_dfs(regmap, gcc_dfs_clocks,
ARRAY_SIZE(gcc_dfs_clocks)); ARRAY_SIZE(gcc_dfs_clocks));
if (ret) if (ret)

View File

@@ -142,23 +142,6 @@ static struct clk_alpha_pll gpll7 = {
}, },
}; };
static struct clk_alpha_pll gpll9 = {
.offset = 0x1c000,
.regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_TRION],
.clkr = {
.enable_reg = 0x52000,
.enable_mask = BIT(9),
.hw.init = &(const struct clk_init_data) {
.name = "gpll9",
.parent_data = &(const struct clk_parent_data) {
.fw_name = "bi_tcxo",
},
.num_parents = 1,
.ops = &clk_alpha_pll_fixed_trion_ops,
},
},
};
static const struct parent_map gcc_parent_map_0[] = { static const struct parent_map gcc_parent_map_0[] = {
{ P_BI_TCXO, 0 }, { P_BI_TCXO, 0 },
{ P_GPLL0_OUT_MAIN, 1 }, { P_GPLL0_OUT_MAIN, 1 },
@@ -258,7 +241,7 @@ static const struct parent_map gcc_parent_map_7[] = {
static const struct clk_parent_data gcc_parents_7[] = { static const struct clk_parent_data gcc_parents_7[] = {
{ .fw_name = "bi_tcxo", }, { .fw_name = "bi_tcxo", },
{ .hw = &gpll0.clkr.hw }, { .hw = &gpll0.clkr.hw },
{ .hw = &gpll9.clkr.hw }, { .name = "gppl9" },
{ .hw = &gpll4.clkr.hw }, { .hw = &gpll4.clkr.hw },
{ .hw = &gpll0_out_even.clkr.hw }, { .hw = &gpll0_out_even.clkr.hw },
}; };
@@ -277,6 +260,28 @@ static const struct clk_parent_data gcc_parents_8[] = {
{ .hw = &gpll0_out_even.clkr.hw }, { .hw = &gpll0_out_even.clkr.hw },
}; };
static const struct freq_tbl ftbl_gcc_cpuss_ahb_clk_src[] = {
F(19200000, P_BI_TCXO, 1, 0, 0),
F(50000000, P_GPLL0_OUT_MAIN, 12, 0, 0),
F(100000000, P_GPLL0_OUT_MAIN, 6, 0, 0),
{ }
};
static struct clk_rcg2 gcc_cpuss_ahb_clk_src = {
.cmd_rcgr = 0x48014,
.mnd_width = 0,
.hid_width = 5,
.parent_map = gcc_parent_map_0,
.freq_tbl = ftbl_gcc_cpuss_ahb_clk_src,
.clkr.hw.init = &(struct clk_init_data){
.name = "gcc_cpuss_ahb_clk_src",
.parent_data = gcc_parents_0,
.num_parents = ARRAY_SIZE(gcc_parents_0),
.flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops,
},
};
static const struct freq_tbl ftbl_gcc_emac_ptp_clk_src[] = { static const struct freq_tbl ftbl_gcc_emac_ptp_clk_src[] = {
F(19200000, P_BI_TCXO, 1, 0, 0), F(19200000, P_BI_TCXO, 1, 0, 0),
F(50000000, P_GPLL0_OUT_EVEN, 6, 0, 0), F(50000000, P_GPLL0_OUT_EVEN, 6, 0, 0),
@@ -911,7 +916,7 @@ static const struct freq_tbl ftbl_gcc_sdcc2_apps_clk_src[] = {
F(25000000, P_GPLL0_OUT_MAIN, 12, 1, 2), F(25000000, P_GPLL0_OUT_MAIN, 12, 1, 2),
F(50000000, P_GPLL0_OUT_MAIN, 12, 0, 0), F(50000000, P_GPLL0_OUT_MAIN, 12, 0, 0),
F(100000000, P_GPLL0_OUT_MAIN, 6, 0, 0), F(100000000, P_GPLL0_OUT_MAIN, 6, 0, 0),
F(202000000, P_GPLL9_OUT_MAIN, 4, 0, 0), F(200000000, P_GPLL0_OUT_MAIN, 3, 0, 0),
{ } { }
}; };
@@ -934,8 +939,9 @@ static const struct freq_tbl ftbl_gcc_sdcc4_apps_clk_src[] = {
F(400000, P_BI_TCXO, 12, 1, 4), F(400000, P_BI_TCXO, 12, 1, 4),
F(9600000, P_BI_TCXO, 2, 0, 0), F(9600000, P_BI_TCXO, 2, 0, 0),
F(19200000, P_BI_TCXO, 1, 0, 0), F(19200000, P_BI_TCXO, 1, 0, 0),
F(37500000, P_GPLL0_OUT_MAIN, 16, 0, 0),
F(50000000, P_GPLL0_OUT_MAIN, 12, 0, 0), F(50000000, P_GPLL0_OUT_MAIN, 12, 0, 0),
F(100000000, P_GPLL0_OUT_MAIN, 6, 0, 0), F(75000000, P_GPLL0_OUT_MAIN, 8, 0, 0),
{ } { }
}; };
@@ -1593,6 +1599,25 @@ static struct clk_branch gcc_cfg_noc_usb3_sec_axi_clk = {
}, },
}; };
/* For CPUSS functionality the AHB clock needs to be left enabled */
static struct clk_branch gcc_cpuss_ahb_clk = {
.halt_reg = 0x48000,
.halt_check = BRANCH_HALT_VOTED,
.clkr = {
.enable_reg = 0x52004,
.enable_mask = BIT(21),
.hw.init = &(struct clk_init_data){
.name = "gcc_cpuss_ahb_clk",
.parent_hws = (const struct clk_hw *[]){
&gcc_cpuss_ahb_clk_src.clkr.hw
},
.num_parents = 1,
.flags = CLK_IS_CRITICAL | CLK_SET_RATE_PARENT,
.ops = &clk_branch2_ops,
},
},
};
static struct clk_branch gcc_cpuss_rbcpr_clk = { static struct clk_branch gcc_cpuss_rbcpr_clk = {
.halt_reg = 0x48008, .halt_reg = 0x48008,
.halt_check = BRANCH_HALT, .halt_check = BRANCH_HALT,
@@ -3125,6 +3150,25 @@ static struct clk_branch gcc_sdcc4_apps_clk = {
}, },
}; };
/* For CPUSS functionality the SYS NOC clock needs to be left enabled */
static struct clk_branch gcc_sys_noc_cpuss_ahb_clk = {
.halt_reg = 0x4819c,
.halt_check = BRANCH_HALT_VOTED,
.clkr = {
.enable_reg = 0x52004,
.enable_mask = BIT(0),
.hw.init = &(struct clk_init_data){
.name = "gcc_sys_noc_cpuss_ahb_clk",
.parent_hws = (const struct clk_hw *[]){
&gcc_cpuss_ahb_clk_src.clkr.hw
},
.num_parents = 1,
.flags = CLK_IS_CRITICAL | CLK_SET_RATE_PARENT,
.ops = &clk_branch2_ops,
},
},
};
static struct clk_branch gcc_tsif_ahb_clk = { static struct clk_branch gcc_tsif_ahb_clk = {
.halt_reg = 0x36004, .halt_reg = 0x36004,
.halt_check = BRANCH_HALT, .halt_check = BRANCH_HALT,
@@ -4214,6 +4258,8 @@ static struct clk_regmap *gcc_sc8180x_clocks[] = {
[GCC_CFG_NOC_USB3_MP_AXI_CLK] = &gcc_cfg_noc_usb3_mp_axi_clk.clkr, [GCC_CFG_NOC_USB3_MP_AXI_CLK] = &gcc_cfg_noc_usb3_mp_axi_clk.clkr,
[GCC_CFG_NOC_USB3_PRIM_AXI_CLK] = &gcc_cfg_noc_usb3_prim_axi_clk.clkr, [GCC_CFG_NOC_USB3_PRIM_AXI_CLK] = &gcc_cfg_noc_usb3_prim_axi_clk.clkr,
[GCC_CFG_NOC_USB3_SEC_AXI_CLK] = &gcc_cfg_noc_usb3_sec_axi_clk.clkr, [GCC_CFG_NOC_USB3_SEC_AXI_CLK] = &gcc_cfg_noc_usb3_sec_axi_clk.clkr,
[GCC_CPUSS_AHB_CLK] = &gcc_cpuss_ahb_clk.clkr,
[GCC_CPUSS_AHB_CLK_SRC] = &gcc_cpuss_ahb_clk_src.clkr,
[GCC_CPUSS_RBCPR_CLK] = &gcc_cpuss_rbcpr_clk.clkr, [GCC_CPUSS_RBCPR_CLK] = &gcc_cpuss_rbcpr_clk.clkr,
[GCC_DDRSS_GPU_AXI_CLK] = &gcc_ddrss_gpu_axi_clk.clkr, [GCC_DDRSS_GPU_AXI_CLK] = &gcc_ddrss_gpu_axi_clk.clkr,
[GCC_DISP_HF_AXI_CLK] = &gcc_disp_hf_axi_clk.clkr, [GCC_DISP_HF_AXI_CLK] = &gcc_disp_hf_axi_clk.clkr,
@@ -4350,6 +4396,7 @@ static struct clk_regmap *gcc_sc8180x_clocks[] = {
[GCC_SDCC4_AHB_CLK] = &gcc_sdcc4_ahb_clk.clkr, [GCC_SDCC4_AHB_CLK] = &gcc_sdcc4_ahb_clk.clkr,
[GCC_SDCC4_APPS_CLK] = &gcc_sdcc4_apps_clk.clkr, [GCC_SDCC4_APPS_CLK] = &gcc_sdcc4_apps_clk.clkr,
[GCC_SDCC4_APPS_CLK_SRC] = &gcc_sdcc4_apps_clk_src.clkr, [GCC_SDCC4_APPS_CLK_SRC] = &gcc_sdcc4_apps_clk_src.clkr,
[GCC_SYS_NOC_CPUSS_AHB_CLK] = &gcc_sys_noc_cpuss_ahb_clk.clkr,
[GCC_TSIF_AHB_CLK] = &gcc_tsif_ahb_clk.clkr, [GCC_TSIF_AHB_CLK] = &gcc_tsif_ahb_clk.clkr,
[GCC_TSIF_INACTIVITY_TIMERS_CLK] = &gcc_tsif_inactivity_timers_clk.clkr, [GCC_TSIF_INACTIVITY_TIMERS_CLK] = &gcc_tsif_inactivity_timers_clk.clkr,
[GCC_TSIF_REF_CLK] = &gcc_tsif_ref_clk.clkr, [GCC_TSIF_REF_CLK] = &gcc_tsif_ref_clk.clkr,
@@ -4436,7 +4483,6 @@ static struct clk_regmap *gcc_sc8180x_clocks[] = {
[GPLL1] = &gpll1.clkr, [GPLL1] = &gpll1.clkr,
[GPLL4] = &gpll4.clkr, [GPLL4] = &gpll4.clkr,
[GPLL7] = &gpll7.clkr, [GPLL7] = &gpll7.clkr,
[GPLL9] = &gpll9.clkr,
}; };
static const struct qcom_reset_map gcc_sc8180x_resets[] = { static const struct qcom_reset_map gcc_sc8180x_resets[] = {

View File

@@ -454,7 +454,7 @@ static struct clk_init_data gcc_qupv3_wrap0_s0_clk_src_init = {
.name = "gcc_qupv3_wrap0_s0_clk_src", .name = "gcc_qupv3_wrap0_s0_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap0_s0_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap0_s0_clk_src = {
@@ -470,7 +470,7 @@ static struct clk_init_data gcc_qupv3_wrap0_s1_clk_src_init = {
.name = "gcc_qupv3_wrap0_s1_clk_src", .name = "gcc_qupv3_wrap0_s1_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap0_s1_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap0_s1_clk_src = {
@@ -486,7 +486,7 @@ static struct clk_init_data gcc_qupv3_wrap0_s2_clk_src_init = {
.name = "gcc_qupv3_wrap0_s2_clk_src", .name = "gcc_qupv3_wrap0_s2_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap0_s2_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap0_s2_clk_src = {
@@ -502,7 +502,7 @@ static struct clk_init_data gcc_qupv3_wrap0_s3_clk_src_init = {
.name = "gcc_qupv3_wrap0_s3_clk_src", .name = "gcc_qupv3_wrap0_s3_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap0_s3_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap0_s3_clk_src = {
@@ -518,7 +518,7 @@ static struct clk_init_data gcc_qupv3_wrap0_s4_clk_src_init = {
.name = "gcc_qupv3_wrap0_s4_clk_src", .name = "gcc_qupv3_wrap0_s4_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap0_s4_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap0_s4_clk_src = {
@@ -534,7 +534,7 @@ static struct clk_init_data gcc_qupv3_wrap0_s5_clk_src_init = {
.name = "gcc_qupv3_wrap0_s5_clk_src", .name = "gcc_qupv3_wrap0_s5_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap0_s5_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap0_s5_clk_src = {
@@ -550,7 +550,7 @@ static struct clk_init_data gcc_qupv3_wrap0_s6_clk_src_init = {
.name = "gcc_qupv3_wrap0_s6_clk_src", .name = "gcc_qupv3_wrap0_s6_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap0_s6_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap0_s6_clk_src = {
@@ -566,7 +566,7 @@ static struct clk_init_data gcc_qupv3_wrap0_s7_clk_src_init = {
.name = "gcc_qupv3_wrap0_s7_clk_src", .name = "gcc_qupv3_wrap0_s7_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap0_s7_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap0_s7_clk_src = {
@@ -582,7 +582,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s0_clk_src_init = {
.name = "gcc_qupv3_wrap1_s0_clk_src", .name = "gcc_qupv3_wrap1_s0_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s0_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s0_clk_src = {
@@ -598,7 +598,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s1_clk_src_init = {
.name = "gcc_qupv3_wrap1_s1_clk_src", .name = "gcc_qupv3_wrap1_s1_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s1_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s1_clk_src = {
@@ -614,7 +614,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s2_clk_src_init = {
.name = "gcc_qupv3_wrap1_s2_clk_src", .name = "gcc_qupv3_wrap1_s2_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s2_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s2_clk_src = {
@@ -630,7 +630,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s3_clk_src_init = {
.name = "gcc_qupv3_wrap1_s3_clk_src", .name = "gcc_qupv3_wrap1_s3_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s3_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s3_clk_src = {
@@ -646,7 +646,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s4_clk_src_init = {
.name = "gcc_qupv3_wrap1_s4_clk_src", .name = "gcc_qupv3_wrap1_s4_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s4_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s4_clk_src = {
@@ -662,7 +662,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s5_clk_src_init = {
.name = "gcc_qupv3_wrap1_s5_clk_src", .name = "gcc_qupv3_wrap1_s5_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s5_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s5_clk_src = {
@@ -678,7 +678,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s6_clk_src_init = {
.name = "gcc_qupv3_wrap1_s6_clk_src", .name = "gcc_qupv3_wrap1_s6_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s6_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s6_clk_src = {
@@ -694,7 +694,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s7_clk_src_init = {
.name = "gcc_qupv3_wrap1_s7_clk_src", .name = "gcc_qupv3_wrap1_s7_clk_src",
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s7_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s7_clk_src = {
@@ -4019,6 +4019,7 @@ static struct platform_driver gcc_sdm845_driver = {
.driver = { .driver = {
.name = "gcc-sdm845", .name = "gcc-sdm845",
.of_match_table = gcc_sdm845_match_table, .of_match_table = gcc_sdm845_match_table,
.sync_state = clk_sync_state,
}, },
}; };

File diff suppressed because it is too large Load Diff

0
drivers/clk/qcom/gcc-sm4450.c Executable file → Normal file
View File

View File

@@ -100,8 +100,8 @@ static struct clk_alpha_pll gpll6 = {
.enable_mask = BIT(6), .enable_mask = BIT(6),
.hw.init = &(struct clk_init_data){ .hw.init = &(struct clk_init_data){
.name = "gpll6", .name = "gpll6",
.parent_data = &(const struct clk_parent_data){ .parent_hws = (const struct clk_hw*[]){
.fw_name = "bi_tcxo", &gpll0.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.ops = &clk_alpha_pll_fixed_fabia_ops, .ops = &clk_alpha_pll_fixed_fabia_ops,
@@ -124,7 +124,7 @@ static struct clk_alpha_pll_postdiv gpll6_out_even = {
.clkr.hw.init = &(struct clk_init_data){ .clkr.hw.init = &(struct clk_init_data){
.name = "gpll6_out_even", .name = "gpll6_out_even",
.parent_hws = (const struct clk_hw*[]){ .parent_hws = (const struct clk_hw*[]){
&gpll6.clkr.hw, &gpll0.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.ops = &clk_alpha_pll_postdiv_fabia_ops, .ops = &clk_alpha_pll_postdiv_fabia_ops,
@@ -139,8 +139,8 @@ static struct clk_alpha_pll gpll7 = {
.enable_mask = BIT(7), .enable_mask = BIT(7),
.hw.init = &(struct clk_init_data){ .hw.init = &(struct clk_init_data){
.name = "gpll7", .name = "gpll7",
.parent_data = &(const struct clk_parent_data){ .parent_hws = (const struct clk_hw*[]){
.fw_name = "bi_tcxo", &gpll0.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.ops = &clk_alpha_pll_fixed_fabia_ops, .ops = &clk_alpha_pll_fixed_fabia_ops,
@@ -182,14 +182,6 @@ static const struct clk_parent_data gcc_parent_data_2_ao[] = {
{ .hw = &gpll0_out_odd.clkr.hw }, { .hw = &gpll0_out_odd.clkr.hw },
}; };
static const struct parent_map gcc_parent_map_3[] = {
{ P_BI_TCXO, 0 },
};
static const struct clk_parent_data gcc_parent_data_3[] = {
{ .fw_name = "bi_tcxo" },
};
static const struct parent_map gcc_parent_map_4[] = { static const struct parent_map gcc_parent_map_4[] = {
{ P_BI_TCXO, 0 }, { P_BI_TCXO, 0 },
{ P_GPLL0_OUT_MAIN, 1 }, { P_GPLL0_OUT_MAIN, 1 },
@@ -709,12 +701,13 @@ static struct clk_rcg2 gcc_ufs_phy_phy_aux_clk_src = {
.cmd_rcgr = 0x3a0b0, .cmd_rcgr = 0x3a0b0,
.mnd_width = 0, .mnd_width = 0,
.hid_width = 5, .hid_width = 5,
.parent_map = gcc_parent_map_3,
.freq_tbl = ftbl_gcc_ufs_phy_phy_aux_clk_src, .freq_tbl = ftbl_gcc_ufs_phy_phy_aux_clk_src,
.clkr.hw.init = &(struct clk_init_data){ .clkr.hw.init = &(struct clk_init_data){
.name = "gcc_ufs_phy_phy_aux_clk_src", .name = "gcc_ufs_phy_phy_aux_clk_src",
.parent_data = gcc_parent_data_3, .parent_data = &(const struct clk_parent_data){
.num_parents = ARRAY_SIZE(gcc_parent_data_3), .fw_name = "bi_tcxo",
},
.num_parents = 1,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -771,12 +764,13 @@ static struct clk_rcg2 gcc_usb30_prim_mock_utmi_clk_src = {
.cmd_rcgr = 0x1a034, .cmd_rcgr = 0x1a034,
.mnd_width = 0, .mnd_width = 0,
.hid_width = 5, .hid_width = 5,
.parent_map = gcc_parent_map_3,
.freq_tbl = ftbl_gcc_usb30_prim_mock_utmi_clk_src, .freq_tbl = ftbl_gcc_usb30_prim_mock_utmi_clk_src,
.clkr.hw.init = &(struct clk_init_data){ .clkr.hw.init = &(struct clk_init_data){
.name = "gcc_usb30_prim_mock_utmi_clk_src", .name = "gcc_usb30_prim_mock_utmi_clk_src",
.parent_data = gcc_parent_data_3, .parent_data = &(const struct clk_parent_data){
.num_parents = ARRAY_SIZE(gcc_parent_data_3), .fw_name = "bi_tcxo",
},
.num_parents = 1,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -2320,9 +2314,6 @@ static struct clk_branch gcc_video_xo_clk = {
static struct gdsc usb30_prim_gdsc = { static struct gdsc usb30_prim_gdsc = {
.gdscr = 0x1a004, .gdscr = 0x1a004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "usb30_prim_gdsc", .name = "usb30_prim_gdsc",
}, },
@@ -2331,9 +2322,6 @@ static struct gdsc usb30_prim_gdsc = {
static struct gdsc ufs_phy_gdsc = { static struct gdsc ufs_phy_gdsc = {
.gdscr = 0x3a004, .gdscr = 0x3a004,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "ufs_phy_gdsc", .name = "ufs_phy_gdsc",
}, },

View File

@@ -3226,7 +3226,7 @@ static struct gdsc pcie_0_gdsc = {
.pd = { .pd = {
.name = "pcie_0_gdsc", .name = "pcie_0_gdsc",
}, },
.pwrsts = PWRSTS_RET_ON, .pwrsts = PWRSTS_OFF_ON,
}; };
static struct gdsc pcie_1_gdsc = { static struct gdsc pcie_1_gdsc = {
@@ -3234,7 +3234,7 @@ static struct gdsc pcie_1_gdsc = {
.pd = { .pd = {
.name = "pcie_1_gdsc", .name = "pcie_1_gdsc",
}, },
.pwrsts = PWRSTS_RET_ON, .pwrsts = PWRSTS_OFF_ON,
}; };
static struct gdsc pcie_2_gdsc = { static struct gdsc pcie_2_gdsc = {
@@ -3242,7 +3242,7 @@ static struct gdsc pcie_2_gdsc = {
.pd = { .pd = {
.name = "pcie_2_gdsc", .name = "pcie_2_gdsc",
}, },
.pwrsts = PWRSTS_RET_ON, .pwrsts = PWRSTS_OFF_ON,
}; };
static struct gdsc ufs_card_gdsc = { static struct gdsc ufs_card_gdsc = {

View File

@@ -2974,7 +2974,7 @@ static struct gdsc pcie_0_gdsc = {
.pd = { .pd = {
.name = "pcie_0_gdsc", .name = "pcie_0_gdsc",
}, },
.pwrsts = PWRSTS_RET_ON, .pwrsts = PWRSTS_OFF_ON,
}; };
static struct gdsc pcie_1_gdsc = { static struct gdsc pcie_1_gdsc = {
@@ -2982,7 +2982,7 @@ static struct gdsc pcie_1_gdsc = {
.pd = { .pd = {
.name = "pcie_1_gdsc", .name = "pcie_1_gdsc",
}, },
.pwrsts = PWRSTS_RET_ON, .pwrsts = PWRSTS_OFF_ON,
}; };
static struct gdsc ufs_phy_gdsc = { static struct gdsc ufs_phy_gdsc = {

View File

@@ -536,7 +536,7 @@ static struct clk_rcg2 gcc_qupv3_i2c_s0_clk_src = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}, },
}; };
@@ -551,7 +551,7 @@ static struct clk_rcg2 gcc_qupv3_i2c_s1_clk_src = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}, },
}; };
@@ -566,7 +566,7 @@ static struct clk_rcg2 gcc_qupv3_i2c_s2_clk_src = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}, },
}; };
@@ -581,7 +581,7 @@ static struct clk_rcg2 gcc_qupv3_i2c_s3_clk_src = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}, },
}; };
@@ -596,7 +596,7 @@ static struct clk_rcg2 gcc_qupv3_i2c_s4_clk_src = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}, },
}; };
@@ -611,7 +611,7 @@ static struct clk_rcg2 gcc_qupv3_i2c_s5_clk_src = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}, },
}; };
@@ -626,7 +626,7 @@ static struct clk_rcg2 gcc_qupv3_i2c_s6_clk_src = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}, },
}; };
@@ -641,7 +641,7 @@ static struct clk_rcg2 gcc_qupv3_i2c_s7_clk_src = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}, },
}; };
@@ -656,7 +656,7 @@ static struct clk_rcg2 gcc_qupv3_i2c_s8_clk_src = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}, },
}; };
@@ -671,7 +671,7 @@ static struct clk_rcg2 gcc_qupv3_i2c_s9_clk_src = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}, },
}; };
@@ -700,7 +700,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s0_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s0_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s0_clk_src = {
@@ -717,7 +717,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s1_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s1_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s1_clk_src = {
@@ -750,7 +750,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s2_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s2_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s2_clk_src = {
@@ -767,7 +767,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s3_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s3_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s3_clk_src = {
@@ -784,7 +784,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s4_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s4_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s4_clk_src = {
@@ -801,7 +801,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s5_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s5_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s5_clk_src = {
@@ -818,7 +818,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s6_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s6_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s6_clk_src = {
@@ -835,7 +835,7 @@ static struct clk_init_data gcc_qupv3_wrap1_s7_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap1_s7_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap1_s7_clk_src = {
@@ -852,7 +852,7 @@ static struct clk_init_data gcc_qupv3_wrap2_s0_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap2_s0_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap2_s0_clk_src = {
@@ -869,7 +869,7 @@ static struct clk_init_data gcc_qupv3_wrap2_s1_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap2_s1_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap2_s1_clk_src = {
@@ -886,7 +886,7 @@ static struct clk_init_data gcc_qupv3_wrap2_s2_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap2_s2_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap2_s2_clk_src = {
@@ -903,7 +903,7 @@ static struct clk_init_data gcc_qupv3_wrap2_s3_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap2_s3_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap2_s3_clk_src = {
@@ -920,7 +920,7 @@ static struct clk_init_data gcc_qupv3_wrap2_s4_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap2_s4_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap2_s4_clk_src = {
@@ -937,7 +937,7 @@ static struct clk_init_data gcc_qupv3_wrap2_s5_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap2_s5_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap2_s5_clk_src = {
@@ -975,7 +975,7 @@ static struct clk_init_data gcc_qupv3_wrap2_s6_clk_src_init = {
.parent_data = gcc_parent_data_8, .parent_data = gcc_parent_data_8,
.num_parents = ARRAY_SIZE(gcc_parent_data_8), .num_parents = ARRAY_SIZE(gcc_parent_data_8),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap2_s6_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap2_s6_clk_src = {
@@ -992,7 +992,7 @@ static struct clk_init_data gcc_qupv3_wrap2_s7_clk_src_init = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_ops, .ops = &clk_rcg2_shared_ops,
}; };
static struct clk_rcg2 gcc_qupv3_wrap2_s7_clk_src = { static struct clk_rcg2 gcc_qupv3_wrap2_s7_clk_src = {
@@ -1159,7 +1159,7 @@ static struct clk_rcg2 gcc_usb30_prim_master_clk_src = {
.parent_data = gcc_parent_data_0, .parent_data = gcc_parent_data_0,
.num_parents = ARRAY_SIZE(gcc_parent_data_0), .num_parents = ARRAY_SIZE(gcc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_no_init_park_ops, .ops = &clk_rcg2_shared_ops,
}, },
}; };
@@ -3003,7 +3003,7 @@ static struct gdsc pcie_0_gdsc = {
.pd = { .pd = {
.name = "pcie_0_gdsc", .name = "pcie_0_gdsc",
}, },
.pwrsts = PWRSTS_RET_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = VOTABLE | POLL_CFG_GDSCR | RETAIN_FF_ENABLE, .flags = VOTABLE | POLL_CFG_GDSCR | RETAIN_FF_ENABLE,
}; };
@@ -3014,7 +3014,7 @@ static struct gdsc pcie_0_phy_gdsc = {
.pd = { .pd = {
.name = "pcie_0_phy_gdsc", .name = "pcie_0_phy_gdsc",
}, },
.pwrsts = PWRSTS_RET_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = VOTABLE | POLL_CFG_GDSCR | RETAIN_FF_ENABLE, .flags = VOTABLE | POLL_CFG_GDSCR | RETAIN_FF_ENABLE,
}; };
@@ -3025,7 +3025,7 @@ static struct gdsc pcie_1_gdsc = {
.pd = { .pd = {
.name = "pcie_1_gdsc", .name = "pcie_1_gdsc",
}, },
.pwrsts = PWRSTS_RET_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = VOTABLE | POLL_CFG_GDSCR | RETAIN_FF_ENABLE, .flags = VOTABLE | POLL_CFG_GDSCR | RETAIN_FF_ENABLE,
}; };
@@ -3036,7 +3036,7 @@ static struct gdsc pcie_1_phy_gdsc = {
.pd = { .pd = {
.name = "pcie_1_phy_gdsc", .name = "pcie_1_phy_gdsc",
}, },
.pwrsts = PWRSTS_RET_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = VOTABLE | POLL_CFG_GDSCR | RETAIN_FF_ENABLE, .flags = VOTABLE | POLL_CFG_GDSCR | RETAIN_FF_ENABLE,
}; };

0
drivers/clk/qcom/gcc-sun.c Executable file → Normal file
View File

0
drivers/clk/qcom/gcc-tuna.c Executable file → Normal file
View File

0
drivers/clk/qcom/gdsc-debug.h Executable file → Normal file
View File

0
drivers/clk/qcom/gdsc-regulator.c Executable file → Normal file
View File

View File

@@ -1,6 +1,7 @@
// SPDX-License-Identifier: GPL-2.0-only // SPDX-License-Identifier: GPL-2.0-only
/* /*
* Copyright (c) 2015, 2017-2018, 2022, The Linux Foundation. All rights reserved. * Copyright (c) 2015, 2017-2018, 2022, The Linux Foundation. All rights reserved.
* Copyright (c) 2024, Qualcomm Innovation Center, Inc. All rights reserved.
*/ */
#include <linux/bitops.h> #include <linux/bitops.h>
@@ -136,10 +137,49 @@ static int gdsc_update_collapse_bit(struct gdsc *sc, bool val)
return 0; return 0;
} }
static void log_gdsc_debug_regs(struct gdsc *sc)
{
u32 val;
pr_err("Dumping %s registers\n", sc->pd.name);
regmap_read(sc->regmap, sc->gds_hw_ctrl, &val);
pr_err("HW_CTRL_CFG1_GDSR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gdscr, &val);
pr_err("GDSCR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gdscr + 4, &val);
pr_err("CFG_GDSCR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gdscr + 8, &val);
pr_err("CFG2_GDSCR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gdscr + 0xc, &val);
pr_err("CFG3_GDSCR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gdscr + 0x10, &val);
pr_err("CFG4_GDSCR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gds_hw_ctrl, &val);
pr_err("HW_CTRL_CFG1_GDSR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gds_hw_ctrl + 4, &val);
pr_err("HW_CTRL_CFG2_GDSR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gds_hw_ctrl + 8, &val);
pr_err("HW_CTRL_DVM_STATUS_GDSR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gds_hw_ctrl + 0xc, &val);
pr_err("HW_CTRL_HALT1_STATUS_GDSR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gds_hw_ctrl + 0x10, &val);
pr_err("HW_CTRL_HALT2_STATUS_GDSR : 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gds_hw_ctrl + 0x14, &val);
pr_err("HW_CTRL_REQ_SW_GDSR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gds_hw_ctrl + 0x18, &val);
pr_err("HW_CTRL_IRQ_STATUS_GDSR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gds_hw_ctrl + 0x20, &val);
pr_err("HW_CTRL_IRQ_CLEAR_GDSR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gds_hw_ctrl, &val);
pr_err("HW_CTRL_CFG1_GDSR: 0x%.8x\n\n", val);
}
static int gdsc_toggle_logic(struct gdsc *sc, enum gdsc_status status, static int gdsc_toggle_logic(struct gdsc *sc, enum gdsc_status status,
bool wait) bool wait)
{ {
int ret; int ret;
u32 val;
if (status == GDSC_ON && sc->rsupply) { if (status == GDSC_ON && sc->rsupply) {
ret = regulator_enable(sc->rsupply); ret = regulator_enable(sc->rsupply);
@@ -147,6 +187,12 @@ static int gdsc_toggle_logic(struct gdsc *sc, enum gdsc_status status,
return ret; return ret;
} }
regmap_read(sc->regmap, sc->gdscr, &val);
if (val & HW_CONTROL_MASK) {
pr_debug("%s in HW control mode\n", sc->pd.name);
return 0;
}
ret = gdsc_update_collapse_bit(sc, status == GDSC_OFF); ret = gdsc_update_collapse_bit(sc, status == GDSC_OFF);
/* If disabling votable gdscs, don't poll on status */ /* If disabling votable gdscs, don't poll on status */
@@ -157,7 +203,7 @@ static int gdsc_toggle_logic(struct gdsc *sc, enum gdsc_status status,
* unknown state * unknown state
*/ */
udelay(TIMEOUT_US); udelay(TIMEOUT_US);
return 0; goto out;
} }
if (sc->gds_hw_ctrl) { if (sc->gds_hw_ctrl) {
@@ -175,8 +221,21 @@ static int gdsc_toggle_logic(struct gdsc *sc, enum gdsc_status status,
} }
ret = gdsc_poll_status(sc, status); ret = gdsc_poll_status(sc, status);
if (ret && sc->gds_hw_ctrl) {
pr_err("%s enable timed out, Re-polling\n", sc->pd.name);
log_gdsc_debug_regs(sc);
ret = gdsc_poll_status(sc, status);
if (ret) {
log_gdsc_debug_regs(sc);
udelay(500);
log_gdsc_debug_regs(sc);
udelay(1000);
log_gdsc_debug_regs(sc);
}
}
WARN(ret, "%s status stuck at 'o%s'", sc->pd.name, status ? "ff" : "n"); WARN(ret, "%s status stuck at 'o%s'", sc->pd.name, status ? "ff" : "n");
out:
if (!ret && status == GDSC_OFF && sc->rsupply) { if (!ret && status == GDSC_OFF && sc->rsupply) {
ret = regulator_disable(sc->rsupply); ret = regulator_disable(sc->rsupply);
if (ret < 0) if (ret < 0)
@@ -292,9 +351,6 @@ static int gdsc_enable(struct generic_pm_domain *domain)
*/ */
udelay(1); udelay(1);
if (sc->flags & RETAIN_FF_ENABLE)
gdsc_retain_ff_on(sc);
/* Turn on HW trigger mode if supported */ /* Turn on HW trigger mode if supported */
if (sc->flags & HW_CTRL) { if (sc->flags & HW_CTRL) {
ret = gdsc_hwctrl(sc, true); ret = gdsc_hwctrl(sc, true);
@@ -311,6 +367,9 @@ static int gdsc_enable(struct generic_pm_domain *domain)
udelay(1); udelay(1);
} }
if (sc->flags & RETAIN_FF_ENABLE)
gdsc_retain_ff_on(sc);
return 0; return 0;
} }
@@ -324,6 +383,13 @@ static int gdsc_disable(struct generic_pm_domain *domain)
/* Turn off HW trigger mode if supported */ /* Turn off HW trigger mode if supported */
if (sc->flags & HW_CTRL) { if (sc->flags & HW_CTRL) {
if (sc->flags & HW_CTRL_SKIP_DIS) {
if (sc->rsupply)
return regulator_disable(sc->rsupply);
return 0;
}
ret = gdsc_hwctrl(sc, false); ret = gdsc_hwctrl(sc, false);
if (ret < 0) if (ret < 0)
return ret; return ret;
@@ -420,14 +486,6 @@ static int gdsc_init(struct gdsc *sc)
goto err_disable_supply; goto err_disable_supply;
} }
/*
* Make sure the retain bit is set if the GDSC is already on,
* otherwise we end up turning off the GDSC and destroying all
* the register contents that we thought we were saving.
*/
if (sc->flags & RETAIN_FF_ENABLE)
gdsc_retain_ff_on(sc);
/* Turn on HW trigger mode if supported */ /* Turn on HW trigger mode if supported */
if (sc->flags & HW_CTRL) { if (sc->flags & HW_CTRL) {
ret = gdsc_hwctrl(sc, true); ret = gdsc_hwctrl(sc, true);
@@ -435,6 +493,13 @@ static int gdsc_init(struct gdsc *sc)
goto err_disable_supply; goto err_disable_supply;
} }
/*
* Make sure the retain bit is set if the GDSC is already on,
* otherwise we end up turning off the GDSC and destroying all
* the register contents that we thought we were saving.
*/
if (sc->flags & RETAIN_FF_ENABLE)
gdsc_retain_ff_on(sc);
} else if (sc->flags & ALWAYS_ON) { } else if (sc->flags & ALWAYS_ON) {
/* If ALWAYS_ON GDSCs are not ON, turn them ON */ /* If ALWAYS_ON GDSCs are not ON, turn them ON */
gdsc_enable(&sc->pd); gdsc_enable(&sc->pd);
@@ -466,23 +531,6 @@ err_disable_supply:
return ret; return ret;
} }
static void gdsc_pm_subdomain_remove(struct gdsc_desc *desc, size_t num)
{
struct device *dev = desc->dev;
struct gdsc **scs = desc->scs;
int i;
/* Remove subdomains */
for (i = num - 1; i >= 0; i--) {
if (!scs[i])
continue;
if (scs[i]->parent)
pm_genpd_remove_subdomain(scs[i]->parent, &scs[i]->pd);
else if (!IS_ERR_OR_NULL(dev->pm_domain))
pm_genpd_remove_subdomain(pd_to_genpd(dev->pm_domain), &scs[i]->pd);
}
}
int gdsc_register(struct gdsc_desc *desc, int gdsc_register(struct gdsc_desc *desc,
struct reset_controller_dev *rcdev, struct regmap *regmap) struct reset_controller_dev *rcdev, struct regmap *regmap)
{ {
@@ -527,27 +575,30 @@ int gdsc_register(struct gdsc_desc *desc,
if (!scs[i]) if (!scs[i])
continue; continue;
if (scs[i]->parent) if (scs[i]->parent)
ret = pm_genpd_add_subdomain(scs[i]->parent, &scs[i]->pd); pm_genpd_add_subdomain(scs[i]->parent, &scs[i]->pd);
else if (!IS_ERR_OR_NULL(dev->pm_domain)) else if (!IS_ERR_OR_NULL(dev->pm_domain))
ret = pm_genpd_add_subdomain(pd_to_genpd(dev->pm_domain), &scs[i]->pd); pm_genpd_add_subdomain(pd_to_genpd(dev->pm_domain), &scs[i]->pd);
if (ret)
goto err_pm_subdomain_remove;
} }
return of_genpd_add_provider_onecell(dev->of_node, data); return of_genpd_add_provider_onecell(dev->of_node, data);
err_pm_subdomain_remove:
gdsc_pm_subdomain_remove(desc, i);
return ret;
} }
void gdsc_unregister(struct gdsc_desc *desc) void gdsc_unregister(struct gdsc_desc *desc)
{ {
int i;
struct device *dev = desc->dev; struct device *dev = desc->dev;
struct gdsc **scs = desc->scs;
size_t num = desc->num; size_t num = desc->num;
gdsc_pm_subdomain_remove(desc, num); /* Remove subdomains */
for (i = 0; i < num; i++) {
if (!scs[i])
continue;
if (scs[i]->parent)
pm_genpd_remove_subdomain(scs[i]->parent, &scs[i]->pd);
else if (!IS_ERR_OR_NULL(dev->pm_domain))
pm_genpd_remove_subdomain(pd_to_genpd(dev->pm_domain), &scs[i]->pd);
}
of_genpd_del_provider(dev->of_node); of_genpd_del_provider(dev->of_node);
} }
@@ -572,7 +623,146 @@ void gdsc_unregister(struct gdsc_desc *desc)
*/ */
int gdsc_gx_do_nothing_enable(struct generic_pm_domain *domain) int gdsc_gx_do_nothing_enable(struct generic_pm_domain *domain)
{ {
/* Do nothing but give genpd the impression that we were successful */ struct gdsc *sc = domain_to_gdsc(domain);
return 0; int ret = 0;
/* Enable the parent supply, when controlled through the regulator framework. */
if (sc->rsupply)
ret = regulator_enable(sc->rsupply);
/* Do nothing with the GDSC itself */
return ret;
} }
EXPORT_SYMBOL_GPL(gdsc_gx_do_nothing_enable); EXPORT_SYMBOL_GPL(gdsc_gx_do_nothing_enable);
static void gdsc_debug_print_registers(struct gdsc *sc)
{
u32 val;
regmap_read(sc->regmap, sc->gdscr, &val);
pr_err("GDSCR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gdscr + 4, &val);
pr_err("CFG_GDSCR: 0x%.8x\n", val);
regmap_read(sc->regmap, sc->gdscr + 8, &val);
pr_err("CFG2_GDSCR: 0x%.8x\n", val);
if (sc->gds_hw_ctrl) {
regmap_read(sc->regmap, sc->gds_hw_ctrl, &val);
pr_err("GDS_HW_CTRL: 0x%.8x\n", val);
}
if (sc->collapse_ctrl) {
regmap_read(sc->regmap, sc->collapse_ctrl, &val);
pr_err("COLLAPSE_CTRL: 0x%.8x\n", val);
}
}
static void genpd_dump_consumers(struct generic_pm_domain *genpd)
{
static const char * const status_lookup[] = {
[RPM_ACTIVE] = "active",
[RPM_RESUMING] = "resuming",
[RPM_SUSPENDED] = "suspended",
[RPM_SUSPENDING] = "suspending"
};
struct pm_domain_data *pm_data;
const char *kobj_path;
const char *p = "";
struct device *dev;
pr_err("%-30s %-50s\n", genpd->name, genpd->status ? "off" : "on");
pr_err("Consumers:\n");
list_for_each_entry(pm_data, &genpd->dev_list, list_node) {
kobj_path = kobject_get_path(&pm_data->dev->kobj,
genpd->flags & GENPD_FLAG_IRQ_SAFE ?
GFP_ATOMIC : GFP_KERNEL);
if (kobj_path == NULL)
continue;
dev = pm_data->dev;
if (dev->power.runtime_error)
p = "error";
else if (dev->power.disable_depth)
p = "unsupported";
else if (dev->power.runtime_status < ARRAY_SIZE(status_lookup))
p = status_lookup[dev->power.runtime_status];
pr_err("%-50s %-25s\n", kobj_path, p);
pr_err("usage_count:%d\n", atomic_read(&dev->power.usage_count));
pr_err("last_busy:%llu\n", dev->power.last_busy);
pr_err("timer_expires:%llu\n", dev->power.timer_expires);
pr_err("timer_state:%d\n", dev->power.suspend_timer.state);
pr_err("rpm_request:%d\n", dev->power.request);
pr_err("request_pending:%u\n", dev->power.request_pending);
pr_err("timer_autosuspends:%d\n", dev->power.timer_autosuspends);
pr_err("runtime_error:%d\n", dev->power.runtime_error);
pr_err("autosuspend_delay:%d\n", dev->power.autosuspend_delay);
pr_err("disable_depth:%u\n", dev->power.disable_depth);
pr_err("child_count:%d\n", atomic_read(&dev->power.child_count));
pr_err("deferred_resume:%u\n", dev->power.deferred_resume);
pr_err("ignore_children:%u\n", dev->power.ignore_children);
pr_err("use_autosuspend:%u\n", dev->power.use_autosuspend);
pr_err("current_time: %llu\n", ktime_get_mono_fast_ns());
kfree(kobj_path);
}
pr_err("device_count: %d\n", genpd->device_count);
pr_err("prepared_count: %d\n", genpd->prepared_count);
pr_err("suspended_count: %d\n", genpd->suspended_count);
pr_err("sd_count: %d\n", atomic_read(&genpd->sd_count));
}
void qcom_gdsc_pd_dump(struct device *device)
{
struct generic_pm_domain *genpd, *child;
struct gpd_link *link;
struct gdsc *sc;
if (!device) {
pr_err("Null device handle passed\n");
return;
}
if (device && IS_ERR_OR_NULL(device->pm_domain)) {
pr_err("No pm_domain linked to device\n");
return;
}
genpd = pd_to_genpd(device->pm_domain);
if (IS_ERR(genpd)) {
pr_err("No pd linked to device\n");
return;
}
if (mutex_lock_interruptible(&genpd->mlock)) {
pr_err("Failed to acquire %s genpd lock\n", genpd->name);
return;
}
genpd_dump_consumers(genpd);
pr_err("Child_domains:\n");
list_for_each_entry(link, &genpd->parent_links, parent_node) {
child = link->child;
if (mutex_lock_interruptible(&child->mlock)) {
pr_err("Failed to acquire %s genpd lock\n", child->name);
mutex_unlock(&genpd->mlock);
return;
}
genpd_dump_consumers(child);
mutex_unlock(&child->mlock);
}
sc = domain_to_gdsc(genpd);
pr_err("Dumping %s registers\n", sc->pd.name);
gdsc_debug_print_registers(sc);
mutex_unlock(&genpd->mlock);
}
EXPORT_SYMBOL_GPL(qcom_gdsc_pd_dump);

View File

@@ -1,6 +1,7 @@
/* SPDX-License-Identifier: GPL-2.0-only */ /* SPDX-License-Identifier: GPL-2.0-only */
/* /*
* Copyright (c) 2015, 2017-2018, 2022, The Linux Foundation. All rights reserved. * Copyright (c) 2015, 2017-2018, 2022, The Linux Foundation. All rights reserved.
* Copyright (c) 2024, Qualcomm Innovation Center, Inc. All rights reserved.
*/ */
#ifndef __QCOM_GDSC_H__ #ifndef __QCOM_GDSC_H__
@@ -67,6 +68,7 @@ struct gdsc {
#define ALWAYS_ON BIT(6) #define ALWAYS_ON BIT(6)
#define RETAIN_FF_ENABLE BIT(7) #define RETAIN_FF_ENABLE BIT(7)
#define NO_RET_PERIPH BIT(8) #define NO_RET_PERIPH BIT(8)
#define HW_CTRL_SKIP_DIS BIT(9)
struct reset_controller_dev *rcdev; struct reset_controller_dev *rcdev;
unsigned int *resets; unsigned int *resets;
unsigned int reset_count; unsigned int reset_count;

0
drivers/clk/qcom/gpucc-monaco.c Executable file → Normal file
View File

0
drivers/clk/qcom/gpucc-parrot.c Executable file → Normal file
View File

0
drivers/clk/qcom/gpucc-pineapple.c Executable file → Normal file
View File

View File

@@ -1,6 +1,6 @@
// SPDX-License-Identifier: GPL-2.0-only // SPDX-License-Identifier: GPL-2.0-only
/* /*
* Copyright (c) 2021-2022, 2024, Qualcomm Innovation Center, Inc. All rights reserved. * Copyright (c) 2021-2022, Qualcomm Innovation Center, Inc. All rights reserved.
* Copyright (c) 2023, Linaro Limited * Copyright (c) 2023, Linaro Limited
*/ */
@@ -161,7 +161,7 @@ static struct clk_rcg2 gpu_cc_ff_clk_src = {
.name = "gpu_cc_ff_clk_src", .name = "gpu_cc_ff_clk_src",
.parent_data = gpu_cc_parent_data_0, .parent_data = gpu_cc_parent_data_0,
.num_parents = ARRAY_SIZE(gpu_cc_parent_data_0), .num_parents = ARRAY_SIZE(gpu_cc_parent_data_0),
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -181,7 +181,7 @@ static struct clk_rcg2 gpu_cc_gmu_clk_src = {
.parent_data = gpu_cc_parent_data_1, .parent_data = gpu_cc_parent_data_1,
.num_parents = ARRAY_SIZE(gpu_cc_parent_data_1), .num_parents = ARRAY_SIZE(gpu_cc_parent_data_1),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -200,7 +200,7 @@ static struct clk_rcg2 gpu_cc_hub_clk_src = {
.name = "gpu_cc_hub_clk_src", .name = "gpu_cc_hub_clk_src",
.parent_data = gpu_cc_parent_data_2, .parent_data = gpu_cc_parent_data_2,
.num_parents = ARRAY_SIZE(gpu_cc_parent_data_2), .num_parents = ARRAY_SIZE(gpu_cc_parent_data_2),
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -280,7 +280,7 @@ static struct clk_branch gpu_cc_ahb_clk = {
&gpu_cc_hub_ahb_div_clk_src.clkr.hw, &gpu_cc_hub_ahb_div_clk_src.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT | CLK_IS_CRITICAL,
.ops = &clk_branch2_ops, .ops = &clk_branch2_ops,
}, },
}, },
@@ -294,7 +294,8 @@ static struct clk_branch gpu_cc_cb_clk = {
.enable_mask = BIT(0), .enable_mask = BIT(0),
.hw.init = &(const struct clk_init_data){ .hw.init = &(const struct clk_init_data){
.name = "gpu_cc_cb_clk", .name = "gpu_cc_cb_clk",
.ops = &clk_branch2_aon_ops, .flags = CLK_IS_CRITICAL,
.ops = &clk_branch2_ops,
}, },
}, },
}; };
@@ -311,7 +312,7 @@ static struct clk_branch gpu_cc_crc_ahb_clk = {
&gpu_cc_hub_ahb_div_clk_src.clkr.hw, &gpu_cc_hub_ahb_div_clk_src.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT | CLK_IS_CRITICAL,
.ops = &clk_branch2_ops, .ops = &clk_branch2_ops,
}, },
}, },
@@ -329,7 +330,7 @@ static struct clk_branch gpu_cc_cx_ff_clk = {
&gpu_cc_ff_clk_src.clkr.hw, &gpu_cc_ff_clk_src.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT | CLK_IS_CRITICAL,
.ops = &clk_branch2_ops, .ops = &clk_branch2_ops,
}, },
}, },
@@ -347,7 +348,7 @@ static struct clk_branch gpu_cc_cx_gmu_clk = {
&gpu_cc_gmu_clk_src.clkr.hw, &gpu_cc_gmu_clk_src.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT | CLK_IS_CRITICAL,
.ops = &clk_branch2_aon_ops, .ops = &clk_branch2_aon_ops,
}, },
}, },
@@ -361,6 +362,7 @@ static struct clk_branch gpu_cc_cx_snoc_dvm_clk = {
.enable_mask = BIT(0), .enable_mask = BIT(0),
.hw.init = &(const struct clk_init_data){ .hw.init = &(const struct clk_init_data){
.name = "gpu_cc_cx_snoc_dvm_clk", .name = "gpu_cc_cx_snoc_dvm_clk",
.flags = CLK_IS_CRITICAL,
.ops = &clk_branch2_ops, .ops = &clk_branch2_ops,
}, },
}, },
@@ -378,7 +380,7 @@ static struct clk_branch gpu_cc_cxo_aon_clk = {
&gpu_cc_xo_clk_src.clkr.hw, &gpu_cc_xo_clk_src.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT | CLK_IS_CRITICAL,
.ops = &clk_branch2_ops, .ops = &clk_branch2_ops,
}, },
}, },
@@ -396,7 +398,7 @@ static struct clk_branch gpu_cc_cxo_clk = {
&gpu_cc_xo_clk_src.clkr.hw, &gpu_cc_xo_clk_src.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT | CLK_IS_CRITICAL,
.ops = &clk_branch2_ops, .ops = &clk_branch2_ops,
}, },
}, },
@@ -414,7 +416,7 @@ static struct clk_branch gpu_cc_demet_clk = {
&gpu_cc_demet_div_clk_src.clkr.hw, &gpu_cc_demet_div_clk_src.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT | CLK_IS_CRITICAL,
.ops = &clk_branch2_aon_ops, .ops = &clk_branch2_aon_ops,
}, },
}, },
@@ -428,6 +430,7 @@ static struct clk_branch gpu_cc_hlos1_vote_gpu_smmu_clk = {
.enable_mask = BIT(0), .enable_mask = BIT(0),
.hw.init = &(const struct clk_init_data){ .hw.init = &(const struct clk_init_data){
.name = "gpu_cc_hlos1_vote_gpu_smmu_clk", .name = "gpu_cc_hlos1_vote_gpu_smmu_clk",
.flags = CLK_IS_CRITICAL,
.ops = &clk_branch2_ops, .ops = &clk_branch2_ops,
}, },
}, },
@@ -445,7 +448,7 @@ static struct clk_branch gpu_cc_hub_aon_clk = {
&gpu_cc_hub_clk_src.clkr.hw, &gpu_cc_hub_clk_src.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT | CLK_IS_CRITICAL,
.ops = &clk_branch2_aon_ops, .ops = &clk_branch2_aon_ops,
}, },
}, },
@@ -463,7 +466,7 @@ static struct clk_branch gpu_cc_hub_cx_int_clk = {
&gpu_cc_hub_cx_int_div_clk_src.clkr.hw, &gpu_cc_hub_cx_int_div_clk_src.clkr.hw,
}, },
.num_parents = 1, .num_parents = 1,
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT | CLK_IS_CRITICAL,
.ops = &clk_branch2_aon_ops, .ops = &clk_branch2_aon_ops,
}, },
}, },
@@ -477,6 +480,7 @@ static struct clk_branch gpu_cc_memnoc_gfx_clk = {
.enable_mask = BIT(0), .enable_mask = BIT(0),
.hw.init = &(const struct clk_init_data){ .hw.init = &(const struct clk_init_data){
.name = "gpu_cc_memnoc_gfx_clk", .name = "gpu_cc_memnoc_gfx_clk",
.flags = CLK_IS_CRITICAL,
.ops = &clk_branch2_ops, .ops = &clk_branch2_ops,
}, },
}, },
@@ -490,6 +494,7 @@ static struct clk_branch gpu_cc_sleep_clk = {
.enable_mask = BIT(0), .enable_mask = BIT(0),
.hw.init = &(const struct clk_init_data){ .hw.init = &(const struct clk_init_data){
.name = "gpu_cc_sleep_clk", .name = "gpu_cc_sleep_clk",
.flags = CLK_IS_CRITICAL,
.ops = &clk_branch2_ops, .ops = &clk_branch2_ops,
}, },
}, },
@@ -523,22 +528,16 @@ static struct clk_regmap *gpu_cc_sa8775p_clocks[] = {
static struct gdsc cx_gdsc = { static struct gdsc cx_gdsc = {
.gdscr = 0x9108, .gdscr = 0x9108,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.gds_hw_ctrl = 0x953c, .gds_hw_ctrl = 0x953c,
.pd = { .pd = {
.name = "cx_gdsc", .name = "cx_gdsc",
}, },
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = VOTABLE | RETAIN_FF_ENABLE, .flags = VOTABLE | RETAIN_FF_ENABLE | ALWAYS_ON,
}; };
static struct gdsc gx_gdsc = { static struct gdsc gx_gdsc = {
.gdscr = 0x905c, .gdscr = 0x905c,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0xf,
.pd = { .pd = {
.name = "gx_gdsc", .name = "gx_gdsc",
.power_on = gdsc_gx_do_nothing_enable, .power_on = gdsc_gx_do_nothing_enable,

View File

@@ -200,6 +200,7 @@ static struct platform_driver gpu_cc_sdm845_driver = {
.driver = { .driver = {
.name = "sdm845-gpucc", .name = "sdm845-gpucc",
.of_match_table = gpu_cc_sdm845_match_table, .of_match_table = gpu_cc_sdm845_match_table,
.sync_state = clk_sync_state,
}, },
}; };

0
drivers/clk/qcom/gpucc-sm4450.c Executable file → Normal file
View File

View File

@@ -412,9 +412,6 @@ static struct clk_branch gpu_cc_gx_vsense_clk = {
static struct gdsc gpu_cx_gdsc = { static struct gdsc gpu_cx_gdsc = {
.gdscr = 0x106c, .gdscr = 0x106c,
.gds_hw_ctrl = 0x1540, .gds_hw_ctrl = 0x1540,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0x8,
.pd = { .pd = {
.name = "gpu_cx_gdsc", .name = "gpu_cx_gdsc",
}, },
@@ -425,9 +422,6 @@ static struct gdsc gpu_cx_gdsc = {
static struct gdsc gpu_gx_gdsc = { static struct gdsc gpu_gx_gdsc = {
.gdscr = 0x100c, .gdscr = 0x100c,
.clamp_io_ctrl = 0x1508, .clamp_io_ctrl = 0x1508,
.en_rest_wait_val = 0x2,
.en_few_wait_val = 0x2,
.clk_dis_wait_val = 0x2,
.pd = { .pd = {
.name = "gpu_gx_gdsc", .name = "gpu_gx_gdsc",
.power_on = gdsc_gx_do_nothing_enable, .power_on = gdsc_gx_do_nothing_enable,

View File

@@ -2,7 +2,6 @@
/* /*
* Copyright (c) 2019-2020, The Linux Foundation. All rights reserved. * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved.
* Copyright (c) 2022, Linaro Limited * Copyright (c) 2022, Linaro Limited
* Copyright (c) 2024, Qualcomm Innovation Center, Inc. All rights reserved.
*/ */
#include <linux/clk.h> #include <linux/clk.h>
@@ -148,7 +147,7 @@ static struct clk_rcg2 gpu_cc_gmu_clk_src = {
.parent_data = gpu_cc_parent_data_0, .parent_data = gpu_cc_parent_data_0,
.num_parents = ARRAY_SIZE(gpu_cc_parent_data_0), .num_parents = ARRAY_SIZE(gpu_cc_parent_data_0),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };
@@ -170,7 +169,7 @@ static struct clk_rcg2 gpu_cc_hub_clk_src = {
.parent_data = gpu_cc_parent_data_1, .parent_data = gpu_cc_parent_data_1,
.num_parents = ARRAY_SIZE(gpu_cc_parent_data_1), .num_parents = ARRAY_SIZE(gpu_cc_parent_data_1),
.flags = CLK_SET_RATE_PARENT, .flags = CLK_SET_RATE_PARENT,
.ops = &clk_rcg2_shared_ops, .ops = &clk_rcg2_ops,
}, },
}; };

0
drivers/clk/qcom/gpucc-sun.c Executable file → Normal file
View File

0
drivers/clk/qcom/gpucc-tuna.c Executable file → Normal file
View File

View File

@@ -63,7 +63,9 @@ static int kpss_xcc_driver_probe(struct platform_device *pdev)
if (IS_ERR(hw)) if (IS_ERR(hw))
return PTR_ERR(hw); return PTR_ERR(hw);
return of_clk_add_hw_provider(dev->of_node, of_clk_hw_simple_get, hw); of_clk_add_hw_provider(dev->of_node, of_clk_hw_simple_get, hw);
return 0;
} }
static struct platform_driver kpss_xcc_driver = { static struct platform_driver kpss_xcc_driver = {

View File

@@ -2535,8 +2535,6 @@ static struct clk_branch vmem_ahb_clk = {
static struct gdsc video_top_gdsc = { static struct gdsc video_top_gdsc = {
.gdscr = 0x1024, .gdscr = 0x1024,
.cxcs = (unsigned int []){ 0x1028, 0x1034, 0x1038 },
.cxc_count = 3,
.pd = { .pd = {
.name = "video_top", .name = "video_top",
}, },
@@ -2545,26 +2543,20 @@ static struct gdsc video_top_gdsc = {
static struct gdsc video_subcore0_gdsc = { static struct gdsc video_subcore0_gdsc = {
.gdscr = 0x1040, .gdscr = 0x1040,
.cxcs = (unsigned int []){ 0x1048 },
.cxc_count = 1,
.pd = { .pd = {
.name = "video_subcore0", .name = "video_subcore0",
}, },
.parent = &video_top_gdsc.pd, .parent = &video_top_gdsc.pd,
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = HW_CTRL,
}; };
static struct gdsc video_subcore1_gdsc = { static struct gdsc video_subcore1_gdsc = {
.gdscr = 0x1044, .gdscr = 0x1044,
.cxcs = (unsigned int []){ 0x104c },
.cxc_count = 1,
.pd = { .pd = {
.name = "video_subcore1", .name = "video_subcore1",
}, },
.parent = &video_top_gdsc.pd, .parent = &video_top_gdsc.pd,
.pwrsts = PWRSTS_OFF_ON, .pwrsts = PWRSTS_OFF_ON,
.flags = HW_CTRL,
}; };
static struct gdsc mdss_gdsc = { static struct gdsc mdss_gdsc = {

View File

@@ -2544,7 +2544,7 @@ static struct clk_branch video_core_clk = {
static struct clk_branch video_subcore0_clk = { static struct clk_branch video_subcore0_clk = {
.halt_reg = 0x1048, .halt_reg = 0x1048,
.halt_check = BRANCH_HALT_SKIP, .halt_check = BRANCH_HALT,
.clkr = { .clkr = {
.enable_reg = 0x1048, .enable_reg = 0x1048,
.enable_mask = BIT(0), .enable_mask = BIT(0),

View File

@@ -1,6 +1,7 @@
// SPDX-License-Identifier: GPL-2.0-only // SPDX-License-Identifier: GPL-2.0-only
/* /*
* Copyright (c) 2013, The Linux Foundation. All rights reserved. * Copyright (c) 2013, The Linux Foundation. All rights reserved.
* Copyright (c) 2023-2024, Qualcomm Innovation Center, Inc. All rights reserved.
*/ */
#include <linux/bitops.h> #include <linux/bitops.h>
@@ -8,16 +9,54 @@
#include <linux/regmap.h> #include <linux/regmap.h>
#include <linux/reset-controller.h> #include <linux/reset-controller.h>
#include <linux/delay.h> #include <linux/delay.h>
#include <linux/pm_runtime.h>
#include "reset.h" #include "reset.h"
#include "trace.h"
static int
qcom_reset_runtime_get(struct qcom_reset_controller *rst)
{
int ret;
if (pm_runtime_enabled(rst->dev)) {
ret = pm_runtime_resume_and_get(rst->dev);
if (ret < 0) {
WARN(1, "ret=%d\n", ret);
return ret;
}
}
return 0;
}
static void
qcom_reset_runtime_put(struct qcom_reset_controller *rst)
{
int ret;
if (pm_runtime_enabled(rst->dev)) {
ret = pm_runtime_put_sync(rst->dev);
if (ret < 0)
WARN(1, "ret=%d\n", ret);
}
}
static void qcom_reset_delay(const struct qcom_reset_map *map)
{
/*
* XO div-4 is commonly used for the reset demets, so by default allow
* enough time for 4 demet cycles at 1.2MHz.
*/
fsleep(map->udelay ?: 4);
}
static int qcom_reset(struct reset_controller_dev *rcdev, unsigned long id) static int qcom_reset(struct reset_controller_dev *rcdev, unsigned long id)
{ {
struct qcom_reset_controller *rst = to_qcom_reset_controller(rcdev); struct qcom_reset_controller *rst = to_qcom_reset_controller(rcdev);
rcdev->ops->assert(rcdev, id); rcdev->ops->assert(rcdev, id);
fsleep(rst->reset_map[id].udelay ?: 1); /* use 1 us as default */ qcom_reset_delay(&rst->reset_map[id]);
rcdev->ops->deassert(rcdev, id); rcdev->ops->deassert(rcdev, id);
return 0; return 0;
} }
@@ -27,21 +66,39 @@ static int qcom_reset_set_assert(struct reset_controller_dev *rcdev,
{ {
struct qcom_reset_controller *rst; struct qcom_reset_controller *rst;
const struct qcom_reset_map *map; const struct qcom_reset_map *map;
u32 mask; u32 mask, val;
int ret = 0;
rst = to_qcom_reset_controller(rcdev); rst = to_qcom_reset_controller(rcdev);
map = &rst->reset_map[id]; map = &rst->reset_map[id];
mask = map->bitmask ? map->bitmask : BIT(map->bit); mask = map->bitmask ? map->bitmask : BIT(map->bit);
regmap_update_bits(rst->regmap, map->reg, mask, assert ? mask : 0); ret = qcom_reset_runtime_get(rst);
if (ret < 0)
return ret;
/* Read back the register to ensure write completion, ignore the value */ trace_clk_reset(rst, id, assert);
regmap_read(rst->regmap, map->reg, &mask);
return 0; ret = regmap_update_bits(rst->regmap, map->reg, mask, assert ? mask : 0);
if (ret)
goto err;
/* Ensure the write is fully propagated to the register. */
ret = regmap_read(rst->regmap, map->reg, &val);
if (ret)
goto err;
/* Give demets a chance to propagate the signal. */
qcom_reset_delay(map);
err:
qcom_reset_runtime_put(rst);
return ret;
} }
static int qcom_reset_assert(struct reset_controller_dev *rcdev, unsigned long id) static int
qcom_reset_assert(struct reset_controller_dev *rcdev, unsigned long id)
{ {
return qcom_reset_set_assert(rcdev, id, true); return qcom_reset_set_assert(rcdev, id, true);
} }
@@ -51,9 +108,37 @@ static int qcom_reset_deassert(struct reset_controller_dev *rcdev, unsigned long
return qcom_reset_set_assert(rcdev, id, false); return qcom_reset_set_assert(rcdev, id, false);
} }
static int
qcom_reset_status(struct reset_controller_dev *rcdev, unsigned long id)
{
struct qcom_reset_controller *rst;
const struct qcom_reset_map *map;
u32 mask, reg;
int ret;
rst = to_qcom_reset_controller(rcdev);
map = &rst->reset_map[id];
mask = map->bitmask ? map->bitmask : BIT(map->bit);
ret = qcom_reset_runtime_get(rst);
if (ret < 0)
return ret;
ret = regmap_read(rst->regmap, map->reg, &reg);
if (ret) {
qcom_reset_runtime_put(rst);
return ret;
}
qcom_reset_runtime_put(rst);
return (reg & mask);
}
const struct reset_control_ops qcom_reset_ops = { const struct reset_control_ops qcom_reset_ops = {
.reset = qcom_reset, .reset = qcom_reset,
.assert = qcom_reset_assert, .assert = qcom_reset_assert,
.deassert = qcom_reset_deassert, .deassert = qcom_reset_deassert,
.status = qcom_reset_status,
}; };
EXPORT_SYMBOL_GPL(qcom_reset_ops); EXPORT_SYMBOL_GPL(qcom_reset_ops);

Some files were not shown because too many files have changed in this diff Show More