55 * Copyright (C) 2025 Renesas Electronics Corporation
66 */
77
8- #include <linux/cleanup.h>
98#include <linux/delay.h>
109#include <linux/io.h>
1110#include <linux/module.h>
1211#include <linux/of.h>
1312#include <linux/platform_device.h>
1413#include <linux/pm_runtime.h>
14+ #include <linux/regmap.h>
1515#include <linux/reset.h>
1616#include <linux/reset-controller.h>
1717
18- struct rzv2h_usb2phy_regval {
19- u16 reg ;
20- u16 val ;
21- };
22-
2318struct rzv2h_usb2phy_reset_of_data {
24- const struct rzv2h_usb2phy_regval * init_vals ;
25- unsigned int init_val_count ;
19+ const struct reg_sequence * init_seq ;
20+ unsigned int init_nseq ;
21+
22+ const struct reg_sequence * assert_seq ;
23+ unsigned int assert_nseq ;
24+
25+ const struct reg_sequence * deassert_seq ;
26+ unsigned int deassert_nseq ;
2627
2728 u16 reset_reg ;
28- u16 reset_assert_val ;
29- u16 reset_deassert_val ;
3029 u16 reset_status_bits ;
31- u16 reset_release_val ;
32-
33- u16 reset2_reg ;
34- u16 reset2_acquire_val ;
35- u16 reset2_release_val ;
3630};
3731
3832struct rzv2h_usb2phy_reset_priv {
3933 const struct rzv2h_usb2phy_reset_of_data * data ;
40- void __iomem * base ;
34+ struct regmap * regmap ;
4135 struct device * dev ;
4236 struct reset_controller_dev rcdev ;
43- spinlock_t lock ; /* protects register accesses */
4437};
4538
4639static inline struct rzv2h_usb2phy_reset_priv
@@ -53,31 +46,18 @@ static int rzv2h_usbphy_reset_assert(struct reset_controller_dev *rcdev,
5346 unsigned long id )
5447{
5548 struct rzv2h_usb2phy_reset_priv * priv = rzv2h_usbphy_rcdev_to_priv (rcdev );
56- const struct rzv2h_usb2phy_reset_of_data * data = priv -> data ;
5749
58- scoped_guard (spinlock , & priv -> lock ) {
59- writel (data -> reset2_acquire_val , priv -> base + data -> reset2_reg );
60- writel (data -> reset_assert_val , priv -> base + data -> reset_reg );
61- }
62-
63- usleep_range (11 , 20 );
64-
65- return 0 ;
50+ return regmap_multi_reg_write (priv -> regmap , priv -> data -> assert_seq ,
51+ priv -> data -> assert_nseq );
6652}
6753
6854static int rzv2h_usbphy_reset_deassert (struct reset_controller_dev * rcdev ,
6955 unsigned long id )
7056{
7157 struct rzv2h_usb2phy_reset_priv * priv = rzv2h_usbphy_rcdev_to_priv (rcdev );
72- const struct rzv2h_usb2phy_reset_of_data * data = priv -> data ;
7358
74- scoped_guard (spinlock , & priv -> lock ) {
75- writel (data -> reset_deassert_val , priv -> base + data -> reset_reg );
76- writel (data -> reset2_release_val , priv -> base + data -> reset2_reg );
77- writel (data -> reset_release_val , priv -> base + data -> reset_reg );
78- }
79-
80- return 0 ;
59+ return regmap_multi_reg_write (priv -> regmap , priv -> data -> deassert_seq ,
60+ priv -> data -> deassert_nseq );
8161}
8262
8363static int rzv2h_usbphy_reset_status (struct reset_controller_dev * rcdev ,
@@ -86,7 +66,7 @@ static int rzv2h_usbphy_reset_status(struct reset_controller_dev *rcdev,
8666 struct rzv2h_usb2phy_reset_priv * priv = rzv2h_usbphy_rcdev_to_priv (rcdev );
8767 u32 reg ;
8868
89- reg = readl (priv -> base + priv -> data -> reset_reg );
69+ regmap_read (priv -> regmap , priv -> data -> reset_reg , & reg );
9070
9171 return (reg & priv -> data -> reset_status_bits ) == priv -> data -> reset_status_bits ;
9272}
@@ -104,6 +84,13 @@ static int rzv2h_usb2phy_reset_of_xlate(struct reset_controller_dev *rcdev,
10484 return 0 ;
10585}
10686
87+ static const struct regmap_config rzv2h_usb2phy_reset_regconf = {
88+ .reg_bits = 32 ,
89+ .val_bits = 32 ,
90+ .reg_stride = 4 ,
91+ .can_sleep = true,
92+ };
93+
10794static void rzv2h_usb2phy_reset_pm_runtime_put (void * data )
10895{
10996 pm_runtime_put (data );
@@ -115,6 +102,7 @@ static int rzv2h_usb2phy_reset_probe(struct platform_device *pdev)
115102 struct rzv2h_usb2phy_reset_priv * priv ;
116103 struct device * dev = & pdev -> dev ;
117104 struct reset_control * rstc ;
105+ void __iomem * base ;
118106 int error ;
119107
120108 priv = devm_kzalloc (dev , sizeof (* priv ), GFP_KERNEL );
@@ -124,17 +112,19 @@ static int rzv2h_usb2phy_reset_probe(struct platform_device *pdev)
124112 data = of_device_get_match_data (dev );
125113 priv -> data = data ;
126114 priv -> dev = dev ;
127- priv -> base = devm_platform_ioremap_resource (pdev , 0 );
128- if (IS_ERR (priv -> base ))
129- return PTR_ERR (priv -> base );
115+ base = devm_platform_ioremap_resource (pdev , 0 );
116+ if (IS_ERR (base ))
117+ return PTR_ERR (base );
118+
119+ priv -> regmap = devm_regmap_init_mmio (dev , base , & rzv2h_usb2phy_reset_regconf );
120+ if (IS_ERR (priv -> regmap ))
121+ return PTR_ERR (priv -> regmap );
130122
131123 rstc = devm_reset_control_get_shared_deasserted (dev , NULL );
132124 if (IS_ERR (rstc ))
133125 return dev_err_probe (dev , PTR_ERR (rstc ),
134126 "failed to get deasserted reset\n" );
135127
136- spin_lock_init (& priv -> lock );
137-
138128 error = devm_pm_runtime_enable (dev );
139129 if (error )
140130 return dev_err_probe (dev , error , "Failed to enable pm_runtime\n" );
@@ -148,8 +138,9 @@ static int rzv2h_usb2phy_reset_probe(struct platform_device *pdev)
148138 if (error )
149139 return dev_err_probe (dev , error , "unable to register cleanup action\n" );
150140
151- for (unsigned int i = 0 ; i < data -> init_val_count ; i ++ )
152- writel (data -> init_vals [i ].val , priv -> base + data -> init_vals [i ].reg );
141+ error = regmap_multi_reg_write (priv -> regmap , data -> init_seq , data -> init_nseq );
142+ if (error )
143+ return dev_err_probe (dev , error , "failed to initialize PHY registers\n" );
153144
154145 priv -> rcdev .ops = & rzv2h_usbphy_reset_ops ;
155146 priv -> rcdev .of_reset_n_cells = 0 ;
@@ -169,23 +160,32 @@ static int rzv2h_usb2phy_reset_probe(struct platform_device *pdev)
169160 * initialization values required to prepare the PHY to receive
170161 * assert and deassert requests.
171162 */
172- static const struct rzv2h_usb2phy_regval rzv2h_init_vals [] = {
173- { .reg = 0xc10 , .val = 0x67c },
174- { .reg = 0xc14 , .val = 0x1f },
175- { .reg = 0x600 , .val = 0x909 },
163+ static const struct reg_sequence rzv2h_init_seq [] = {
164+ { .reg = 0xc10 , .def = 0x67c },
165+ { .reg = 0xc14 , .def = 0x01f },
166+ { .reg = 0x600 , .def = 0x909 },
167+ };
168+
169+ static const struct reg_sequence rzv2h_assert_seq [] = {
170+ { .reg = 0xb04 , .def = 0x303 },
171+ { .reg = 0x000 , .def = 0x206 , .delay_us = 11 },
172+ };
173+
174+ static const struct reg_sequence rzv2h_deassert_seq [] = {
175+ { .reg = 0x000 , .def = 0x200 },
176+ { .reg = 0xb04 , .def = 0x003 },
177+ { .reg = 0x000 , .def = 0x000 },
176178};
177179
178180static const struct rzv2h_usb2phy_reset_of_data rzv2h_reset_of_data = {
179- .init_vals = rzv2h_init_vals ,
180- .init_val_count = ARRAY_SIZE (rzv2h_init_vals ),
181+ .init_seq = rzv2h_init_seq ,
182+ .init_nseq = ARRAY_SIZE (rzv2h_init_seq ),
183+ .assert_seq = rzv2h_assert_seq ,
184+ .assert_nseq = ARRAY_SIZE (rzv2h_assert_seq ),
185+ .deassert_seq = rzv2h_deassert_seq ,
186+ .deassert_nseq = ARRAY_SIZE (rzv2h_deassert_seq ),
181187 .reset_reg = 0 ,
182- .reset_assert_val = 0x206 ,
183188 .reset_status_bits = BIT (2 ),
184- .reset_deassert_val = 0x200 ,
185- .reset_release_val = 0x0 ,
186- .reset2_reg = 0xb04 ,
187- .reset2_acquire_val = 0x303 ,
188- .reset2_release_val = 0x3 ,
189189};
190190
191191static const struct of_device_id rzv2h_usb2phy_reset_of_match [] = {
0 commit comments