@@ -192,6 +192,8 @@ struct dwc3_octeon {
192
192
void __iomem * base ;
193
193
};
194
194
195
+ #define DWC3_GPIO_POWER_NONE (-1)
196
+
195
197
#ifdef CONFIG_CAVIUM_OCTEON_SOC
196
198
#include <asm/octeon/octeon.h>
197
199
static inline uint64_t dwc3_octeon_readq (void __iomem * addr )
@@ -258,55 +260,15 @@ static int dwc3_octeon_get_divider(void)
258
260
return div ;
259
261
}
260
262
261
- static int dwc3_octeon_config_power (struct device * dev , void __iomem * base )
262
- {
263
- uint32_t gpio_pwr [3 ];
264
- int gpio , len , power_active_low ;
265
- struct device_node * node = dev -> of_node ;
266
- u64 val ;
267
- void __iomem * uctl_host_cfg_reg = base + USBDRD_UCTL_HOST_CFG ;
268
-
269
- if (of_find_property (node , "power" , & len ) != NULL ) {
270
- if (len == 12 ) {
271
- of_property_read_u32_array (node , "power" , gpio_pwr , 3 );
272
- power_active_low = gpio_pwr [2 ] & 0x01 ;
273
- gpio = gpio_pwr [1 ];
274
- } else if (len == 8 ) {
275
- of_property_read_u32_array (node , "power" , gpio_pwr , 2 );
276
- power_active_low = 0 ;
277
- gpio = gpio_pwr [1 ];
278
- } else {
279
- dev_err (dev , "invalid power configuration\n" );
280
- return - EINVAL ;
281
- }
282
- dwc3_octeon_config_gpio (((u64 )base >> 24 ) & 1 , gpio );
283
-
284
- /* Enable XHCI power control and set if active high or low. */
285
- val = dwc3_octeon_readq (uctl_host_cfg_reg );
286
- val |= USBDRD_UCTL_HOST_PPC_EN ;
287
- if (power_active_low )
288
- val &= ~USBDRD_UCTL_HOST_PPC_ACTIVE_HIGH_EN ;
289
- else
290
- val |= USBDRD_UCTL_HOST_PPC_ACTIVE_HIGH_EN ;
291
- dwc3_octeon_writeq (uctl_host_cfg_reg , val );
292
- } else {
293
- /* Disable XHCI power control and set if active high. */
294
- val = dwc3_octeon_readq (uctl_host_cfg_reg );
295
- val &= ~USBDRD_UCTL_HOST_PPC_EN ;
296
- val &= ~USBDRD_UCTL_HOST_PPC_ACTIVE_HIGH_EN ;
297
- dwc3_octeon_writeq (uctl_host_cfg_reg , val );
298
- dev_info (dev , "power control disabled\n" );
299
- }
300
- return 0 ;
301
- }
302
-
303
- static int dwc3_octeon_clocks_start (struct dwc3_octeon * octeon )
263
+ static int dwc3_octeon_setup (struct dwc3_octeon * octeon ,
264
+ int power_gpio , int power_active_low )
304
265
{
305
266
int i , div , mpll_mul , ref_clk_fsel , ref_clk_sel = 2 ;
306
267
u32 clock_rate ;
307
268
u64 val ;
308
269
struct device * dev = octeon -> dev ;
309
270
void __iomem * uctl_ctl_reg = octeon -> base + USBDRD_UCTL_CTL ;
271
+ void __iomem * uctl_host_cfg_reg = octeon -> base + USBDRD_UCTL_HOST_CFG ;
310
272
311
273
if (dev -> of_node ) {
312
274
const char * ss_clock_type ;
@@ -454,8 +416,21 @@ static int dwc3_octeon_clocks_start(struct dwc3_octeon *octeon)
454
416
udelay (10 );
455
417
456
418
/* Step 8c: Setup power control. */
457
- if (dwc3_octeon_config_power (dev , octeon -> base ))
458
- return - EINVAL ;
419
+ val = dwc3_octeon_readq (uctl_host_cfg_reg );
420
+ val |= USBDRD_UCTL_HOST_PPC_EN ;
421
+ if (power_gpio == DWC3_GPIO_POWER_NONE ) {
422
+ val &= ~USBDRD_UCTL_HOST_PPC_EN ;
423
+ } else {
424
+ val |= USBDRD_UCTL_HOST_PPC_EN ;
425
+ dwc3_octeon_config_gpio (((__force uintptr_t )octeon -> base >> 24 ) & 1 ,
426
+ power_gpio );
427
+ dev_dbg (dev , "power control is using gpio%d\n" , power_gpio );
428
+ }
429
+ if (power_active_low )
430
+ val &= ~USBDRD_UCTL_HOST_PPC_ACTIVE_HIGH_EN ;
431
+ else
432
+ val |= USBDRD_UCTL_HOST_PPC_ACTIVE_HIGH_EN ;
433
+ dwc3_octeon_writeq (uctl_host_cfg_reg , val );
459
434
460
435
/* Step 8d: Deassert UAHC reset signal. */
461
436
val = dwc3_octeon_readq (uctl_ctl_reg );
@@ -508,7 +483,28 @@ static int dwc3_octeon_probe(struct platform_device *pdev)
508
483
struct device * dev = & pdev -> dev ;
509
484
struct device_node * node = dev -> of_node ;
510
485
struct dwc3_octeon * octeon ;
511
- int err ;
486
+ int power_active_low , power_gpio ;
487
+ int err , len ;
488
+
489
+ power_gpio = DWC3_GPIO_POWER_NONE ;
490
+ power_active_low = 0 ;
491
+ if (of_find_property (node , "power" , & len )) {
492
+ u32 gpio_pwr [3 ];
493
+
494
+ switch (len ) {
495
+ case 8 :
496
+ of_property_read_u32_array (node , "power" , gpio_pwr , 2 );
497
+ break ;
498
+ case 12 :
499
+ of_property_read_u32_array (node , "power" , gpio_pwr , 3 );
500
+ power_active_low = gpio_pwr [2 ] & 0x01 ;
501
+ break ;
502
+ default :
503
+ dev_err (dev , "invalid power configuration\n" );
504
+ return - EINVAL ;
505
+ }
506
+ power_gpio = gpio_pwr [1 ];
507
+ }
512
508
513
509
octeon = devm_kzalloc (dev , sizeof (* octeon ), GFP_KERNEL );
514
510
if (!octeon )
@@ -519,7 +515,7 @@ static int dwc3_octeon_probe(struct platform_device *pdev)
519
515
if (IS_ERR (octeon -> base ))
520
516
return PTR_ERR (octeon -> base );
521
517
522
- err = dwc3_octeon_clocks_start (octeon );
518
+ err = dwc3_octeon_setup (octeon , power_gpio , power_active_low );
523
519
if (err )
524
520
return err ;
525
521
0 commit comments