aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/usb/c67x00/c67x00.h
diff options
context:
space:
mode:
authorPeter Korsgaard <jacmet@sunsite.dk>2008-04-27 02:59:43 -0400
committerGreg Kroah-Hartman <gregkh@suse.de>2008-05-02 13:25:56 -0400
commitd6f945044ee3b91a170183e8e34c3db29696d9b8 (patch)
treefba0b46ad13f25aca8751198365a12f80fc26d15 /drivers/usb/c67x00/c67x00.h
parent21ae1dd1d4948968ad2d923c5e104d38fb35b4e4 (diff)
USB: add Cypress c67x00 low level interface code
This patch adds the low level support code for the Cypress c67x00 family of OTG controllers. The low level code is responsible for register access and implements the software protocol for communicating with the 16bit microcontroller inside the c67x00 device. Communication is done over the HPI interface (16bit SRAM-like parallel bus). Signed-off-by: Peter Korsgaard <jacmet@sunsite.dk> Acked-by: David Brownell <dbrownell@users.sourceforge.net> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/usb/c67x00/c67x00.h')
-rw-r--r--drivers/usb/c67x00/c67x00.h285
1 files changed, 285 insertions, 0 deletions
diff --git a/drivers/usb/c67x00/c67x00.h b/drivers/usb/c67x00/c67x00.h
new file mode 100644
index 000000000000..1f1a2eef9a22
--- /dev/null
+++ b/drivers/usb/c67x00/c67x00.h
@@ -0,0 +1,285 @@
1/*
2 * c67x00.h: Cypress C67X00 USB register and field definitions
3 *
4 * Copyright (C) 2006-2008 Barco N.V.
5 * Derived from the Cypress cy7c67200/300 ezusb linux driver and
6 * based on multiple host controller drivers inside the linux kernel.
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License
19 * along with this program; if not, write to the Free Software
20 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
21 * MA 02110-1301 USA.
22 */
23
24#ifndef _USB_C67X00_H
25#define _USB_C67X00_H
26
27#include <linux/spinlock.h>
28#include <linux/platform_device.h>
29#include <linux/completion.h>
30#include <linux/mutex.h>
31
32/* ---------------------------------------------------------------------
33 * Cypress C67x00 register definitions
34 */
35
36/* Hardware Revision Register */
37#define HW_REV_REG 0xC004
38
39/* General USB registers */
40/* ===================== */
41
42/* USB Control Register */
43#define USB_CTL_REG(x) ((x) ? 0xC0AA : 0xC08A)
44
45#define LOW_SPEED_PORT(x) ((x) ? 0x0800 : 0x0400)
46#define HOST_MODE 0x0200
47#define PORT_RES_EN(x) ((x) ? 0x0100 : 0x0080)
48#define SOF_EOP_EN(x) ((x) ? 0x0002 : 0x0001)
49
50/* USB status register - Notice it has different content in hcd/udc mode */
51#define USB_STAT_REG(x) ((x) ? 0xC0B0 : 0xC090)
52
53#define EP0_IRQ_FLG 0x0001
54#define EP1_IRQ_FLG 0x0002
55#define EP2_IRQ_FLG 0x0004
56#define EP3_IRQ_FLG 0x0008
57#define EP4_IRQ_FLG 0x0010
58#define EP5_IRQ_FLG 0x0020
59#define EP6_IRQ_FLG 0x0040
60#define EP7_IRQ_FLG 0x0080
61#define RESET_IRQ_FLG 0x0100
62#define SOF_EOP_IRQ_FLG 0x0200
63#define ID_IRQ_FLG 0x4000
64#define VBUS_IRQ_FLG 0x8000
65
66/* USB Host only registers */
67/* ======================= */
68
69/* Host n Control Register */
70#define HOST_CTL_REG(x) ((x) ? 0xC0A0 : 0xC080)
71
72#define PREAMBLE_EN 0x0080 /* Preamble enable */
73#define SEQ_SEL 0x0040 /* Data Toggle Sequence Bit Select */
74#define ISO_EN 0x0010 /* Isochronous enable */
75#define ARM_EN 0x0001 /* Arm operation */
76
77/* Host n Interrupt Enable Register */
78#define HOST_IRQ_EN_REG(x) ((x) ? 0xC0AC : 0xC08C)
79
80#define SOF_EOP_IRQ_EN 0x0200 /* SOF/EOP Interrupt Enable */
81#define SOF_EOP_TMOUT_IRQ_EN 0x0800 /* SOF/EOP Timeout Interrupt Enable */
82#define ID_IRQ_EN 0x4000 /* ID interrupt enable */
83#define VBUS_IRQ_EN 0x8000 /* VBUS interrupt enable */
84#define DONE_IRQ_EN 0x0001 /* Done Interrupt Enable */
85
86/* USB status register */
87#define HOST_STAT_MASK 0x02FD
88#define PORT_CONNECT_CHANGE(x) ((x) ? 0x0020 : 0x0010)
89#define PORT_SE0_STATUS(x) ((x) ? 0x0008 : 0x0004)
90
91/* Host Frame Register */
92#define HOST_FRAME_REG(x) ((x) ? 0xC0B6 : 0xC096)
93
94#define HOST_FRAME_MASK 0x07FF
95
96/* USB Peripheral only registers */
97/* ============================= */
98
99/* Device n Port Sel reg */
100#define DEVICE_N_PORT_SEL(x) ((x) ? 0xC0A4 : 0xC084)
101
102/* Device n Interrupt Enable Register */
103#define DEVICE_N_IRQ_EN_REG(x) ((x) ? 0xC0AC : 0xC08C)
104
105#define DEVICE_N_ENDPOINT_N_CTL_REG(dev, ep) ((dev) \
106 ? (0x0280 + (ep << 4)) \
107 : (0x0200 + (ep << 4)))
108#define DEVICE_N_ENDPOINT_N_STAT_REG(dev, ep) ((dev) \
109 ? (0x0286 + (ep << 4)) \
110 : (0x0206 + (ep << 4)))
111
112#define DEVICE_N_ADDRESS(dev) ((dev) ? (0xC0AE) : (0xC08E))
113
114/* HPI registers */
115/* ============= */
116
117/* HPI Status register */
118#define SOFEOP_FLG(x) (1 << ((x) ? 12 : 10))
119#define SIEMSG_FLG(x) (1 << (4 + (x)))
120#define RESET_FLG(x) ((x) ? 0x0200 : 0x0002)
121#define DONE_FLG(x) (1 << (2 + (x)))
122#define RESUME_FLG(x) (1 << (6 + (x)))
123#define MBX_OUT_FLG 0x0001 /* Message out available */
124#define MBX_IN_FLG 0x0100
125#define ID_FLG 0x4000
126#define VBUS_FLG 0x8000
127
128/* Interrupt routing register */
129#define HPI_IRQ_ROUTING_REG 0x0142
130
131#define HPI_SWAP_ENABLE(x) ((x) ? 0x0100 : 0x0001)
132#define RESET_TO_HPI_ENABLE(x) ((x) ? 0x0200 : 0x0002)
133#define DONE_TO_HPI_ENABLE(x) ((x) ? 0x0008 : 0x0004)
134#define RESUME_TO_HPI_ENABLE(x) ((x) ? 0x0080 : 0x0040)
135#define SOFEOP_TO_HPI_EN(x) ((x) ? 0x2000 : 0x0800)
136#define SOFEOP_TO_CPU_EN(x) ((x) ? 0x1000 : 0x0400)
137#define ID_TO_HPI_ENABLE 0x4000
138#define VBUS_TO_HPI_ENABLE 0x8000
139
140/* SIE msg registers */
141#define SIEMSG_REG(x) ((x) ? 0x0148 : 0x0144)
142
143#define HUSB_TDListDone 0x1000
144
145#define SUSB_EP0_MSG 0x0001
146#define SUSB_EP1_MSG 0x0002
147#define SUSB_EP2_MSG 0x0004
148#define SUSB_EP3_MSG 0x0008
149#define SUSB_EP4_MSG 0x0010
150#define SUSB_EP5_MSG 0x0020
151#define SUSB_EP6_MSG 0x0040
152#define SUSB_EP7_MSG 0x0080
153#define SUSB_RST_MSG 0x0100
154#define SUSB_SOF_MSG 0x0200
155#define SUSB_CFG_MSG 0x0400
156#define SUSB_SUS_MSG 0x0800
157#define SUSB_ID_MSG 0x4000
158#define SUSB_VBUS_MSG 0x8000
159
160/* BIOS interrupt routines */
161
162#define SUSBx_RECEIVE_INT(x) ((x) ? 97 : 81)
163#define SUSBx_SEND_INT(x) ((x) ? 96 : 80)
164
165#define SUSBx_DEV_DESC_VEC(x) ((x) ? 0x00D4 : 0x00B4)
166#define SUSBx_CONF_DESC_VEC(x) ((x) ? 0x00D6 : 0x00B6)
167#define SUSBx_STRING_DESC_VEC(x) ((x) ? 0x00D8 : 0x00B8)
168
169#define CY_HCD_BUF_ADDR 0x500 /* Base address for host */
170#define SIE_TD_SIZE 0x200 /* size of the td list */
171#define SIE_TD_BUF_SIZE 0x400 /* size of the data buffer */
172
173#define SIE_TD_OFFSET(host) ((host) ? (SIE_TD_SIZE+SIE_TD_BUF_SIZE) : 0)
174#define SIE_BUF_OFFSET(host) (SIE_TD_OFFSET(host) + SIE_TD_SIZE)
175
176/* Base address of HCD + 2 x TD_SIZE + 2 x TD_BUF_SIZE */
177#define CY_UDC_REQ_HEADER_BASE 0x1100
178/* 8- byte request headers for IN/OUT transfers */
179#define CY_UDC_REQ_HEADER_SIZE 8
180
181#define CY_UDC_REQ_HEADER_ADDR(ep_num) (CY_UDC_REQ_HEADER_BASE + \
182 ((ep_num) * CY_UDC_REQ_HEADER_SIZE))
183#define CY_UDC_DESC_BASE_ADDRESS (CY_UDC_REQ_HEADER_ADDR(8))
184
185#define CY_UDC_BIOS_REPLACE_BASE 0x1800
186#define CY_UDC_REQ_BUFFER_BASE 0x2000
187#define CY_UDC_REQ_BUFFER_SIZE 0x0400
188#define CY_UDC_REQ_BUFFER_ADDR(ep_num) (CY_UDC_REQ_BUFFER_BASE + \
189 ((ep_num) * CY_UDC_REQ_BUFFER_SIZE))
190
191/* ---------------------------------------------------------------------
192 * Driver data structures
193 */
194
195struct c67x00_device;
196
197/**
198 * struct c67x00_sie - Common data associated with a SIE
199 * @lock: lock to protect this struct and the associated chip registers
200 * @private_data: subdriver dependent data
201 * @irq: subdriver dependent irq handler, set NULL when not used
202 * @dev: link to common driver structure
203 * @sie_num: SIE number on chip, starting from 0
204 * @mode: SIE mode (host/peripheral/otg/not used)
205 */
206struct c67x00_sie {
207 /* Entries to be used by the subdrivers */
208 spinlock_t lock; /* protect this structure */
209 void *private_data;
210 void (*irq) (struct c67x00_sie *sie, u16 int_status, u16 msg);
211
212 /* Read only: */
213 struct c67x00_device *dev;
214 int sie_num;
215 int mode;
216};
217
218#define sie_dev(s) (&(s)->dev->pdev->dev)
219
220/**
221 * struct c67x00_lcp
222 */
223struct c67x00_lcp {
224 /* Internal use only */
225 struct mutex mutex;
226 struct completion msg_received;
227 u16 last_msg;
228};
229
230/*
231 * struct c67x00_hpi
232 */
233struct c67x00_hpi {
234 void __iomem *base;
235 int regstep;
236 spinlock_t lock;
237 struct c67x00_lcp lcp;
238};
239
240#define C67X00_SIES 2
241#define C67X00_PORTS 2
242
243/**
244 * struct c67x00_device - Common data associated with a c67x00 instance
245 * @hpi: hpi addresses
246 * @sie: array of sie's on this chip
247 * @pdev: platform device of instance
248 * @pdata: configuration provided by the platform
249 */
250struct c67x00_device {
251 struct c67x00_hpi hpi;
252 struct c67x00_sie sie[C67X00_SIES];
253 struct platform_device *pdev;
254 struct c67x00_platform_data *pdata;
255};
256
257/* ---------------------------------------------------------------------
258 * Low level interface functions
259 */
260
261/* Host Port Interface (HPI) functions */
262u16 c67x00_ll_hpi_status(struct c67x00_device *dev);
263void c67x00_ll_hpi_reg_init(struct c67x00_device *dev);
264void c67x00_ll_hpi_enable_sofeop(struct c67x00_sie *sie);
265void c67x00_ll_hpi_disable_sofeop(struct c67x00_sie *sie);
266
267/* General functions */
268u16 c67x00_ll_fetch_siemsg(struct c67x00_device *dev, int sie_num);
269u16 c67x00_ll_get_usb_ctl(struct c67x00_sie *sie);
270void c67x00_ll_usb_clear_status(struct c67x00_sie *sie, u16 bits);
271u16 c67x00_ll_usb_get_status(struct c67x00_sie *sie);
272void c67x00_ll_write_mem_le16(struct c67x00_device *dev, u16 addr,
273 void *data, int len);
274void c67x00_ll_read_mem_le16(struct c67x00_device *dev, u16 addr,
275 void *data, int len);
276
277/* Called by c67x00_irq to handle lcp interrupts */
278void c67x00_ll_irq(struct c67x00_device *dev, u16 int_status);
279
280/* Setup and teardown */
281void c67x00_ll_init(struct c67x00_device *dev);
282void c67x00_ll_release(struct c67x00_device *dev);
283int c67x00_ll_reset(struct c67x00_device *dev);
284
285#endif /* _USB_C67X00_H */