aboutsummaryrefslogtreecommitdiffstats
path: root/arch
diff options
context:
space:
mode:
authorJesper Nilsson <jesper.nilsson@axis.com>2008-01-21 05:44:11 -0500
committerJesper Nilsson <jesper.nilsson@axis.com>2008-02-08 05:06:31 -0500
commitc974a9e5a3c52f1c61501b22a0b0a278250a6bd1 (patch)
treeee24ac27dfc10c4f2ae664a07b982c606b8881d7 /arch
parent4f073eff3fb738dce5ad0d8a3d126e5c09cbfba7 (diff)
CRIS v10: Add synchronous serial port driver for CRIS v10.
Diffstat (limited to 'arch')
-rw-r--r--arch/cris/Kconfig31
-rw-r--r--arch/cris/arch-v10/drivers/Makefile1
-rw-r--r--arch/cris/arch-v10/drivers/sync_serial.c1441
3 files changed, 1473 insertions, 0 deletions
diff --git a/arch/cris/Kconfig b/arch/cris/Kconfig
index 4a27ef374203..e6d440ae5e5b 100644
--- a/arch/cris/Kconfig
+++ b/arch/cris/Kconfig
@@ -292,6 +292,37 @@ config ETRAX_PCF8563
292 292
293endchoice 293endchoice
294 294
295config ETRAX_SYNCHRONOUS_SERIAL
296 bool "Synchronous serial-port support"
297 help
298 Select this to enable the synchronous serial port driver.
299
300config ETRAX_SYNCHRONOUS_SERIAL_PORT0
301 bool "Synchronous serial port 0 enabled"
302 depends on ETRAX_SYNCHRONOUS_SERIAL
303 help
304 Enabled synchronous serial port 0.
305
306config ETRAX_SYNCHRONOUS_SERIAL0_DMA
307 bool "Enable DMA on synchronous serial port 0."
308 depends on ETRAX_SYNCHRONOUS_SERIAL_PORT0
309 help
310 A synchronous serial port can run in manual or DMA mode.
311 Selecting this option will make it run in DMA mode.
312
313config ETRAX_SYNCHRONOUS_SERIAL_PORT1
314 bool "Synchronous serial port 1 enabled"
315 depends on ETRAX_SYNCHRONOUS_SERIAL && (ETRAXFS || ETRAX_ARCH_V10)
316 help
317 Enabled synchronous serial port 1.
318
319config ETRAX_SYNCHRONOUS_SERIAL1_DMA
320 bool "Enable DMA on synchronous serial port 1."
321 depends on ETRAX_SYNCHRONOUS_SERIAL_PORT1
322 help
323 A synchronous serial port can run in manual or DMA mode.
324 Selecting this option will make it run in DMA mode.
325
295choice 326choice
296 prompt "Network LED behavior" 327 prompt "Network LED behavior"
297 depends on ETRAX_ETHERNET 328 depends on ETRAX_ETHERNET
diff --git a/arch/cris/arch-v10/drivers/Makefile b/arch/cris/arch-v10/drivers/Makefile
index 074e10ff4156..44bf2e88c26e 100644
--- a/arch/cris/arch-v10/drivers/Makefile
+++ b/arch/cris/arch-v10/drivers/Makefile
@@ -8,4 +8,5 @@ obj-$(CONFIG_ETRAX_I2C_EEPROM) += eeprom.o
8obj-$(CONFIG_ETRAX_GPIO) += gpio.o 8obj-$(CONFIG_ETRAX_GPIO) += gpio.o
9obj-$(CONFIG_ETRAX_DS1302) += ds1302.o 9obj-$(CONFIG_ETRAX_DS1302) += ds1302.o
10obj-$(CONFIG_ETRAX_PCF8563) += pcf8563.o 10obj-$(CONFIG_ETRAX_PCF8563) += pcf8563.o
11obj-$(CONFIG_ETRAX_SYNCHRONOUS_SERIAL) += sync_serial.o
11 12
diff --git a/arch/cris/arch-v10/drivers/sync_serial.c b/arch/cris/arch-v10/drivers/sync_serial.c
new file mode 100644
index 000000000000..069546e342c5
--- /dev/null
+++ b/arch/cris/arch-v10/drivers/sync_serial.c
@@ -0,0 +1,1441 @@
1/*
2 * Simple synchronous serial port driver for ETRAX 100LX.
3 *
4 * Synchronous serial ports are used for continuous streamed data like audio.
5 * The default setting for this driver is compatible with the STA 013 MP3
6 * decoder. The driver can easily be tuned to fit other audio encoder/decoders
7 * and SPI
8 *
9 * Copyright (c) 2001-2008 Axis Communications AB
10 *
11 * Author: Mikael Starvik, Johan Adolfsson
12 *
13 */
14#include <linux/module.h>
15#include <linux/kernel.h>
16#include <linux/types.h>
17#include <linux/errno.h>
18#include <linux/major.h>
19#include <linux/sched.h>
20#include <linux/slab.h>
21#include <linux/interrupt.h>
22#include <linux/poll.h>
23#include <linux/init.h>
24#include <linux/timer.h>
25#include <asm/irq.h>
26#include <asm/dma.h>
27#include <asm/io.h>
28#include <asm/arch/svinto.h>
29#include <asm/uaccess.h>
30#include <asm/system.h>
31#include <asm/sync_serial.h>
32#include <asm/arch/io_interface_mux.h>
33
34/* The receiver is a bit tricky beacuse of the continuous stream of data.*/
35/* */
36/* Three DMA descriptors are linked together. Each DMA descriptor is */
37/* responsible for port->bufchunk of a common buffer. */
38/* */
39/* +---------------------------------------------+ */
40/* | +----------+ +----------+ +----------+ | */
41/* +-> | Descr[0] |-->| Descr[1] |-->| Descr[2] |-+ */
42/* +----------+ +----------+ +----------+ */
43/* | | | */
44/* v v v */
45/* +-------------------------------------+ */
46/* | BUFFER | */
47/* +-------------------------------------+ */
48/* |<- data_avail ->| */
49/* readp writep */
50/* */
51/* If the application keeps up the pace readp will be right after writep.*/
52/* If the application can't keep the pace we have to throw away data. */
53/* The idea is that readp should be ready with the data pointed out by */
54/* Descr[i] when the DMA has filled in Descr[i+1]. */
55/* Otherwise we will discard */
56/* the rest of the data pointed out by Descr1 and set readp to the start */
57/* of Descr2 */
58
59#define SYNC_SERIAL_MAJOR 125
60
61/* IN_BUFFER_SIZE should be a multiple of 6 to make sure that 24 bit */
62/* words can be handled */
63#define IN_BUFFER_SIZE 12288
64#define IN_DESCR_SIZE 256
65#define NUM_IN_DESCR (IN_BUFFER_SIZE/IN_DESCR_SIZE)
66#define OUT_BUFFER_SIZE 4096
67
68#define DEFAULT_FRAME_RATE 0
69#define DEFAULT_WORD_RATE 7
70
71/* NOTE: Enabling some debug will likely cause overrun or underrun,
72 * especially if manual mode is use.
73 */
74#define DEBUG(x)
75#define DEBUGREAD(x)
76#define DEBUGWRITE(x)
77#define DEBUGPOLL(x)
78#define DEBUGRXINT(x)
79#define DEBUGTXINT(x)
80
81/* Define some macros to access ETRAX 100 registers */
82#define SETF(var, reg, field, val) \
83 do { \
84 var = (var & ~IO_MASK_(reg##_, field##_)) | \
85 IO_FIELD_(reg##_, field##_, val); \
86 } while (0)
87
88#define SETS(var, reg, field, val) \
89 do { \
90 var = (var & ~IO_MASK_(reg##_, field##_)) | \
91 IO_STATE_(reg##_, field##_, _##val); \
92 } while (0)
93
94struct sync_port {
95 /* Etrax registers and bits*/
96 const volatile unsigned *const status;
97 volatile unsigned *const ctrl_data;
98 volatile unsigned *const output_dma_first;
99 volatile unsigned char *const output_dma_cmd;
100 volatile unsigned char *const output_dma_clr_irq;
101 volatile unsigned *const input_dma_first;
102 volatile unsigned char *const input_dma_cmd;
103 volatile unsigned *const input_dma_descr;
104 /* 8*4 */
105 volatile unsigned char *const input_dma_clr_irq;
106 volatile unsigned *const data_out;
107 const volatile unsigned *const data_in;
108 char data_avail_bit; /* In R_IRQ_MASK1_RD/SET/CLR */
109 char transmitter_ready_bit; /* In R_IRQ_MASK1_RD/SET/CLR */
110 char input_dma_descr_bit; /* In R_IRQ_MASK2_RD */
111
112 char output_dma_bit; /* In R_IRQ_MASK2_RD */
113 /* End of fields initialised in array */
114 char started; /* 1 if port has been started */
115 char port_nbr; /* Port 0 or 1 */
116 char busy; /* 1 if port is busy */
117
118 char enabled; /* 1 if port is enabled */
119 char use_dma; /* 1 if port uses dma */
120 char tr_running;
121
122 char init_irqs;
123
124 /* Register shadow */
125 unsigned int ctrl_data_shadow;
126 /* Remaining bytes for current transfer */
127 volatile unsigned int out_count;
128 /* Current position in out_buffer */
129 unsigned char *outp;
130 /* 16*4 */
131 /* Next byte to be read by application */
132 volatile unsigned char *volatile readp;
133 /* Next byte to be written by etrax */
134 volatile unsigned char *volatile writep;
135
136 unsigned int in_buffer_size;
137 unsigned int inbufchunk;
138 struct etrax_dma_descr out_descr __attribute__ ((aligned(32)));
139 struct etrax_dma_descr in_descr[NUM_IN_DESCR] __attribute__ ((aligned(32)));
140 unsigned char out_buffer[OUT_BUFFER_SIZE] __attribute__ ((aligned(32)));
141 unsigned char in_buffer[IN_BUFFER_SIZE]__attribute__ ((aligned(32)));
142 unsigned char flip[IN_BUFFER_SIZE] __attribute__ ((aligned(32)));
143 struct etrax_dma_descr *next_rx_desc;
144 struct etrax_dma_descr *prev_rx_desc;
145 int full;
146
147 wait_queue_head_t out_wait_q;
148 wait_queue_head_t in_wait_q;
149};
150
151
152static int etrax_sync_serial_init(void);
153static void initialize_port(int portnbr);
154static inline int sync_data_avail(struct sync_port *port);
155
156static int sync_serial_open(struct inode *inode, struct file *file);
157static int sync_serial_release(struct inode *inode, struct file *file);
158static unsigned int sync_serial_poll(struct file *filp, poll_table *wait);
159
160static int sync_serial_ioctl(struct inode *inode, struct file *file,
161 unsigned int cmd, unsigned long arg);
162static ssize_t sync_serial_write(struct file *file, const char *buf,
163 size_t count, loff_t *ppos);
164static ssize_t sync_serial_read(struct file *file, char *buf,
165 size_t count, loff_t *ppos);
166
167#if ((defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL_PORT0) && \
168 defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL0_DMA)) || \
169 (defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL_PORT1) && \
170 defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL1_DMA)))
171#define SYNC_SER_DMA
172#endif
173
174static void send_word(struct sync_port *port);
175static void start_dma(struct sync_port *port, const char *data, int count);
176static void start_dma_in(struct sync_port *port);
177#ifdef SYNC_SER_DMA
178static irqreturn_t tr_interrupt(int irq, void *dev_id);
179static irqreturn_t rx_interrupt(int irq, void *dev_id);
180#endif
181#if ((defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL_PORT0) && \
182 !defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL0_DMA)) || \
183 (defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL_PORT1) && \
184 !defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL1_DMA)))
185#define SYNC_SER_MANUAL
186#endif
187#ifdef SYNC_SER_MANUAL
188static irqreturn_t manual_interrupt(int irq, void *dev_id);
189#endif
190
191/* The ports */
192static struct sync_port ports[] = {
193 {
194 .status = R_SYNC_SERIAL1_STATUS,
195 .ctrl_data = R_SYNC_SERIAL1_CTRL,
196 .output_dma_first = R_DMA_CH8_FIRST,
197 .output_dma_cmd = R_DMA_CH8_CMD,
198 .output_dma_clr_irq = R_DMA_CH8_CLR_INTR,
199 .input_dma_first = R_DMA_CH9_FIRST,
200 .input_dma_cmd = R_DMA_CH9_CMD,
201 .input_dma_descr = R_DMA_CH9_DESCR,
202 .input_dma_clr_irq = R_DMA_CH9_CLR_INTR,
203 .data_out = R_SYNC_SERIAL1_TR_DATA,
204 .data_in = R_SYNC_SERIAL1_REC_DATA,
205 .data_avail_bit = IO_BITNR(R_IRQ_MASK1_RD, ser1_data),
206 .transmitter_ready_bit = IO_BITNR(R_IRQ_MASK1_RD, ser1_ready),
207 .input_dma_descr_bit = IO_BITNR(R_IRQ_MASK2_RD, dma9_descr),
208 .output_dma_bit = IO_BITNR(R_IRQ_MASK2_RD, dma8_eop),
209 .init_irqs = 1,
210#if defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL0_DMA)
211 .use_dma = 1,
212#else
213 .use_dma = 0,
214#endif
215 },
216 {
217 .status = R_SYNC_SERIAL3_STATUS,
218 .ctrl_data = R_SYNC_SERIAL3_CTRL,
219 .output_dma_first = R_DMA_CH4_FIRST,
220 .output_dma_cmd = R_DMA_CH4_CMD,
221 .output_dma_clr_irq = R_DMA_CH4_CLR_INTR,
222 .input_dma_first = R_DMA_CH5_FIRST,
223 .input_dma_cmd = R_DMA_CH5_CMD,
224 .input_dma_descr = R_DMA_CH5_DESCR,
225 .input_dma_clr_irq = R_DMA_CH5_CLR_INTR,
226 .data_out = R_SYNC_SERIAL3_TR_DATA,
227 .data_in = R_SYNC_SERIAL3_REC_DATA,
228 .data_avail_bit = IO_BITNR(R_IRQ_MASK1_RD, ser3_data),
229 .transmitter_ready_bit = IO_BITNR(R_IRQ_MASK1_RD, ser3_ready),
230 .input_dma_descr_bit = IO_BITNR(R_IRQ_MASK2_RD, dma5_descr),
231 .output_dma_bit = IO_BITNR(R_IRQ_MASK2_RD, dma4_eop),
232 .init_irqs = 1,
233#if defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL1_DMA)
234 .use_dma = 1,
235#else
236 .use_dma = 0,
237#endif
238 }
239};
240
241/* Register shadows */
242static unsigned sync_serial_prescale_shadow;
243
244#define NUMBER_OF_PORTS 2
245
246static struct file_operations sync_serial_fops = {
247 .owner = THIS_MODULE,
248 .write = sync_serial_write,
249 .read = sync_serial_read,
250 .poll = sync_serial_poll,
251 .ioctl = sync_serial_ioctl,
252 .open = sync_serial_open,
253 .release = sync_serial_release
254};
255
256static int __init etrax_sync_serial_init(void)
257{
258 ports[0].enabled = 0;
259 ports[1].enabled = 0;
260
261#if defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL_PORT0)
262 if (cris_request_io_interface(if_sync_serial_1, "sync_ser1")) {
263 printk(KERN_CRIT "ETRAX100LX sync_serial: "
264 "Could not allocate IO group for port %d\n", 0);
265 return -EBUSY;
266 }
267#endif
268#if defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL_PORT1)
269 if (cris_request_io_interface(if_sync_serial_3, "sync_ser3")) {
270#if defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL_PORT0)
271 cris_free_io_interface(if_sync_serial_1);
272#endif
273 printk(KERN_CRIT "ETRAX100LX sync_serial: "
274 "Could not allocate IO group for port %d\n", 1);
275 return -EBUSY;
276 }
277#endif
278
279 if (register_chrdev(SYNC_SERIAL_MAJOR, "sync serial",
280 &sync_serial_fops) < 0) {
281#if defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL_PORT1)
282 cris_free_io_interface(if_sync_serial_3);
283#endif
284#if defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL_PORT0)
285 cris_free_io_interface(if_sync_serial_1);
286#endif
287 printk("unable to get major for synchronous serial port\n");
288 return -EBUSY;
289 }
290
291 /* Deselect synchronous serial ports while configuring. */
292 SETS(gen_config_ii_shadow, R_GEN_CONFIG_II, sermode1, async);
293 SETS(gen_config_ii_shadow, R_GEN_CONFIG_II, sermode3, async);
294 *R_GEN_CONFIG_II = gen_config_ii_shadow;
295
296 /* Initialize Ports */
297#if defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL_PORT0)
298 ports[0].enabled = 1;
299 SETS(port_pb_i2c_shadow, R_PORT_PB_I2C, syncser1, ss1extra);
300 SETS(gen_config_ii_shadow, R_GEN_CONFIG_II, sermode1, sync);
301#if defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL0_DMA)
302 ports[0].use_dma = 1;
303#else
304 ports[0].use_dma = 0;
305#endif
306 initialize_port(0);
307#endif
308
309#if defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL_PORT1)
310 ports[1].enabled = 1;
311 SETS(port_pb_i2c_shadow, R_PORT_PB_I2C, syncser3, ss3extra);
312 SETS(gen_config_ii_shadow, R_GEN_CONFIG_II, sermode3, sync);
313#if defined(CONFIG_ETRAX_SYNCHRONOUS_SERIAL1_DMA)
314 ports[1].use_dma = 1;
315#else
316 ports[1].use_dma = 0;
317#endif
318 initialize_port(1);
319#endif
320
321 *R_PORT_PB_I2C = port_pb_i2c_shadow; /* Use PB4/PB7 */
322
323 /* Set up timing */
324 *R_SYNC_SERIAL_PRESCALE = sync_serial_prescale_shadow = (
325 IO_STATE(R_SYNC_SERIAL_PRESCALE, clk_sel_u1, codec) |
326 IO_STATE(R_SYNC_SERIAL_PRESCALE, word_stb_sel_u1, external) |
327 IO_STATE(R_SYNC_SERIAL_PRESCALE, clk_sel_u3, codec) |
328 IO_STATE(R_SYNC_SERIAL_PRESCALE, word_stb_sel_u3, external) |
329 IO_STATE(R_SYNC_SERIAL_PRESCALE, prescaler, div4) |
330 IO_FIELD(R_SYNC_SERIAL_PRESCALE, frame_rate,
331 DEFAULT_FRAME_RATE) |
332 IO_FIELD(R_SYNC_SERIAL_PRESCALE, word_rate, DEFAULT_WORD_RATE) |
333 IO_STATE(R_SYNC_SERIAL_PRESCALE, warp_mode, normal));
334
335 /* Select synchronous ports */
336 *R_GEN_CONFIG_II = gen_config_ii_shadow;
337
338 printk(KERN_INFO "ETRAX 100LX synchronous serial port driver\n");
339 return 0;
340}
341
342static void __init initialize_port(int portnbr)
343{
344 struct sync_port *port = &ports[portnbr];
345
346 DEBUG(printk(KERN_DEBUG "Init sync serial port %d\n", portnbr));
347
348 port->started = 0;
349 port->port_nbr = portnbr;
350 port->busy = 0;
351 port->tr_running = 0;
352
353 port->out_count = 0;
354 port->outp = port->out_buffer;
355
356 port->readp = port->flip;
357 port->writep = port->flip;
358 port->in_buffer_size = IN_BUFFER_SIZE;
359 port->inbufchunk = IN_DESCR_SIZE;
360 port->next_rx_desc = &port->in_descr[0];
361 port->prev_rx_desc = &port->in_descr[NUM_IN_DESCR-1];
362 port->prev_rx_desc->ctrl = d_eol;
363
364 init_waitqueue_head(&port->out_wait_q);
365 init_waitqueue_head(&port->in_wait_q);
366
367 port->ctrl_data_shadow =
368 IO_STATE(R_SYNC_SERIAL1_CTRL, tr_baud, c115k2Hz) |
369 IO_STATE(R_SYNC_SERIAL1_CTRL, mode, master_output) |
370 IO_STATE(R_SYNC_SERIAL1_CTRL, error, ignore) |
371 IO_STATE(R_SYNC_SERIAL1_CTRL, rec_enable, disable) |
372 IO_STATE(R_SYNC_SERIAL1_CTRL, f_synctype, normal) |
373 IO_STATE(R_SYNC_SERIAL1_CTRL, f_syncsize, word) |
374 IO_STATE(R_SYNC_SERIAL1_CTRL, f_sync, on) |
375 IO_STATE(R_SYNC_SERIAL1_CTRL, clk_mode, normal) |
376 IO_STATE(R_SYNC_SERIAL1_CTRL, clk_halt, stopped) |
377 IO_STATE(R_SYNC_SERIAL1_CTRL, bitorder, msb) |
378 IO_STATE(R_SYNC_SERIAL1_CTRL, tr_enable, disable) |
379 IO_STATE(R_SYNC_SERIAL1_CTRL, wordsize, size8bit) |
380 IO_STATE(R_SYNC_SERIAL1_CTRL, buf_empty, lmt_8) |
381 IO_STATE(R_SYNC_SERIAL1_CTRL, buf_full, lmt_8) |
382 IO_STATE(R_SYNC_SERIAL1_CTRL, flow_ctrl, enabled) |
383 IO_STATE(R_SYNC_SERIAL1_CTRL, clk_polarity, neg) |
384 IO_STATE(R_SYNC_SERIAL1_CTRL, frame_polarity, normal)|
385 IO_STATE(R_SYNC_SERIAL1_CTRL, status_polarity, inverted)|
386 IO_STATE(R_SYNC_SERIAL1_CTRL, clk_driver, normal) |
387 IO_STATE(R_SYNC_SERIAL1_CTRL, frame_driver, normal) |
388 IO_STATE(R_SYNC_SERIAL1_CTRL, status_driver, normal)|
389 IO_STATE(R_SYNC_SERIAL1_CTRL, def_out0, high);
390
391 if (port->use_dma)
392 port->ctrl_data_shadow |= IO_STATE(R_SYNC_SERIAL1_CTRL,
393 dma_enable, on);
394 else
395 port->ctrl_data_shadow |= IO_STATE(R_SYNC_SERIAL1_CTRL,
396 dma_enable, off);
397
398 *port->ctrl_data = port->ctrl_data_shadow;
399}
400
401static inline int sync_data_avail(struct sync_port *port)
402{
403 int avail;
404 unsigned char *start;
405 unsigned char *end;
406
407 start = (unsigned char *)port->readp; /* cast away volatile */
408 end = (unsigned char *)port->writep; /* cast away volatile */
409 /* 0123456789 0123456789
410 * ----- - -----
411 * ^rp ^wp ^wp ^rp
412 */
413 if (end >= start)
414 avail = end - start;
415 else
416 avail = port->in_buffer_size - (start - end);
417 return avail;
418}
419
420static inline int sync_data_avail_to_end(struct sync_port *port)
421{
422 int avail;
423 unsigned char *start;
424 unsigned char *end;
425
426 start = (unsigned char *)port->readp; /* cast away volatile */
427 end = (unsigned char *)port->writep; /* cast away volatile */
428 /* 0123456789 0123456789
429 * ----- -----
430 * ^rp ^wp ^wp ^rp
431 */
432
433 if (end >= start)
434 avail = end - start;
435 else
436 avail = port->flip + port->in_buffer_size - start;
437 return avail;
438}
439
440
441static int sync_serial_open(struct inode *inode, struct file *file)
442{
443 int dev = MINOR(inode->i_rdev);
444 struct sync_port *port;
445 int mode;
446
447 DEBUG(printk(KERN_DEBUG "Open sync serial port %d\n", dev));
448
449 if (dev < 0 || dev >= NUMBER_OF_PORTS || !ports[dev].enabled) {
450 DEBUG(printk(KERN_DEBUG "Invalid minor %d\n", dev));
451 return -ENODEV;
452 }
453 port = &ports[dev];
454 /* Allow open this device twice (assuming one reader and one writer) */
455 if (port->busy == 2) {
456 DEBUG(printk(KERN_DEBUG "Device is busy.. \n"));
457 return -EBUSY;
458 }
459 if (port->init_irqs) {
460 if (port->use_dma) {
461 if (port == &ports[0]) {
462#ifdef SYNC_SER_DMA
463 if (request_irq(24, tr_interrupt, 0,
464 "synchronous serial 1 dma tr",
465 &ports[0])) {
466 printk(KERN_CRIT "Can't alloc "
467 "sync serial port 1 IRQ");
468 return -EBUSY;
469 } else if (request_irq(25, rx_interrupt, 0,
470 "synchronous serial 1 dma rx",
471 &ports[0])) {
472 free_irq(24, &port[0]);
473 printk(KERN_CRIT "Can't alloc "
474 "sync serial port 1 IRQ");
475 return -EBUSY;
476 } else if (cris_request_dma(8,
477 "synchronous serial 1 dma tr",
478 DMA_VERBOSE_ON_ERROR,
479 dma_ser1)) {
480 free_irq(24, &port[0]);
481 free_irq(25, &port[0]);
482 printk(KERN_CRIT "Can't alloc "
483 "sync serial port 1 "
484 "TX DMA channel");
485 return -EBUSY;
486 } else if (cris_request_dma(9,
487 "synchronous serial 1 dma rec",
488 DMA_VERBOSE_ON_ERROR,
489 dma_ser1)) {
490 cris_free_dma(8, NULL);
491 free_irq(24, &port[0]);
492 free_irq(25, &port[0]);
493 printk(KERN_CRIT "Can't alloc "
494 "sync serial port 1 "
495 "RX DMA channel");
496 return -EBUSY;
497 }
498#endif
499 RESET_DMA(8); WAIT_DMA(8);
500 RESET_DMA(9); WAIT_DMA(9);
501 *R_DMA_CH8_CLR_INTR =
502 IO_STATE(R_DMA_CH8_CLR_INTR, clr_eop,
503 do) |
504 IO_STATE(R_DMA_CH8_CLR_INTR, clr_descr,
505 do);
506 *R_DMA_CH9_CLR_INTR =
507 IO_STATE(R_DMA_CH9_CLR_INTR, clr_eop,
508 do) |
509 IO_STATE(R_DMA_CH9_CLR_INTR, clr_descr,
510 do);
511 *R_IRQ_MASK2_SET =
512 IO_STATE(R_IRQ_MASK2_SET, dma8_eop,
513 set) |
514 IO_STATE(R_IRQ_MASK2_SET, dma9_descr,
515 set);
516 } else if (port == &ports[1]) {
517#ifdef SYNC_SER_DMA
518 if (request_irq(20, tr_interrupt, 0,
519 "synchronous serial 3 dma tr",
520 &ports[1])) {
521 printk(KERN_CRIT "Can't alloc "
522 "sync serial port 3 IRQ");
523 return -EBUSY;
524 } else if (request_irq(21, rx_interrupt, 0,
525 "synchronous serial 3 dma rx",
526 &ports[1])) {
527 free_irq(20, &ports[1]);
528 printk(KERN_CRIT "Can't alloc "
529 "sync serial port 3 IRQ");
530 return -EBUSY;
531 } else if (cris_request_dma(4,
532 "synchronous serial 3 dma tr",
533 DMA_VERBOSE_ON_ERROR,
534 dma_ser3)) {
535 free_irq(21, &ports[1]);
536 free_irq(20, &ports[1]);
537 printk(KERN_CRIT "Can't alloc "
538 "sync serial port 3 "
539 "TX DMA channel");
540 return -EBUSY;
541 } else if (cris_request_dma(5,
542 "synchronous serial 3 dma rec",
543 DMA_VERBOSE_ON_ERROR,
544 dma_ser3)) {
545 cris_free_dma(4, NULL);
546 free_irq(21, &ports[1]);
547 free_irq(20, &ports[1]);
548 printk(KERN_CRIT "Can't alloc "
549 "sync serial port 3 "
550 "RX DMA channel");
551 return -EBUSY;
552 }
553#endif
554 RESET_DMA(4); WAIT_DMA(4);
555 RESET_DMA(5); WAIT_DMA(5);
556 *R_DMA_CH4_CLR_INTR =
557 IO_STATE(R_DMA_CH4_CLR_INTR, clr_eop,
558 do) |
559 IO_STATE(R_DMA_CH4_CLR_INTR, clr_descr,
560 do);
561 *R_DMA_CH5_CLR_INTR =
562 IO_STATE(R_DMA_CH5_CLR_INTR, clr_eop,
563 do) |
564 IO_STATE(R_DMA_CH5_CLR_INTR, clr_descr,
565 do);
566 *R_IRQ_MASK2_SET =
567 IO_STATE(R_IRQ_MASK2_SET, dma4_eop,
568 set) |
569 IO_STATE(R_IRQ_MASK2_SET, dma5_descr,
570 set);
571 }
572 start_dma_in(port);
573 port->init_irqs = 0;
574 } else { /* !port->use_dma */
575#ifdef SYNC_SER_MANUAL
576 if (port == &ports[0]) {
577 if (request_irq(8,
578 manual_interrupt,
579 IRQF_SHARED | IRQF_DISABLED,
580 "synchronous serial manual irq",
581 &ports[0])) {
582 printk(KERN_CRIT "Can't alloc "
583 "sync serial manual irq");
584 return -EBUSY;
585 }
586 } else if (port == &ports[1]) {
587 if (request_irq(8,
588 manual_interrupt,
589 IRQF_SHARED | IRQF_DISABLED,
590 "synchronous serial manual irq",
591 &ports[1])) {
592 printk(KERN_CRIT "Can't alloc "
593 "sync serial manual irq");
594 return -EBUSY;
595 }
596 }
597 port->init_irqs = 0;
598#else
599 panic("sync_serial: Manual mode not supported.\n");
600#endif /* SYNC_SER_MANUAL */
601 }
602 } /* port->init_irqs */
603
604 port->busy++;
605 /* Start port if we use it as input */
606 mode = IO_EXTRACT(R_SYNC_SERIAL1_CTRL, mode, port->ctrl_data_shadow);
607 if (mode == IO_STATE_VALUE(R_SYNC_SERIAL1_CTRL, mode, master_input) ||
608 mode == IO_STATE_VALUE(R_SYNC_SERIAL1_CTRL, mode, slave_input) ||
609 mode == IO_STATE_VALUE(R_SYNC_SERIAL1_CTRL, mode, master_bidir) ||
610 mode == IO_STATE_VALUE(R_SYNC_SERIAL1_CTRL, mode, slave_bidir)) {
611 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, clk_halt,
612 running);
613 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, tr_enable,
614 enable);
615 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, rec_enable,
616 enable);
617 port->started = 1;
618 *port->ctrl_data = port->ctrl_data_shadow;
619 if (!port->use_dma)
620 *R_IRQ_MASK1_SET = 1 << port->data_avail_bit;
621 DEBUG(printk(KERN_DEBUG "sser%d rec started\n", dev));
622 }
623 return 0;
624}
625
626static int sync_serial_release(struct inode *inode, struct file *file)
627{
628 int dev = MINOR(inode->i_rdev);
629 struct sync_port *port;
630
631 if (dev < 0 || dev >= NUMBER_OF_PORTS || !ports[dev].enabled) {
632 DEBUG(printk(KERN_DEBUG "Invalid minor %d\n", dev));
633 return -ENODEV;
634 }
635 port = &ports[dev];
636 if (port->busy)
637 port->busy--;
638 if (!port->busy)
639 *R_IRQ_MASK1_CLR = ((1 << port->data_avail_bit) |
640 (1 << port->transmitter_ready_bit));
641
642 return 0;
643}
644
645
646
647static unsigned int sync_serial_poll(struct file *file, poll_table *wait)
648{
649 int dev = MINOR(file->f_dentry->d_inode->i_rdev);
650 unsigned int mask = 0;
651 struct sync_port *port;
652 DEBUGPOLL(static unsigned int prev_mask = 0);
653
654 port = &ports[dev];
655 poll_wait(file, &port->out_wait_q, wait);
656 poll_wait(file, &port->in_wait_q, wait);
657 /* Some room to write */
658 if (port->out_count < OUT_BUFFER_SIZE)
659 mask |= POLLOUT | POLLWRNORM;
660 /* At least an inbufchunk of data */
661 if (sync_data_avail(port) >= port->inbufchunk)
662 mask |= POLLIN | POLLRDNORM;
663
664 DEBUGPOLL(if (mask != prev_mask)
665 printk(KERN_DEBUG "sync_serial_poll: mask 0x%08X %s %s\n",
666 mask,
667 mask & POLLOUT ? "POLLOUT" : "",
668 mask & POLLIN ? "POLLIN" : "");
669 prev_mask = mask;
670 );
671 return mask;
672}
673
674static int sync_serial_ioctl(struct inode *inode, struct file *file,
675 unsigned int cmd, unsigned long arg)
676{
677 int return_val = 0;
678 unsigned long flags;
679
680 int dev = MINOR(file->f_dentry->d_inode->i_rdev);
681 struct sync_port *port;
682
683 if (dev < 0 || dev >= NUMBER_OF_PORTS || !ports[dev].enabled) {
684 DEBUG(printk(KERN_DEBUG "Invalid minor %d\n", dev));
685 return -1;
686 }
687 port = &ports[dev];
688
689 local_irq_save(flags);
690 /* Disable port while changing config */
691 if (dev) {
692 if (port->use_dma) {
693 RESET_DMA(4); WAIT_DMA(4);
694 port->tr_running = 0;
695 port->out_count = 0;
696 port->outp = port->out_buffer;
697 *R_DMA_CH4_CLR_INTR =
698 IO_STATE(R_DMA_CH4_CLR_INTR, clr_eop, do) |
699 IO_STATE(R_DMA_CH4_CLR_INTR, clr_descr, do);
700 }
701 SETS(gen_config_ii_shadow, R_GEN_CONFIG_II, sermode3, async);
702 } else {
703 if (port->use_dma) {
704 RESET_DMA(8); WAIT_DMA(8);
705 port->tr_running = 0;
706 port->out_count = 0;
707 port->outp = port->out_buffer;
708 *R_DMA_CH8_CLR_INTR =
709 IO_STATE(R_DMA_CH8_CLR_INTR, clr_eop, do) |
710 IO_STATE(R_DMA_CH8_CLR_INTR, clr_descr, do);
711 }
712 SETS(gen_config_ii_shadow, R_GEN_CONFIG_II, sermode1, async);
713 }
714 *R_GEN_CONFIG_II = gen_config_ii_shadow;
715 local_irq_restore(flags);
716
717 switch (cmd) {
718 case SSP_SPEED:
719 if (GET_SPEED(arg) == CODEC) {
720 if (dev)
721 SETS(sync_serial_prescale_shadow,
722 R_SYNC_SERIAL_PRESCALE, clk_sel_u3,
723 codec);
724 else
725 SETS(sync_serial_prescale_shadow,
726 R_SYNC_SERIAL_PRESCALE, clk_sel_u1,
727 codec);
728
729 SETF(sync_serial_prescale_shadow,
730 R_SYNC_SERIAL_PRESCALE, prescaler,
731 GET_FREQ(arg));
732 SETF(sync_serial_prescale_shadow,
733 R_SYNC_SERIAL_PRESCALE, frame_rate,
734 GET_FRAME_RATE(arg));
735 SETF(sync_serial_prescale_shadow,
736 R_SYNC_SERIAL_PRESCALE, word_rate,
737 GET_WORD_RATE(arg));
738 } else {
739 SETF(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
740 tr_baud, GET_SPEED(arg));
741 if (dev)
742 SETS(sync_serial_prescale_shadow,
743 R_SYNC_SERIAL_PRESCALE, clk_sel_u3,
744 baudrate);
745 else
746 SETS(sync_serial_prescale_shadow,
747 R_SYNC_SERIAL_PRESCALE, clk_sel_u1,
748 baudrate);
749 }
750 break;
751 case SSP_MODE:
752 if (arg > 5)
753 return -EINVAL;
754 if (arg == MASTER_OUTPUT || arg == SLAVE_OUTPUT)
755 *R_IRQ_MASK1_CLR = 1 << port->data_avail_bit;
756 else if (!port->use_dma)
757 *R_IRQ_MASK1_SET = 1 << port->data_avail_bit;
758 SETF(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, mode, arg);
759 break;
760 case SSP_FRAME_SYNC:
761 if (arg & NORMAL_SYNC)
762 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
763 f_synctype, normal);
764 else if (arg & EARLY_SYNC)
765 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
766 f_synctype, early);
767
768 if (arg & BIT_SYNC)
769 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
770 f_syncsize, bit);
771 else if (arg & WORD_SYNC)
772 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
773 f_syncsize, word);
774 else if (arg & EXTENDED_SYNC)
775 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
776 f_syncsize, extended);
777
778 if (arg & SYNC_ON)
779 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
780 f_sync, on);
781 else if (arg & SYNC_OFF)
782 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
783 f_sync, off);
784
785 if (arg & WORD_SIZE_8)
786 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
787 wordsize, size8bit);
788 else if (arg & WORD_SIZE_12)
789 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
790 wordsize, size12bit);
791 else if (arg & WORD_SIZE_16)
792 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
793 wordsize, size16bit);
794 else if (arg & WORD_SIZE_24)
795 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
796 wordsize, size24bit);
797 else if (arg & WORD_SIZE_32)
798 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
799 wordsize, size32bit);
800
801 if (arg & BIT_ORDER_MSB)
802 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
803 bitorder, msb);
804 else if (arg & BIT_ORDER_LSB)
805 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
806 bitorder, lsb);
807
808 if (arg & FLOW_CONTROL_ENABLE)
809 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
810 flow_ctrl, enabled);
811 else if (arg & FLOW_CONTROL_DISABLE)
812 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
813 flow_ctrl, disabled);
814
815 if (arg & CLOCK_NOT_GATED)
816 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
817 clk_mode, normal);
818 else if (arg & CLOCK_GATED)
819 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
820 clk_mode, gated);
821
822 break;
823 case SSP_IPOLARITY:
824 /* NOTE!! negedge is considered NORMAL */
825 if (arg & CLOCK_NORMAL)
826 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
827 clk_polarity, neg);
828 else if (arg & CLOCK_INVERT)
829 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
830 clk_polarity, pos);
831
832 if (arg & FRAME_NORMAL)
833 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
834 frame_polarity, normal);
835 else if (arg & FRAME_INVERT)
836 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
837 frame_polarity, inverted);
838
839 if (arg & STATUS_NORMAL)
840 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
841 status_polarity, normal);
842 else if (arg & STATUS_INVERT)
843 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
844 status_polarity, inverted);
845 break;
846 case SSP_OPOLARITY:
847 if (arg & CLOCK_NORMAL)
848 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
849 clk_driver, normal);
850 else if (arg & CLOCK_INVERT)
851 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
852 clk_driver, inverted);
853
854 if (arg & FRAME_NORMAL)
855 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
856 frame_driver, normal);
857 else if (arg & FRAME_INVERT)
858 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
859 frame_driver, inverted);
860
861 if (arg & STATUS_NORMAL)
862 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
863 status_driver, normal);
864 else if (arg & STATUS_INVERT)
865 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
866 status_driver, inverted);
867 break;
868 case SSP_SPI:
869 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, flow_ctrl,
870 disabled);
871 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, bitorder,
872 msb);
873 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, wordsize,
874 size8bit);
875 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, f_sync, on);
876 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, f_syncsize,
877 word);
878 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, f_synctype,
879 normal);
880 if (arg & SPI_SLAVE) {
881 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
882 frame_polarity, inverted);
883 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
884 clk_polarity, neg);
885 SETF(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
886 mode, SLAVE_INPUT);
887 } else {
888 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
889 frame_driver, inverted);
890 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
891 clk_driver, inverted);
892 SETF(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL,
893 mode, MASTER_OUTPUT);
894 }
895 break;
896 case SSP_INBUFCHUNK:
897#if 0
898 if (arg > port->in_buffer_size/NUM_IN_DESCR)
899 return -EINVAL;
900 port->inbufchunk = arg;
901 /* Make sure in_buffer_size is a multiple of inbufchunk */
902 port->in_buffer_size =
903 (port->in_buffer_size/port->inbufchunk) *
904 port->inbufchunk;
905 DEBUG(printk(KERN_DEBUG "inbufchunk %i in_buffer_size: %i\n",
906 port->inbufchunk, port->in_buffer_size));
907 if (port->use_dma) {
908 if (port->port_nbr == 0) {
909 RESET_DMA(9);
910 WAIT_DMA(9);
911 } else {
912 RESET_DMA(5);
913 WAIT_DMA(5);
914 }
915 start_dma_in(port);
916 }
917#endif
918 break;
919 default:
920 return_val = -1;
921 }
922 /* Make sure we write the config without interruption */
923 local_irq_save(flags);
924 /* Set config and enable port */
925 *port->ctrl_data = port->ctrl_data_shadow;
926 nop(); nop(); nop(); nop();
927 *R_SYNC_SERIAL_PRESCALE = sync_serial_prescale_shadow;
928 nop(); nop(); nop(); nop();
929 if (dev)
930 SETS(gen_config_ii_shadow, R_GEN_CONFIG_II, sermode3, sync);
931 else
932 SETS(gen_config_ii_shadow, R_GEN_CONFIG_II, sermode1, sync);
933
934 *R_GEN_CONFIG_II = gen_config_ii_shadow;
935 /* Reset DMA. At readout from serial port the data could be shifted
936 * one byte if not resetting DMA.
937 */
938 if (port->use_dma) {
939 if (port->port_nbr == 0) {
940 RESET_DMA(9);
941 WAIT_DMA(9);
942 } else {
943 RESET_DMA(5);
944 WAIT_DMA(5);
945 }
946 start_dma_in(port);
947 }
948 local_irq_restore(flags);
949 return return_val;
950}
951
952
953static ssize_t sync_serial_write(struct file *file, const char *buf,
954 size_t count, loff_t *ppos)
955{
956 int dev = MINOR(file->f_dentry->d_inode->i_rdev);
957 DECLARE_WAITQUEUE(wait, current);
958 struct sync_port *port;
959 unsigned long flags;
960 unsigned long c, c1;
961 unsigned long free_outp;
962 unsigned long outp;
963 unsigned long out_buffer;
964
965 if (dev < 0 || dev >= NUMBER_OF_PORTS || !ports[dev].enabled) {
966 DEBUG(printk(KERN_DEBUG "Invalid minor %d\n", dev));
967 return -ENODEV;
968 }
969 port = &ports[dev];
970
971 DEBUGWRITE(printk(KERN_DEBUG "W d%d c %lu (%d/%d)\n",
972 port->port_nbr, count, port->out_count, OUT_BUFFER_SIZE));
973 /* Space to end of buffer */
974 /*
975 * out_buffer <c1>012345<- c ->OUT_BUFFER_SIZE
976 * outp^ +out_count
977 * ^free_outp
978 * out_buffer 45<- c ->0123OUT_BUFFER_SIZE
979 * +out_count outp^
980 * free_outp
981 *
982 */
983
984 /* Read variables that may be updated by interrupts */
985 local_irq_save(flags);
986 if (count > OUT_BUFFER_SIZE - port->out_count)
987 count = OUT_BUFFER_SIZE - port->out_count;
988
989 outp = (unsigned long)port->outp;
990 free_outp = outp + port->out_count;
991 local_irq_restore(flags);
992 out_buffer = (unsigned long)port->out_buffer;
993
994 /* Find out where and how much to write */
995 if (free_outp >= out_buffer + OUT_BUFFER_SIZE)
996 free_outp -= OUT_BUFFER_SIZE;
997 if (free_outp >= outp)
998 c = out_buffer + OUT_BUFFER_SIZE - free_outp;
999 else
1000 c = outp - free_outp;
1001 if (c > count)
1002 c = count;
1003
1004 DEBUGWRITE(printk(KERN_DEBUG "w op %08lX fop %08lX c %lu\n",
1005 outp, free_outp, c));
1006 if (copy_from_user((void *)free_outp, buf, c))
1007 return -EFAULT;
1008
1009 if (c != count) {
1010 buf += c;
1011 c1 = count - c;
1012 DEBUGWRITE(printk(KERN_DEBUG "w2 fi %lu c %lu c1 %lu\n",
1013 free_outp-out_buffer, c, c1));
1014 if (copy_from_user((void *)out_buffer, buf, c1))
1015 return -EFAULT;
1016 }
1017 local_irq_save(flags);
1018 port->out_count += count;
1019 local_irq_restore(flags);
1020
1021 /* Make sure transmitter/receiver is running */
1022 if (!port->started) {
1023 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, clk_halt,
1024 running);
1025 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, tr_enable,
1026 enable);
1027 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, rec_enable,
1028 enable);
1029 port->started = 1;
1030 }
1031
1032 *port->ctrl_data = port->ctrl_data_shadow;
1033
1034 if (file->f_flags & O_NONBLOCK) {
1035 local_irq_save(flags);
1036 if (!port->tr_running) {
1037 if (!port->use_dma) {
1038 /* Start sender by writing data */
1039 send_word(port);
1040 /* and enable transmitter ready IRQ */
1041 *R_IRQ_MASK1_SET = 1 <<
1042 port->transmitter_ready_bit;
1043 } else
1044 start_dma(port,
1045 (unsigned char *volatile)port->outp, c);
1046 }
1047 local_irq_restore(flags);
1048 DEBUGWRITE(printk(KERN_DEBUG "w d%d c %lu NB\n",
1049 port->port_nbr, count));
1050 return count;
1051 }
1052
1053 /* Sleep until all sent */
1054 add_wait_queue(&port->out_wait_q, &wait);
1055 set_current_state(TASK_INTERRUPTIBLE);
1056 local_irq_save(flags);
1057 if (!port->tr_running) {
1058 if (!port->use_dma) {
1059 /* Start sender by writing data */
1060 send_word(port);
1061 /* and enable transmitter ready IRQ */
1062 *R_IRQ_MASK1_SET = 1 << port->transmitter_ready_bit;
1063 } else
1064 start_dma(port, port->outp, c);
1065 }
1066 local_irq_restore(flags);
1067 schedule();
1068 set_current_state(TASK_RUNNING);
1069 remove_wait_queue(&port->out_wait_q, &wait);
1070 if (signal_pending(current))
1071 return -EINTR;
1072
1073 DEBUGWRITE(printk(KERN_DEBUG "w d%d c %lu\n", port->port_nbr, count));
1074 return count;
1075}
1076
1077static ssize_t sync_serial_read(struct file *file, char *buf,
1078 size_t count, loff_t *ppos)
1079{
1080 int dev = MINOR(file->f_dentry->d_inode->i_rdev);
1081 int avail;
1082 struct sync_port *port;
1083 unsigned char *start;
1084 unsigned char *end;
1085 unsigned long flags;
1086
1087 if (dev < 0 || dev >= NUMBER_OF_PORTS || !ports[dev].enabled) {
1088 DEBUG(printk(KERN_DEBUG "Invalid minor %d\n", dev));
1089 return -ENODEV;
1090 }
1091 port = &ports[dev];
1092
1093 DEBUGREAD(printk(KERN_DEBUG "R%d c %d ri %lu wi %lu /%lu\n",
1094 dev, count, port->readp - port->flip,
1095 port->writep - port->flip, port->in_buffer_size));
1096
1097 if (!port->started) {
1098 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, clk_halt,
1099 running);
1100 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, tr_enable,
1101 enable);
1102 SETS(port->ctrl_data_shadow, R_SYNC_SERIAL1_CTRL, rec_enable,
1103 enable);
1104 port->started = 1;
1105 }
1106 *port->ctrl_data = port->ctrl_data_shadow;
1107
1108 /* Calculate number of available bytes */
1109 /* Save pointers to avoid that they are modified by interrupt */
1110 local_irq_save(flags);
1111 start = (unsigned char *)port->readp; /* cast away volatile */
1112 end = (unsigned char *)port->writep; /* cast away volatile */
1113 local_irq_restore(flags);
1114 while (start == end && !port->full) {
1115 /* No data */
1116 if (file->f_flags & O_NONBLOCK)
1117 return -EAGAIN;
1118
1119 interruptible_sleep_on(&port->in_wait_q);
1120 if (signal_pending(current))
1121 return -EINTR;
1122
1123 local_irq_save(flags);
1124 start = (unsigned char *)port->readp; /* cast away volatile */
1125 end = (unsigned char *)port->writep; /* cast away volatile */
1126 local_irq_restore(flags);
1127 }
1128
1129 /* Lazy read, never return wrapped data. */
1130 if (port->full)
1131 avail = port->in_buffer_size;
1132 else if (end > start)
1133 avail = end - start;
1134 else
1135 avail = port->flip + port->in_buffer_size - start;
1136
1137 count = count > avail ? avail : count;
1138 if (copy_to_user(buf, start, count))
1139 return -EFAULT;
1140 /* Disable interrupts while updating readp */
1141 local_irq_save(flags);
1142 port->readp += count;
1143 if (port->readp >= port->flip + port->in_buffer_size) /* Wrap? */
1144 port->readp = port->flip;
1145 port->full = 0;
1146 local_irq_restore(flags);
1147 DEBUGREAD(printk(KERN_DEBUG "r %d\n", count));
1148 return count;
1149}
1150
1151static void send_word(struct sync_port *port)
1152{
1153 switch (IO_EXTRACT(R_SYNC_SERIAL1_CTRL, wordsize,
1154 port->ctrl_data_shadow)) {
1155 case IO_STATE_VALUE(R_SYNC_SERIAL1_CTRL, wordsize, size8bit):
1156 port->out_count--;
1157 *port->data_out = *port->outp++;
1158 if (port->outp >= port->out_buffer + OUT_BUFFER_SIZE)
1159 port->outp = port->out_buffer;
1160 break;
1161 case IO_STATE_VALUE(R_SYNC_SERIAL1_CTRL, wordsize, size12bit):
1162 {
1163 int data = (*port->outp++) << 8;
1164 data |= *port->outp++;
1165 port->out_count -= 2;
1166 *port->data_out = data;
1167 if (port->outp >= port->out_buffer + OUT_BUFFER_SIZE)
1168 port->outp = port->out_buffer;
1169 break;
1170 }
1171 case IO_STATE_VALUE(R_SYNC_SERIAL1_CTRL, wordsize, size16bit):
1172 port->out_count -= 2;
1173 *port->data_out = *(unsigned short *)port->outp;
1174 port->outp += 2;
1175 if (port->outp >= port->out_buffer + OUT_BUFFER_SIZE)
1176 port->outp = port->out_buffer;
1177 break;
1178 case IO_STATE_VALUE(R_SYNC_SERIAL1_CTRL, wordsize, size24bit):
1179 port->out_count -= 3;
1180 *port->data_out = *(unsigned int *)port->outp;
1181 port->outp += 3;
1182 if (port->outp >= port->out_buffer + OUT_BUFFER_SIZE)
1183 port->outp = port->out_buffer;
1184 break;
1185 case IO_STATE_VALUE(R_SYNC_SERIAL1_CTRL, wordsize, size32bit):
1186 port->out_count -= 4;
1187 *port->data_out = *(unsigned int *)port->outp;
1188 port->outp += 4;
1189 if (port->outp >= port->out_buffer + OUT_BUFFER_SIZE)
1190 port->outp = port->out_buffer;
1191 break;
1192 }
1193}
1194
1195
1196static void start_dma(struct sync_port *port, const char *data, int count)
1197{
1198 port->tr_running = 1;
1199 port->out_descr.hw_len = 0;
1200 port->out_descr.next = 0;
1201 port->out_descr.ctrl = d_eol | d_eop; /* No d_wait to avoid glitches */
1202 port->out_descr.sw_len = count;
1203 port->out_descr.buf = virt_to_phys(data);
1204 port->out_descr.status = 0;
1205
1206 *port->output_dma_first = virt_to_phys(&port->out_descr);
1207 *port->output_dma_cmd = IO_STATE(R_DMA_CH0_CMD, cmd, start);
1208 DEBUGTXINT(printk(KERN_DEBUG "dma %08lX c %d\n",
1209 (unsigned long)data, count));
1210}
1211
1212static void start_dma_in(struct sync_port *port)
1213{
1214 int i;
1215 unsigned long buf;
1216 port->writep = port->flip;
1217
1218 if (port->writep > port->flip + port->in_buffer_size) {
1219 panic("Offset too large in sync serial driver\n");
1220 return;
1221 }
1222 buf = virt_to_phys(port->in_buffer);
1223 for (i = 0; i < NUM_IN_DESCR; i++) {
1224 port->in_descr[i].sw_len = port->inbufchunk;
1225 port->in_descr[i].ctrl = d_int;
1226 port->in_descr[i].next = virt_to_phys(&port->in_descr[i+1]);
1227 port->in_descr[i].buf = buf;
1228 port->in_descr[i].hw_len = 0;
1229 port->in_descr[i].status = 0;
1230 port->in_descr[i].fifo_len = 0;
1231 buf += port->inbufchunk;
1232 prepare_rx_descriptor(&port->in_descr[i]);
1233 }
1234 /* Link the last descriptor to the first */
1235 port->in_descr[i-1].next = virt_to_phys(&port->in_descr[0]);
1236 port->in_descr[i-1].ctrl |= d_eol;
1237 port->next_rx_desc = &port->in_descr[0];
1238 port->prev_rx_desc = &port->in_descr[NUM_IN_DESCR - 1];
1239 *port->input_dma_first = virt_to_phys(port->next_rx_desc);
1240 *port->input_dma_cmd = IO_STATE(R_DMA_CH0_CMD, cmd, start);
1241}
1242
1243#ifdef SYNC_SER_DMA
1244static irqreturn_t tr_interrupt(int irq, void *dev_id)
1245{
1246 unsigned long ireg = *R_IRQ_MASK2_RD;
1247 struct etrax_dma_descr *descr;
1248 unsigned int sentl;
1249 int handled = 0;
1250 int i;
1251
1252 for (i = 0; i < NUMBER_OF_PORTS; i++) {
1253 struct sync_port *port = &ports[i];
1254 if (!port->enabled || !port->use_dma)
1255 continue;
1256
1257 /* IRQ active for the port? */
1258 if (!(ireg & (1 << port->output_dma_bit)))
1259 continue;
1260
1261 handled = 1;
1262
1263 /* Clear IRQ */
1264 *port->output_dma_clr_irq =
1265 IO_STATE(R_DMA_CH0_CLR_INTR, clr_eop, do) |
1266 IO_STATE(R_DMA_CH0_CLR_INTR, clr_descr, do);
1267
1268 descr = &port->out_descr;
1269 if (!(descr->status & d_stop))
1270 sentl = descr->sw_len;
1271 else
1272 /* Otherwise find amount of data sent here */
1273 sentl = descr->hw_len;
1274
1275 port->out_count -= sentl;
1276 port->outp += sentl;
1277 if (port->outp >= port->out_buffer + OUT_BUFFER_SIZE)
1278 port->outp = port->out_buffer;
1279 if (port->out_count) {
1280 int c = port->out_buffer + OUT_BUFFER_SIZE - port->outp;
1281 if (c > port->out_count)
1282 c = port->out_count;
1283 DEBUGTXINT(printk(KERN_DEBUG
1284 "tx_int DMAWRITE %i %i\n", sentl, c));
1285 start_dma(port, port->outp, c);
1286 } else {
1287 DEBUGTXINT(printk(KERN_DEBUG
1288 "tx_int DMA stop %i\n", sentl));
1289 port->tr_running = 0;
1290 }
1291 /* wake up the waiting process */
1292 wake_up_interruptible(&port->out_wait_q);
1293 }
1294 return IRQ_RETVAL(handled);
1295} /* tr_interrupt */
1296
1297static irqreturn_t rx_interrupt(int irq, void *dev_id)
1298{
1299 unsigned long ireg = *R_IRQ_MASK2_RD;
1300 int i;
1301 int handled = 0;
1302
1303 for (i = 0; i < NUMBER_OF_PORTS; i++) {
1304 struct sync_port *port = &ports[i];
1305
1306 if (!port->enabled || !port->use_dma)
1307 continue;
1308
1309 if (!(ireg & (1 << port->input_dma_descr_bit)))
1310 continue;
1311
1312 /* Descriptor interrupt */
1313 handled = 1;
1314 while (*port->input_dma_descr !=
1315 virt_to_phys(port->next_rx_desc)) {
1316 if (port->writep + port->inbufchunk > port->flip +
1317 port->in_buffer_size) {
1318 int first_size = port->flip +
1319 port->in_buffer_size - port->writep;
1320 memcpy(port->writep,
1321 phys_to_virt(port->next_rx_desc->buf),
1322 first_size);
1323 memcpy(port->flip,
1324 phys_to_virt(port->next_rx_desc->buf +
1325 first_size),
1326 port->inbufchunk - first_size);
1327 port->writep = port->flip +
1328 port->inbufchunk - first_size;
1329 } else {
1330 memcpy(port->writep,
1331 phys_to_virt(port->next_rx_desc->buf),
1332 port->inbufchunk);
1333 port->writep += port->inbufchunk;
1334 if (port->writep >= port->flip
1335 + port->in_buffer_size)
1336 port->writep = port->flip;
1337 }
1338 if (port->writep == port->readp)
1339 port->full = 1;
1340 prepare_rx_descriptor(port->next_rx_desc);
1341 port->next_rx_desc->ctrl |= d_eol;
1342 port->prev_rx_desc->ctrl &= ~d_eol;
1343 port->prev_rx_desc = phys_to_virt((unsigned)
1344 port->next_rx_desc);
1345 port->next_rx_desc = phys_to_virt((unsigned)
1346 port->next_rx_desc->next);
1347 /* Wake up the waiting process */
1348 wake_up_interruptible(&port->in_wait_q);
1349 *port->input_dma_cmd = IO_STATE(R_DMA_CH1_CMD,
1350 cmd, restart);
1351 /* DMA has reached end of descriptor */
1352 *port->input_dma_clr_irq = IO_STATE(R_DMA_CH0_CLR_INTR,
1353 clr_descr, do);
1354 }
1355 }
1356 return IRQ_RETVAL(handled);
1357} /* rx_interrupt */
1358#endif /* SYNC_SER_DMA */
1359
1360#ifdef SYNC_SER_MANUAL
1361static irqreturn_t manual_interrupt(int irq, void *dev_id)
1362{
1363 int i;
1364 int handled = 0;
1365
1366 for (i = 0; i < NUMBER_OF_PORTS; i++) {
1367 struct sync_port *port = &ports[i];
1368
1369 if (!port->enabled || port->use_dma)
1370 continue;
1371
1372 /* Data received? */
1373 if (*R_IRQ_MASK1_RD & (1 << port->data_avail_bit)) {
1374 handled = 1;
1375 /* Read data */
1376 switch (port->ctrl_data_shadow &
1377 IO_MASK(R_SYNC_SERIAL1_CTRL, wordsize)) {
1378 case IO_STATE(R_SYNC_SERIAL1_CTRL, wordsize, size8bit):
1379 *port->writep++ =
1380 *(volatile char *)port->data_in;
1381 break;
1382 case IO_STATE(R_SYNC_SERIAL1_CTRL, wordsize, size12bit):
1383 {
1384 int data = *(unsigned short *)port->data_in;
1385 *port->writep = (data & 0x0ff0) >> 4;
1386 *(port->writep + 1) = data & 0x0f;
1387 port->writep += 2;
1388 break;
1389 }
1390 case IO_STATE(R_SYNC_SERIAL1_CTRL, wordsize, size16bit):
1391 *(unsigned short *)port->writep =
1392 *(volatile unsigned short *)port->data_in;
1393 port->writep += 2;
1394 break;
1395 case IO_STATE(R_SYNC_SERIAL1_CTRL, wordsize, size24bit):
1396 *(unsigned int *)port->writep = *port->data_in;
1397 port->writep += 3;
1398 break;
1399 case IO_STATE(R_SYNC_SERIAL1_CTRL, wordsize, size32bit):
1400 *(unsigned int *)port->writep = *port->data_in;
1401 port->writep += 4;
1402 break;
1403 }
1404
1405 /* Wrap? */
1406 if (port->writep >= port->flip + port->in_buffer_size)
1407 port->writep = port->flip;
1408 if (port->writep == port->readp) {
1409 /* Receive buffer overrun, discard oldest */
1410 port->readp++;
1411 /* Wrap? */
1412 if (port->readp >= port->flip +
1413 port->in_buffer_size)
1414 port->readp = port->flip;
1415 }
1416 if (sync_data_avail(port) >= port->inbufchunk) {
1417 /* Wake up application */
1418 wake_up_interruptible(&port->in_wait_q);
1419 }
1420 }
1421
1422 /* Transmitter ready? */
1423 if (*R_IRQ_MASK1_RD & (1 << port->transmitter_ready_bit)) {
1424 if (port->out_count > 0) {
1425 /* More data to send */
1426 send_word(port);
1427 } else {
1428 /* Transmission finished */
1429 /* Turn off IRQ */
1430 *R_IRQ_MASK1_CLR = 1 <<
1431 port->transmitter_ready_bit;
1432 /* Wake up application */
1433 wake_up_interruptible(&port->out_wait_q);
1434 }
1435 }
1436 }
1437 return IRQ_RETVAL(handled);
1438}
1439#endif
1440
1441module_init(etrax_sync_serial_init);