00001
00040 #include "hw/hw_ser.h"
00041 #include <hw/hw_cpufreq.h>
00042
00043 #include "cfg/cfg_ser.h"
00044 #include <cfg/debug.h>
00045
00046
00047 #include <io/arm.h>
00048
00049 #include <cpu/attr.h>
00050
00051 #include <drv/ser.h>
00052 #include <drv/ser_p.h>
00053
00054 #include <struct/fifobuf.h>
00055
00056
00057 #define SERIRQ_PRIORITY 4 ///< default priority for serial irqs.
00058
00080 #ifndef SER_UART0_BUS_TXINIT
00081
00086 #if !CPU_ARM_SAM7S_LARGE && !CPU_ARM_SAM7X
00087 #warning Check USART0 pins!
00088 #endif
00089 #define SER_UART0_BUS_TXINIT do { \
00090 PIOA_PDR = BV(RXD0) | BV(TXD0); \
00091 } while (0)
00092
00093 #endif
00094
00095 #ifndef SER_UART0_BUS_TXBEGIN
00096
00099 #define SER_UART0_BUS_TXBEGIN
00100 #endif
00101
00102 #ifndef SER_UART0_BUS_TXCHAR
00103
00106 #define SER_UART0_BUS_TXCHAR(c) do { \
00107 US0_THR = (c); \
00108 } while (0)
00109 #endif
00110
00111 #ifndef SER_UART0_BUS_TXEND
00112
00115 #define SER_UART0_BUS_TXEND
00116 #endif
00117
00118
00119
00120 #ifndef SER_UART1_BUS_TXINIT
00121
00126 #if !CPU_ARM_SAM7S_LARGE && !CPU_ARM_SAM7X
00127 #warning Check USART1 pins!
00128 #endif
00129 #define SER_UART1_BUS_TXINIT do { \
00130 PIOA_PDR = BV(RXD1) | BV(TXD1); \
00131 } while (0)
00132
00133 #endif
00134
00135 #ifndef SER_UART1_BUS_TXBEGIN
00136
00139 #define SER_UART1_BUS_TXBEGIN
00140 #endif
00141
00142 #ifndef SER_UART1_BUS_TXCHAR
00143
00146 #define SER_UART1_BUS_TXCHAR(c) do { \
00147 US1_THR = (c); \
00148 } while (0)
00149 #endif
00150
00151 #ifndef SER_UART1_BUS_TXEND
00152
00155 #define SER_UART1_BUS_TXEND
00156 #endif
00157
00167 #ifndef SER_SPI0_BUS_TXINIT
00168
00172 #define SER_SPI0_BUS_TXINIT
00173 #endif
00174
00175 #ifndef SER_SPI0_BUS_TXCLOSE
00176
00180 #define SER_SPI0_BUS_TXCLOSE
00181 #endif
00182
00183 #if CPU_ARM_SAM7X
00184
00185 #ifndef SER_SPI1_BUS_TXINIT
00186
00190 #define SER_SPI1_BUS_TXINIT
00191 #endif
00192
00193 #ifndef SER_SPI1_BUS_TXCLOSE
00194
00198 #define SER_SPI1_BUS_TXCLOSE
00199 #endif
00200 #endif
00201
00202
00203
00204
00205
00206
00207 extern struct Serial *ser_handles[SER_CNT];
00208
00209
00210 static unsigned char uart0_txbuffer[CONFIG_UART0_TXBUFSIZE];
00211 static unsigned char uart0_rxbuffer[CONFIG_UART0_RXBUFSIZE];
00212
00213 static unsigned char uart1_txbuffer[CONFIG_UART1_TXBUFSIZE];
00214 static unsigned char uart1_rxbuffer[CONFIG_UART1_RXBUFSIZE];
00215
00216 static unsigned char spi0_txbuffer[CONFIG_SPI0_TXBUFSIZE];
00217 static unsigned char spi0_rxbuffer[CONFIG_SPI0_RXBUFSIZE];
00218 #if CPU_ARM_SAM7X
00219 static unsigned char spi1_txbuffer[CONFIG_SPI1_TXBUFSIZE];
00220 static unsigned char spi1_rxbuffer[CONFIG_SPI1_RXBUFSIZE];
00221 #endif
00222
00239 struct ArmSerial
00240 {
00241 struct SerialHardware hw;
00242 volatile bool sending;
00243 };
00244
00245 static ISR_PROTO(uart0_irq_dispatcher);
00246 static ISR_PROTO(uart1_irq_dispatcher);
00247 static ISR_PROTO(spi0_irq_handler);
00248 #if CPU_ARM_SAM7X
00249 static ISR_PROTO(spi1_irq_handler);
00250 #endif
00251
00252
00253
00254 static void uart0_init(
00255 UNUSED_ARG(struct SerialHardware *, _hw),
00256 UNUSED_ARG(struct Serial *, ser))
00257 {
00258 US0_IDR = 0xFFFFFFFF;
00259
00260 AIC_SVR(US0_ID) = uart0_irq_dispatcher;
00261
00262 AIC_SMR(US0_ID) = AIC_SRCTYPE_INT_LEVEL_SENSITIVE | SERIRQ_PRIORITY;
00263 PMC_PCER = BV(US0_ID);
00264
00265
00266
00267
00268
00269
00270
00271 US0_CR = BV(US_RSTRX) | BV(US_RSTTX);
00272 US0_MR = US_CHMODE_NORMAL | US_CHRL_8 | US_NBSTOP_1 | US_PAR_NO;
00273 US0_CR = BV(US_RXEN) | BV(US_TXEN);
00274 US0_IER = BV(US_RXRDY);
00275
00276 SER_UART0_BUS_TXINIT;
00277
00278
00279 AIC_IECR = BV(US0_ID);
00280
00281 SER_STROBE_INIT;
00282 }
00283
00284 static void uart0_cleanup(UNUSED_ARG(struct SerialHardware *, _hw))
00285 {
00286 US0_CR = BV(US_RSTRX) | BV(US_RSTTX) | BV(US_RXDIS) | BV(US_TXDIS) | BV(US_RSTSTA);
00287 }
00288
00289 static void uart0_enabletxirq(struct SerialHardware *_hw)
00290 {
00291 struct ArmSerial *hw = (struct ArmSerial *)_hw;
00292
00293
00294
00295
00296
00297
00298 if (!hw->sending)
00299 {
00300 hw->sending = true;
00301
00302
00303
00304
00305 SER_UART0_BUS_TXBEGIN;
00306 US0_IER = BV(US_TXEMPTY);
00307 }
00308 }
00309
00310 static void uart0_setbaudrate(UNUSED_ARG(struct SerialHardware *, _hw), unsigned long rate)
00311 {
00312
00313 US0_BRGR = CPU_FREQ / (16 * rate);
00314
00315 }
00316
00317 static void uart0_setparity(UNUSED_ARG(struct SerialHardware *, _hw), int parity)
00318 {
00319 US0_MR &= ~US_PAR_MASK;
00320
00321 switch(parity)
00322 {
00323 case SER_PARITY_NONE:
00324 {
00325
00326 US0_MR |= US_PAR_NO;
00327 break;
00328 }
00329 case SER_PARITY_EVEN:
00330 {
00331
00332 US0_MR |= US_PAR_EVEN;
00333 break;
00334 }
00335 case SER_PARITY_ODD:
00336 {
00337
00338 US0_MR |= US_PAR_ODD;
00339 break;
00340 }
00341 default:
00342 ASSERT(0);
00343 }
00344
00345 }
00346
00347
00348
00349 static void uart1_init(
00350 UNUSED_ARG(struct SerialHardware *, _hw),
00351 UNUSED_ARG(struct Serial *, ser))
00352 {
00353 US1_IDR = 0xFFFFFFFF;
00354
00355 AIC_SVR(US1_ID) = uart1_irq_dispatcher;
00356
00357 AIC_SMR(US1_ID) = AIC_SRCTYPE_INT_LEVEL_SENSITIVE | SERIRQ_PRIORITY;
00358 PMC_PCER = BV(US1_ID);
00359
00360
00361
00362
00363
00364
00365
00366 US1_CR = BV(US_RSTRX) | BV(US_RSTTX);
00367 US1_MR = US_CHMODE_NORMAL | US_CHRL_8 | US_NBSTOP_1 | US_PAR_NO;
00368 US1_CR = BV(US_RXEN) | BV(US_TXEN);
00369 US1_IER = BV(US_RXRDY);
00370
00371 SER_UART1_BUS_TXINIT;
00372
00373
00374 AIC_IECR = BV(US1_ID);
00375
00376 SER_STROBE_INIT;
00377 }
00378
00379 static void uart1_cleanup(UNUSED_ARG(struct SerialHardware *, _hw))
00380 {
00381 US1_CR = BV(US_RSTRX) | BV(US_RSTTX) | BV(US_RXDIS) | BV(US_TXDIS) | BV(US_RSTSTA);
00382 }
00383
00384 static void uart1_enabletxirq(struct SerialHardware *_hw)
00385 {
00386 struct ArmSerial *hw = (struct ArmSerial *)_hw;
00387
00388
00389
00390
00391
00392
00393 if (!hw->sending)
00394 {
00395 hw->sending = true;
00396
00397
00398
00399
00400 SER_UART1_BUS_TXBEGIN;
00401 US1_IER = BV(US_TXEMPTY);
00402 }
00403 }
00404
00405 static void uart1_setbaudrate(UNUSED_ARG(struct SerialHardware *, _hw), unsigned long rate)
00406 {
00407
00408 US1_BRGR = CPU_FREQ / (16 * rate);
00409
00410 }
00411
00412 static void uart1_setparity(UNUSED_ARG(struct SerialHardware *, _hw), int parity)
00413 {
00414 US1_MR &= ~US_PAR_MASK;
00415
00416 switch(parity)
00417 {
00418 case SER_PARITY_NONE:
00419 {
00420
00421 US1_MR |= US_PAR_NO;
00422 break;
00423 }
00424 case SER_PARITY_EVEN:
00425 {
00426
00427 US1_MR |= US_PAR_EVEN;
00428 break;
00429 }
00430 case SER_PARITY_ODD:
00431 {
00432
00433 US1_MR |= US_PAR_ODD;
00434 break;
00435 }
00436 default:
00437 ASSERT(0);
00438 }
00439
00440 }
00441
00442
00443 static void spi0_init(UNUSED_ARG(struct SerialHardware *, _hw), UNUSED_ARG(struct Serial *, ser))
00444 {
00445
00446 PIOA_PDR = BV(SPI0_SPCK) | BV(SPI0_MOSI) | BV(SPI0_MISO);
00447
00448
00449 SPI0_CR = BV(SPI_SWRST);
00450
00451
00452
00453
00454
00455 SPI0_MR = BV(SPI_MSTR) | BV(SPI_MODFDIS);
00456
00457
00458
00459
00460
00461
00462 SPI0_CSR0 = BV(SPI_NCPHA) | (255 << SPI_SCBR_SHIFT);
00463
00464
00465 SPI0_IDR = 0xFFFFFFFF;
00466
00467 AIC_SVR(SPI0_ID) = spi0_irq_handler;
00468
00469 AIC_SMR(SPI0_ID) = AIC_SRCTYPE_INT_EDGE_TRIGGERED | SERIRQ_PRIORITY;
00470
00471 AIC_IECR = BV(SPI0_ID);
00472 PMC_PCER = BV(SPI0_ID);
00473
00474
00475 SPI0_IER = BV(SPI_TXEMPTY);
00476
00477
00478 SPI0_CR = BV(SPI_SPIEN);
00479
00480
00481 SER_SPI0_BUS_TXINIT;
00482
00483 SER_STROBE_INIT;
00484 }
00485
00486 static void spi0_cleanup(UNUSED_ARG(struct SerialHardware *, _hw))
00487 {
00488
00489 SPI0_CR = BV(SPI_SPIDIS);
00490
00491
00492 SPI0_IDR = 0xFFFFFFFF;
00493
00494 SER_SPI0_BUS_TXCLOSE;
00495
00496
00497 PIOA_PER = BV(SPI0_SPCK) | BV(SPI0_MOSI) | BV(SPI0_MISO);
00498 }
00499
00500 static void spi0_starttx(struct SerialHardware *_hw)
00501 {
00502 struct ArmSerial *hw = (struct ArmSerial *)_hw;
00503
00504 cpu_flags_t flags;
00505 IRQ_SAVE_DISABLE(flags);
00506
00507
00508 if (!hw->sending && !fifo_isempty(&ser_handles[SER_SPI0]->txfifo))
00509 {
00510 hw->sending = true;
00511 SPI0_TDR = fifo_pop(&ser_handles[SER_SPI0]->txfifo);
00512 }
00513
00514 IRQ_RESTORE(flags);
00515 }
00516
00517 static void spi0_setbaudrate(UNUSED_ARG(struct SerialHardware *, _hw), unsigned long rate)
00518 {
00519 SPI0_CSR0 &= ~SPI_SCBR;
00520
00521 ASSERT((uint8_t)DIV_ROUND(CPU_FREQ, rate));
00522 SPI0_CSR0 |= DIV_ROUND(CPU_FREQ, rate) << SPI_SCBR_SHIFT;
00523 }
00524
00525 #if CPU_ARM_SAM7X
00526
00527 static void spi1_init(UNUSED_ARG(struct SerialHardware *, _hw), UNUSED_ARG(struct Serial *, ser))
00528 {
00529
00530 PIOA_PDR = BV(SPI1_SPCK) | BV(SPI1_MOSI) | BV(SPI1_MISO);
00531
00532
00533 PIOA_BSR = BV(SPI1_SPCK) | BV(SPI1_MOSI) | BV(SPI1_MISO);
00534
00535
00536 SPI1_CR = BV(SPI_SWRST);
00537
00538
00539
00540
00541
00542 SPI1_MR = BV(SPI_MSTR) | BV(SPI_MODFDIS);
00543
00544
00545
00546
00547
00548
00549 SPI1_CSR0 = BV(SPI_NCPHA) | (255 << SPI_SCBR_SHIFT);
00550
00551
00552 SPI1_IDR = 0xFFFFFFFF;
00553
00554 AIC_SVR(SPI1_ID) = spi1_irq_handler;
00555
00556 AIC_SMR(SPI1_ID) = AIC_SRCTYPE_INT_EDGE_TRIGGERED | SERIRQ_PRIORITY;
00557
00558 AIC_IECR = BV(SPI1_ID);
00559 PMC_PCER = BV(SPI1_ID);
00560
00561
00562 SPI1_IER = BV(SPI_TXEMPTY);
00563
00564
00565 SPI1_CR = BV(SPI_SPIEN);
00566
00567
00568 SER_SPI1_BUS_TXINIT;
00569
00570 SER_STROBE_INIT;
00571 }
00572
00573 static void spi1_cleanup(UNUSED_ARG(struct SerialHardware *, _hw))
00574 {
00575
00576 SPI1_CR = BV(SPI_SPIDIS);
00577
00578
00579 SPI1_IDR = 0xFFFFFFFF;
00580
00581 SER_SPI1_BUS_TXCLOSE;
00582
00583
00584 PIOA_PER = BV(SPI1_SPCK) | BV(SPI1_MOSI) | BV(SPI1_MISO);
00585 }
00586
00587 static void spi1_starttx(struct SerialHardware *_hw)
00588 {
00589 struct ArmSerial *hw = (struct ArmSerial *)_hw;
00590
00591 cpu_flags_t flags;
00592 IRQ_SAVE_DISABLE(flags);
00593
00594
00595 if (!hw->sending && !fifo_isempty(&ser_handles[SER_SPI1]->txfifo))
00596 {
00597 hw->sending = true;
00598 SPI1_TDR = fifo_pop(&ser_handles[SER_SPI1]->txfifo);
00599 }
00600
00601 IRQ_RESTORE(flags);
00602 }
00603
00604 static void spi1_setbaudrate(UNUSED_ARG(struct SerialHardware *, _hw), unsigned long rate)
00605 {
00606 SPI1_CSR0 &= ~SPI_SCBR;
00607
00608 ASSERT((uint8_t)DIV_ROUND(CPU_FREQ, rate));
00609 SPI1_CSR0 |= DIV_ROUND(CPU_FREQ, rate) << SPI_SCBR_SHIFT;
00610 }
00611 #endif
00612
00613 static void spi_setparity(UNUSED_ARG(struct SerialHardware *, _hw), UNUSED_ARG(int, parity))
00614 {
00615
00616 }
00617
00618
00619 static bool tx_sending(struct SerialHardware* _hw)
00620 {
00621 struct ArmSerial *hw = (struct ArmSerial *)_hw;
00622 return hw->sending;
00623 }
00624
00625
00626 #if COMPILER_C99
00627 #define C99INIT(name,val) .name = val
00628 #elif defined(__GNUC__)
00629 #define C99INIT(name,val) name: val
00630 #else
00631 #warning No designated initializers, double check your code
00632 #define C99INIT(name,val) (val)
00633 #endif
00634
00635
00636
00637
00638 static const struct SerialHardwareVT UART0_VT =
00639 {
00640 C99INIT(init, uart0_init),
00641 C99INIT(cleanup, uart0_cleanup),
00642 C99INIT(setBaudrate, uart0_setbaudrate),
00643 C99INIT(setParity, uart0_setparity),
00644 C99INIT(txStart, uart0_enabletxirq),
00645 C99INIT(txSending, tx_sending),
00646 };
00647
00648 static const struct SerialHardwareVT UART1_VT =
00649 {
00650 C99INIT(init, uart1_init),
00651 C99INIT(cleanup, uart1_cleanup),
00652 C99INIT(setBaudrate, uart1_setbaudrate),
00653 C99INIT(setParity, uart1_setparity),
00654 C99INIT(txStart, uart1_enabletxirq),
00655 C99INIT(txSending, tx_sending),
00656 };
00657
00658 static const struct SerialHardwareVT SPI0_VT =
00659 {
00660 C99INIT(init, spi0_init),
00661 C99INIT(cleanup, spi0_cleanup),
00662 C99INIT(setBaudrate, spi0_setbaudrate),
00663 C99INIT(setParity, spi_setparity),
00664 C99INIT(txStart, spi0_starttx),
00665 C99INIT(txSending, tx_sending),
00666 };
00667 #if CPU_ARM_SAM7X
00668 static const struct SerialHardwareVT SPI1_VT =
00669 {
00670 C99INIT(init, spi1_init),
00671 C99INIT(cleanup, spi1_cleanup),
00672 C99INIT(setBaudrate, spi1_setbaudrate),
00673 C99INIT(setParity, spi_setparity),
00674 C99INIT(txStart, spi1_starttx),
00675 C99INIT(txSending, tx_sending),
00676 };
00677 #endif
00678
00679 static struct ArmSerial UARTDescs[SER_CNT] =
00680 {
00681 {
00682 C99INIT(hw, ) {
00683 C99INIT(table, &UART0_VT),
00684 C99INIT(txbuffer, uart0_txbuffer),
00685 C99INIT(rxbuffer, uart0_rxbuffer),
00686 C99INIT(txbuffer_size, sizeof(uart0_txbuffer)),
00687 C99INIT(rxbuffer_size, sizeof(uart0_rxbuffer)),
00688 },
00689 C99INIT(sending, false),
00690 },
00691 {
00692 C99INIT(hw, ) {
00693 C99INIT(table, &UART1_VT),
00694 C99INIT(txbuffer, uart1_txbuffer),
00695 C99INIT(rxbuffer, uart1_rxbuffer),
00696 C99INIT(txbuffer_size, sizeof(uart1_txbuffer)),
00697 C99INIT(rxbuffer_size, sizeof(uart1_rxbuffer)),
00698 },
00699 C99INIT(sending, false),
00700 },
00701
00702 {
00703 C99INIT(hw, ) {
00704 C99INIT(table, &SPI0_VT),
00705 C99INIT(txbuffer, spi0_txbuffer),
00706 C99INIT(rxbuffer, spi0_rxbuffer),
00707 C99INIT(txbuffer_size, sizeof(spi0_txbuffer)),
00708 C99INIT(rxbuffer_size, sizeof(spi0_rxbuffer)),
00709 },
00710 C99INIT(sending, false),
00711 },
00712 #if CPU_ARM_SAM7X
00713 {
00714 C99INIT(hw, ) {
00715 C99INIT(table, &SPI1_VT),
00716 C99INIT(txbuffer, spi1_txbuffer),
00717 C99INIT(rxbuffer, spi1_rxbuffer),
00718 C99INIT(txbuffer_size, sizeof(spi1_txbuffer)),
00719 C99INIT(rxbuffer_size, sizeof(spi1_rxbuffer)),
00720 },
00721 C99INIT(sending, false),
00722 }
00723
00724 #endif
00725 };
00726
00727 struct SerialHardware *ser_hw_getdesc(int unit)
00728 {
00729 ASSERT(unit < SER_CNT);
00730 return &UARTDescs[unit].hw;
00731 }
00732
00736 INLINE void uart0_irq_tx(void)
00737 {
00738 SER_STROBE_ON;
00739
00740 struct FIFOBuffer * const txfifo = &ser_handles[SER_UART0]->txfifo;
00741
00742 if (fifo_isempty(txfifo))
00743 {
00744
00745
00746
00747 US0_IDR = BV(US_TXEMPTY);
00748 SER_UART0_BUS_TXEND;
00749 UARTDescs[SER_UART0].sending = false;
00750 }
00751 else
00752 {
00753 char c = fifo_pop(txfifo);
00754 SER_UART0_BUS_TXCHAR(c);
00755 }
00756
00757 SER_STROBE_OFF;
00758 }
00759
00763 INLINE void uart0_irq_rx(void)
00764 {
00765 SER_STROBE_ON;
00766
00767
00768 ser_handles[SER_UART0]->status |= US0_CSR & (SERRF_RXSROVERRUN | SERRF_FRAMEERROR);
00769 US0_CR = BV(US_RSTSTA);
00770
00771 char c = US0_RHR;
00772 struct FIFOBuffer * const rxfifo = &ser_handles[SER_UART0]->rxfifo;
00773
00774 if (fifo_isfull(rxfifo))
00775 ser_handles[SER_UART0]->status |= SERRF_RXFIFOOVERRUN;
00776 else
00777 fifo_push(rxfifo, c);
00778
00779 SER_STROBE_OFF;
00780 }
00781
00785 static DECLARE_ISR(uart0_irq_dispatcher)
00786 {
00787 if (US0_CSR & BV(US_RXRDY))
00788 uart0_irq_rx();
00789
00790 if (US0_CSR & BV(US_TXEMPTY))
00791 uart0_irq_tx();
00792
00793
00794 AIC_EOICR = 0;
00795 }
00796
00800 INLINE void uart1_irq_tx(void)
00801 {
00802 SER_STROBE_ON;
00803
00804 struct FIFOBuffer * const txfifo = &ser_handles[SER_UART1]->txfifo;
00805
00806 if (fifo_isempty(txfifo))
00807 {
00808
00809
00810
00811 US1_IDR = BV(US_TXEMPTY);
00812 SER_UART1_BUS_TXEND;
00813 UARTDescs[SER_UART1].sending = false;
00814 }
00815 else
00816 {
00817 char c = fifo_pop(txfifo);
00818 SER_UART1_BUS_TXCHAR(c);
00819 }
00820
00821 SER_STROBE_OFF;
00822 }
00823
00827 INLINE void uart1_irq_rx(void)
00828 {
00829 SER_STROBE_ON;
00830
00831
00832 ser_handles[SER_UART1]->status |= US1_CSR & (SERRF_RXSROVERRUN | SERRF_FRAMEERROR);
00833 US1_CR = BV(US_RSTSTA);
00834
00835 char c = US1_RHR;
00836 struct FIFOBuffer * const rxfifo = &ser_handles[SER_UART1]->rxfifo;
00837
00838 if (fifo_isfull(rxfifo))
00839 ser_handles[SER_UART1]->status |= SERRF_RXFIFOOVERRUN;
00840 else
00841 fifo_push(rxfifo, c);
00842
00843 SER_STROBE_OFF;
00844 }
00845
00849 static DECLARE_ISR(uart1_irq_dispatcher)
00850 {
00851 if (US1_CSR & BV(US_RXRDY))
00852 uart1_irq_rx();
00853
00854 if (US1_CSR & BV(US_TXEMPTY))
00855 uart1_irq_tx();
00856
00857
00858 AIC_EOICR = 0;
00859 }
00860
00864 static DECLARE_ISR(spi0_irq_handler)
00865 {
00866 SER_STROBE_ON;
00867
00868 char c = SPI0_RDR;
00869
00870 if (!fifo_isfull(&ser_handles[SER_SPI0]->rxfifo))
00871 fifo_push(&ser_handles[SER_SPI0]->rxfifo, c);
00872
00873
00874
00875
00876
00877
00878
00879 if (!fifo_isempty(&ser_handles[SER_SPI0]->txfifo))
00880 SPI0_TDR = fifo_pop(&ser_handles[SER_SPI0]->txfifo);
00881 else
00882 UARTDescs[SER_SPI0].sending = false;
00883
00884
00885 AIC_EOICR = 0;
00886 SER_STROBE_OFF;
00887 }
00888
00889
00890 #if CPU_ARM_SAM7X
00891
00894 static DECLARE_ISR(spi1_irq_handler)
00895 {
00896 SER_STROBE_ON;
00897
00898 char c = SPI1_RDR;
00899
00900 if (!fifo_isfull(&ser_handles[SER_SPI1]->rxfifo))
00901 fifo_push(&ser_handles[SER_SPI1]->rxfifo, c);
00902
00903
00904
00905
00906
00907
00908
00909 if (!fifo_isempty(&ser_handles[SER_SPI1]->txfifo))
00910 SPI1_TDR = fifo_pop(&ser_handles[SER_SPI1]->txfifo);
00911 else
00912 UARTDescs[SER_SPI1].sending = false;
00913
00914
00915 AIC_EOICR = 0;
00916 SER_STROBE_OFF;
00917 }
00918 #endif