2011-03-10 03:28:54 +03:00
/*
* Copyright ( C ) 2011 Google , Inc .
*
* This software is licensed under the terms of the GNU General Public
* License version 2 , as published by the Free Software Foundation , and
* may be copied , distributed , and modified under those terms .
*
* This program is distributed in the hope that it will be useful ,
* but WITHOUT ANY WARRANTY ; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the
* GNU General Public License for more details .
*
*/
2013-06-13 21:24:07 +04:00
# include <linux/export.h>
2011-03-10 03:28:54 +03:00
# include <linux/kernel.h>
# include <linux/usb.h>
# include <linux/io.h>
# include <linux/usb/otg.h>
# include <linux/usb/ulpi.h>
# define ULPI_VIEW_WAKEUP (1 << 31)
# define ULPI_VIEW_RUN (1 << 30)
# define ULPI_VIEW_WRITE (1 << 29)
# define ULPI_VIEW_READ (0 << 29)
# define ULPI_VIEW_ADDR(x) (((x) & 0xff) << 16)
# define ULPI_VIEW_DATA_READ(x) (((x) >> 8) & 0xff)
# define ULPI_VIEW_DATA_WRITE(x) ((x) & 0xff)
static int ulpi_viewport_wait ( void __iomem * view , u32 mask )
{
unsigned long usec = 2000 ;
while ( usec - - ) {
if ( ! ( readl ( view ) & mask ) )
return 0 ;
udelay ( 1 ) ;
2013-10-09 03:01:37 +04:00
}
2011-03-10 03:28:54 +03:00
return - ETIMEDOUT ;
}
2012-02-13 15:24:02 +04:00
static int ulpi_viewport_read ( struct usb_phy * otg , u32 reg )
2011-03-10 03:28:54 +03:00
{
int ret ;
void __iomem * view = otg - > io_priv ;
writel ( ULPI_VIEW_WAKEUP | ULPI_VIEW_WRITE , view ) ;
ret = ulpi_viewport_wait ( view , ULPI_VIEW_WAKEUP ) ;
if ( ret )
return ret ;
writel ( ULPI_VIEW_RUN | ULPI_VIEW_READ | ULPI_VIEW_ADDR ( reg ) , view ) ;
ret = ulpi_viewport_wait ( view , ULPI_VIEW_RUN ) ;
if ( ret )
return ret ;
return ULPI_VIEW_DATA_READ ( readl ( view ) ) ;
}
2012-02-13 15:24:02 +04:00
static int ulpi_viewport_write ( struct usb_phy * otg , u32 val , u32 reg )
2011-03-10 03:28:54 +03:00
{
int ret ;
void __iomem * view = otg - > io_priv ;
writel ( ULPI_VIEW_WAKEUP | ULPI_VIEW_WRITE , view ) ;
ret = ulpi_viewport_wait ( view , ULPI_VIEW_WAKEUP ) ;
if ( ret )
return ret ;
writel ( ULPI_VIEW_RUN | ULPI_VIEW_WRITE | ULPI_VIEW_DATA_WRITE ( val ) |
ULPI_VIEW_ADDR ( reg ) , view ) ;
return ulpi_viewport_wait ( view , ULPI_VIEW_RUN ) ;
}
2012-02-13 15:24:13 +04:00
struct usb_phy_io_ops ulpi_viewport_access_ops = {
2011-03-10 03:28:54 +03:00
. read = ulpi_viewport_read ,
. write = ulpi_viewport_write ,
} ;
2013-06-13 21:24:07 +04:00
EXPORT_SYMBOL_GPL ( ulpi_viewport_access_ops ) ;