@ -137,6 +137,33 @@ static void sunxi_dma_init(volatile u8 *port_mmio)
}
# endif
int ahci_reset ( u32 base )
{
int i = 1000 ;
u32 host_ctl_reg = base + HOST_CTL ;
u32 tmp = readl ( host_ctl_reg ) ; /* global controller reset */
if ( ( tmp & HOST_RESET ) = = 0 )
writel_with_flush ( tmp | HOST_RESET , host_ctl_reg ) ;
/*
* reset must complete within 1 second , or
* the hardware should be considered fried .
*/
do {
udelay ( 1000 ) ;
tmp = readl ( host_ctl_reg ) ;
i - - ;
} while ( ( i > 0 ) & & ( tmp & HOST_RESET ) ) ;
if ( i = = 0 ) {
printf ( " controller reset failed (0x%x) \n " , tmp ) ;
return - 1 ;
}
return 0 ;
}
static int ahci_host_init ( struct ahci_probe_ent * probe_ent )
{
# ifndef CONFIG_SCSI_AHCI_PLAT
@ -156,23 +183,9 @@ static int ahci_host_init(struct ahci_probe_ent *probe_ent)
cap_save & = ( ( 1 < < 28 ) | ( 1 < < 17 ) ) ;
cap_save | = ( 1 < < 27 ) ; /* Staggered Spin-up. Not needed. */
/* global controller reset */
tmp = readl ( mmio + HOST_CTL ) ;
if ( ( tmp & HOST_RESET ) = = 0 )
writel_with_flush ( tmp | HOST_RESET , mmio + HOST_CTL ) ;
/* reset must complete within 1 second, or
* the hardware should be considered fried .
*/
i = 1000 ;
do {
udelay ( 1000 ) ;
tmp = readl ( mmio + HOST_CTL ) ;
if ( ! i - - ) {
debug ( " controller reset failed (0x%x) \n " , tmp ) ;
return - 1 ;
}
} while ( tmp & HOST_RESET ) ;
ret = ahci_reset ( probe_ent - > mmio_base ) ;
if ( ret )
return ret ;
writel_with_flush ( HOST_AHCI_EN , mmio + HOST_CTL ) ;
writel ( cap_save , mmio + HOST_CAP ) ;