blob: 490fb0e25d8ca4c5c80ff5fd40ba3e0cd9d6247e [file] [log] [blame]
Jana Rapavaa5235952011-12-05 11:07:00 +02001/*
2 * Copyright (C) 2011 Jana Rapava <fermata7@gmail.com>
3 * Copyright (C) 2011 CompuLab, Ltd. <www.compulab.co.il>
4 *
5 * Authors: Jana Rapava <fermata7@gmail.com>
6 * Igor Grinberg <grinberg@compulab.co.il>
7 *
8 * Based on:
9 * linux/drivers/usb/otg/ulpi_viewport.c
10 *
11 * Original Copyright follow:
12 * Copyright (C) 2011 Google, Inc.
13 *
14 * This software is licensed under the terms of the GNU General Public
15 * License version 2, as published by the Free Software Foundation, and
16 * may be copied, distributed, and modified under those terms.
17 *
18 * This program is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU General Public License for more details.
22 *
23 */
24
25#include <common.h>
26#include <asm/io.h>
27#include <usb/ulpi.h>
28
29/* ULPI viewport control bits */
30#define ULPI_SS (1 << 27)
31#define ULPI_RWCTRL (1 << 29)
32#define ULPI_RWRUN (1 << 30)
33#define ULPI_WU (1 << 31)
34
35/*
36 * Wait for the ULPI request to complete
37 *
38 * @ulpi_viewport - the address of the viewport
39 * @mask - expected value to wait for
40 *
41 * returns 0 on mask match, ULPI_ERROR on time out.
42 */
43static int ulpi_wait(u32 ulpi_viewport, u32 mask)
44{
45 int timeout = CONFIG_USB_ULPI_TIMEOUT;
46
47 /* Wait for the bits in mask to become zero. */
48 while (--timeout) {
49 if ((readl(ulpi_viewport) & mask) == 0)
50 return 0;
51
52 udelay(1);
53 }
54
55 return ULPI_ERROR;
56}
57
58/*
59 * Wake the ULPI PHY up for communication
60 *
61 * returns 0 on success.
62 */
63static int ulpi_wakeup(u32 ulpi_viewport)
64{
65 int err;
66
67 if (readl(ulpi_viewport) & ULPI_SS)
68 return 0; /* already awake */
69
70 writel(ULPI_WU, ulpi_viewport);
71
72 err = ulpi_wait(ulpi_viewport, ULPI_WU);
73 if (err)
74 printf("ULPI wakeup timed out\n");
75
76 return err;
77}
78
79/*
80 * Issue a ULPI read/write request
81 *
82 * @value - the ULPI request
83 */
84static int ulpi_request(u32 ulpi_viewport, u32 value)
85{
86 int err;
87
88 err = ulpi_wakeup(ulpi_viewport);
89 if (err)
90 return err;
91
92 writel(value, ulpi_viewport);
93
94 err = ulpi_wait(ulpi_viewport, ULPI_RWRUN);
95 if (err)
96 printf("ULPI request timed out\n");
97
98 return err;
99}
100
Igor Grinberg7b4d7682011-12-12 12:08:33 +0200101int ulpi_write(u32 ulpi_viewport, u8 *reg, u32 value)
Jana Rapavaa5235952011-12-05 11:07:00 +0200102{
103 u32 val = ULPI_RWRUN | ULPI_RWCTRL | ((u32)reg << 16) | (value & 0xff);
104
105 return ulpi_request(ulpi_viewport, val);
106}
107
108u32 ulpi_read(u32 ulpi_viewport, u8 *reg)
109{
Igor Grinberg7b4d7682011-12-12 12:08:33 +0200110 int err;
Jana Rapavaa5235952011-12-05 11:07:00 +0200111 u32 val = ULPI_RWRUN | ((u32)reg << 16);
112
113 err = ulpi_request(ulpi_viewport, val);
114 if (err)
115 return err;
116
117 return (readl(ulpi_viewport) >> 8) & 0xff;
118}