00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040 #include <cfg/clock.h>
00041
00042 #ifdef UART_USES_NPL
00043 #include <dev/npl.h>
00044 #endif
00045
00046 #include <sys/atom.h>
00047 #include <sys/event.h>
00048 #include <sys/timer.h>
00049
00050 #include <dev/irqreg.h>
00051
00052 #include <dev/usartat91.h>
00053
00054
00055
00056
00057 #ifndef UART_INIT_BAUDRATE
00058 #define UART_INIT_BAUDRATE 115200
00059 #endif
00060
00061
00062
00063
00064 #ifndef UART_RXTX_PINS_ENABLE
00065 #define UART_RXTX_PINS_ENABLE()
00066 #endif
00067
00068 #ifndef UART_HDX_PIN_ENABLE
00069 #define UART_HDX_PIN_ENABLE()
00070 #endif
00071 #ifndef UART_HDX_RX
00072 #define UART_HDX_RX()
00073 #endif
00074 #ifndef UART_HDX_TX
00075 #define UART_HDX_TX()
00076 #endif
00077
00078 #ifndef UART_RTS_PIN_ENABLE
00079 #define UART_RTS_PIN_ENABLE()
00080 #endif
00081 #ifndef UART_RTS_ON
00082 #define UART_RTS_ON()
00083 #endif
00084 #ifndef UART_RTS_OFF
00085 #define UART_RTS_OFF()
00086 #endif
00087
00088 #ifndef UART_CTS_PIN_ENABLE
00089 #define UART_CTS_PIN_ENABLE()
00090 #endif
00091 #ifndef UART_CTS_IS_ON
00092 #define UART_CTS_IS_ON() (1)
00093 #endif
00094
00095 #ifndef UART_MODEM_PINS_ENABLE
00096 #define UART_MODEM_PINS_ENABLE()
00097 #endif
00098
00099
00100
00101
00102
00103 #if defined(UART_HDX_BIT) && defined(UART_HDX_PIO_ID)
00104
00105 #undef UART_HDX_RX
00106 #undef UART_HDX_TX
00107 #undef UART_HDX_PIN_ENABLE
00108 #undef GPIO_ID
00109 #define GPIO_ID UART_HDX_PIO_ID
00110 #include <cfg/arch/porttran.h>
00111 static INLINE void UART_HDX_PIN_ENABLE(void) {
00112 GPIO_ENABLE(UART_HDX_BIT);
00113 GPIO_OUTPUT(UART_HDX_BIT);
00114 }
00115 #ifdef UART_HDX_FLIP_BIT
00116 static INLINE void UART_HDX_RX(void) { GPIO_SET_HI(UART_HDX_BIT); }
00117 static INLINE void UART_HDX_TX(void) { GPIO_SET_LO(UART_HDX_BIT); }
00118 #else
00119 static INLINE void UART_HDX_RX(void) { GPIO_SET_LO(UART_HDX_BIT); }
00120 static INLINE void UART_HDX_TX(void) { GPIO_SET_HI(UART_HDX_BIT); }
00121 #endif
00122
00123 #elif defined(UART_USES_NPL)
00124
00125 #undef UART_HDX_RX
00126 #undef UART_HDX_TX
00127 #define UART_HDX_RX() cbi(NPL_RSCR, NPL_RSRTS_BIT)
00128 #define UART_HDX_TX() sbi(NPL_RSCR, NPL_RSRTS_BIT)
00129
00130 #endif
00131
00132
00133
00134
00135 #if defined(UART_RTS_BIT) && defined(UART_RTS_PIO_ID)
00136
00137 #undef UART_RTS_ON
00138 #undef UART_RTS_OFF
00139 #undef UART_RTS_PIN_ENABLE
00140 #undef GPIO_ID
00141 #define GPIO_ID UART_RTS_PIO_ID
00142 #include <cfg/arch/porttran.h>
00143 static INLINE void UART_RTS_PIN_ENABLE(void) { \
00144 GPIO_ENABLE(UART_RTS_BIT); \
00145 GPIO_OUTPUT(UART_RTS_BIT); \
00146 }
00147 #ifdef UART_RTS_FLIP_BIT
00148 static INLINE void UART_RTS_ON(void) { GPIO_SET_HI(UART_RTS_BIT); }
00149 static INLINE void UART_RTS_OFF(void) { GPIO_SET_LO(UART_RTS_BIT); }
00150 #else
00151 static INLINE void UART_RTS_ON(void) { GPIO_SET_LO(UART_RTS_BIT); }
00152 static INLINE void UART_RTS_OFF(void) { GPIO_SET_HI(UART_RTS_BIT); }
00153 #endif
00154
00155 #elif defined(UART_USES_NPL)
00156
00157 #undef UART_RTS_ON
00158 #undef UART_RTS_OFF
00159 #define UART_RTS_ON() cbi(NPL_RSCR, NPL_RSRTS_BIT)
00160 #define UART_RTS_OFF() sbi(NPL_RSCR, NPL_RSRTS_BIT)
00161
00162 #endif
00163
00164
00165
00166
00167 #if defined(UART_CTS_BIT) && defined(UART_CTS_PIO_ID)
00168
00169 #undef UART_CTS_IS_ON
00170 #undef UART_CTS_PIN_ENABLE
00171 #undef GPIO_ID
00172 #define GPIO_ID UART_CTS_PIO_ID
00173 #include <cfg/arch/porttran.h>
00174 #ifdef UART_CTS_FLIP_BIT
00175 static INLINE int UART_CTS_IS_ON(void) { return GPIO_GET(UART_CTS_BIT); }
00176 #else
00177 static INLINE int UART_CTS_IS_ON(void) { return !GPIO_GET(UART_CTS_BIT); }
00178 #endif
00179 static INLINE void UART_CTS_PIN_ENABLE(void) { \
00180 GPIO_ENABLE(UART_CTS_BIT); \
00181 GPIO_INPUT(UART_CTS_BIT); \
00182 GPIO_PULLUP_ON(UART_CTS_BIT); \
00183 }
00184
00185 #elif defined(UART_USES_NPL)
00186
00187 #undef UART_CTS_IS_ON
00188 static INLINE int UART_CTS_IS_ON(void) {
00189 outw(NPL_SCR, NPL_RSCTS);
00190 return bit_is_set(NPL_SLR, NPL_RSCTS_BIT);
00191 }
00192
00193 #endif
00194
00195
00196
00197
00198 #if !defined(USE_BUILT_IN_HARDWARE_HANDSHAKE)
00199 #if defined(UART_HARDWARE_HANDSHAKE) && \
00200 defined(US_MODE_HWHANDSHAKE) && \
00201 !defined(UART_RTS_BIT) && \
00202 !defined(UART_CTS_BIT) && \
00203 !defined(UART_USES_NPL)
00204 #define USE_BUILT_IN_HARDWARE_HANDSHAKE 1
00205 #else
00206 #define USE_BUILT_IN_HARDWARE_HANDSHAKE 0
00207 #endif
00208 #endif
00209
00210
00211
00212
00213 #if !defined(USE_BUILT_IN_HALF_DUPLEX)
00214 #if defined(UART_HARDWARE_HANDSHAKE) && !defined(UART_HDX_BIT) && !defined(UART_USES_NPL)
00215 #define USE_BUILT_IN_HALF_DUPLEX 1
00216 #else
00217 #define USE_BUILT_IN_HALF_DUPLEX 0
00218 #endif
00219 #endif
00220
00225
00226
00227 #define ASCII_XON 0x11
00228
00229 #define ASCII_XOFF 0x13
00230
00231
00232 #define XON_PENDING 0x10
00233
00234 #define XOFF_PENDING 0x20
00235
00236 #define XOFF_SENT 0x40
00237
00238 #define XOFF_RCVD 0x80
00239
00240
00244 static unsigned int rx_errors;
00245
00249 static uint_fast8_t flow_control;
00250
00254 static uint_fast8_t tx_aframe;
00255
00261 static uint_fast8_t hdx_control;
00262
00269 static uint_fast8_t rts_control;
00270
00277 static uint_fast8_t cts_sense;
00278
00279 #if (defined(UART_CTS_BIT) && defined(UART_CTS_SIGNAL)) || defined(UART_USES_NPL)
00280
00290 static void At91UsartCts(void *arg)
00291 {
00292
00293 #if defined(UART_USES_NPL)
00294 NplIrqDisable(&sig_RSCTS);
00295 #else
00296
00297 #endif
00298
00299 outr(USARTn_BASE + US_IER_OFF, US_TXRDY);
00300 }
00301 #endif
00302
00303 #if USE_BUILT_IN_HALF_DUPLEX == 0
00304
00305
00306
00307
00308
00309
00310
00311
00312 static void At91UsartTxEmpty(RINGBUF *rbf)
00313 {
00314
00315
00316
00317
00318 if (hdx_control && (rbf->rbf_cnt == 0)) {
00319
00320
00321
00322
00323
00324 outr(USARTn_BASE + US_CR_OFF, US_RXEN | US_TXDIS);
00325 #if defined(UART_HDX_BIT) || defined(UART_USES_NPL)
00326 UART_HDX_RX();
00327 #endif
00328 }
00329 }
00330 #endif
00331
00332
00333
00334
00335
00336
00337 static void At91UsartTxReady(RINGBUF *rbf)
00338 {
00339 register uint8_t *cp = rbf->rbf_tail;
00340
00341
00342
00343
00344 if (flow_control & (XON_PENDING | XOFF_PENDING)) {
00345 if (flow_control & XON_PENDING) {
00346 outr(USARTn_BASE + US_THR_OFF, ASCII_XOFF);
00347 flow_control |= XOFF_SENT;
00348 } else {
00349 outr(USARTn_BASE + US_THR_OFF, ASCII_XON);
00350 flow_control &= ~XOFF_SENT;
00351 }
00352 flow_control &= ~(XON_PENDING | XOFF_PENDING);
00353 return;
00354 }
00355
00356 if (flow_control & XOFF_RCVD) {
00357
00358
00359
00360
00361 outr(USARTn_BASE + US_IDR_OFF, US_TXRDY);
00362 return;
00363 }
00364
00365
00366
00367
00368 if (rbf->rbf_cnt) {
00369 #if defined(UART_CTS_BIT) || defined(UART_USES_NPL)
00370
00371
00372
00373
00374 if (cts_sense && !UART_CTS_IS_ON()) {
00375 outr(USARTn_BASE + US_IDR_OFF, US_TXRDY);
00376 #if defined(UART_CTS_BIT)
00377
00378 #else
00379 NplIrqEnable(&sig_RSCTS);
00380 #endif
00381 return;
00382 }
00383 #endif
00384
00385
00386
00387
00388 if (tx_aframe) {
00389 outr(USARTn_BASE + US_CR_OFF, US_SENDA);
00390 }
00391
00392
00393 outr(USARTn_BASE + US_THR_OFF, *cp);
00394
00395 rbf->rbf_cnt--;
00396
00397 if (++cp == rbf->rbf_last) {
00398 cp = rbf->rbf_start;
00399 }
00400 rbf->rbf_tail = cp;
00401
00402 #if USE_BUILT_IN_HALF_DUPLEX == 0
00403
00404
00405
00406
00407 if( hdx_control && rbf->rbf_cnt == 0) {
00408 outr(USARTn_BASE + US_IER_OFF, US_TXEMPTY);
00409 }
00410 #endif
00411
00412
00413 if (rbf->rbf_cnt == rbf->rbf_lwm) {
00414 NutEventPostFromIrq(&rbf->rbf_que);
00415 }
00416 }
00417
00418
00419
00420
00421 else {
00422
00423 outr(USARTn_BASE + US_IDR_OFF, US_TXRDY);
00424
00425 NutEventPostFromIrq(&rbf->rbf_que);
00426 }
00427 }
00428
00429
00430
00431
00432
00433
00434
00435
00436
00437 static void At91UsartRxReady(RINGBUF *rbf)
00438 {
00439 register size_t cnt;
00440 register uint8_t ch;
00441
00442
00443
00444
00445
00446 ch = inb(USARTn_BASE + US_RHR_OFF);
00447
00448
00449 rx_errors |= inr(USARTn_BASE + US_CSR_OFF) & (US_OVRE | US_FRAME | US_PARE);
00450
00451
00452
00453
00454
00455
00456 if (flow_control) {
00457
00458 if (ch == ASCII_XOFF) {
00459 outr(USARTn_BASE + US_IDR_OFF, US_TXRDY);
00460 flow_control |= XOFF_RCVD;
00461 return;
00462 }
00463
00464 else if (ch == ASCII_XON) {
00465 outr(USARTn_BASE + US_IER_OFF, US_TXRDY);
00466 flow_control &= ~XOFF_RCVD;
00467 return;
00468 }
00469 }
00470
00471
00472
00473
00474 cnt = rbf->rbf_cnt;
00475 if (cnt >= rbf->rbf_siz) {
00476 rx_errors |= US_OVRE;
00477 return;
00478 }
00479
00480
00481 if (cnt++ == 0){
00482 NutEventPostFromIrq(&rbf->rbf_que);
00483 }
00484
00485
00486
00487
00488
00489 else if (flow_control) {
00490 if(cnt >= rbf->rbf_hwm) {
00491 if((flow_control & XOFF_SENT) == 0) {
00492 if (inr(USARTn_BASE + US_CSR_OFF) & US_TXRDY) {
00493 outb(USARTn_BASE + US_THR_OFF, ASCII_XOFF);
00494 flow_control |= XOFF_SENT;
00495 flow_control &= ~XOFF_PENDING;
00496 } else {
00497 flow_control |= XOFF_PENDING;
00498 }
00499 }
00500 }
00501 }
00502
00503 #if defined(UART_RTS_BIT) || defined(UART_USES_NPL)
00504
00505
00506
00507
00508
00509 else if (rts_control && cnt >= rbf->rbf_hwm) {
00510 UART_RTS_OFF();
00511 }
00512 #endif
00513
00514
00515
00516
00517 *rbf->rbf_head++ = ch;
00518 if (rbf->rbf_head == rbf->rbf_last) {
00519 rbf->rbf_head = rbf->rbf_start;
00520 }
00521
00522
00523 rbf->rbf_cnt = cnt;
00524 }
00525
00531 static void At91UsartInterrupt(void *arg)
00532 {
00533 USARTDCB *dcb = (USARTDCB *)arg;
00534 unsigned int csr = inr(USARTn_BASE + US_CSR_OFF);
00535
00536 if (csr & US_RXRDY) {
00537 At91UsartRxReady(&dcb->dcb_rx_rbf);
00538 }
00539 if (csr & US_TXRDY) {
00540 At91UsartTxReady(&dcb->dcb_tx_rbf);
00541 }
00542
00543 #if USE_BUILT_IN_HALF_DUPLEX == 0
00544 if (csr & US_TXEMPTY) {
00545 At91UsartTxEmpty(&dcb->dcb_tx_rbf);
00546 }
00547 #endif
00548 }
00549
00556 static void At91UsartEnable(void)
00557 {
00558
00559 outr(USARTn_BASE + US_CR_OFF, US_RXEN | US_TXEN);
00560
00561 NutIrqEnable(&SIG_UART);
00562 }
00563
00586 static void At91UsartDisable(void)
00587 {
00588
00589 NutIrqDisable(&SIG_UART);
00590
00591 if (inr(USARTn_BASE + US_CSR_OFF) & US_TXRDY) {
00592 while((inr(USARTn_BASE + US_CSR_OFF) & US_TXEMPTY) == 0);
00593 }
00594
00595 outr(USARTn_BASE + US_CR_OFF, US_RXDIS | US_TXDIS);
00596 }
00597
00606 static uint32_t At91UsartGetSpeed(void)
00607 {
00608 unsigned int cs;
00609 uint32_t clk;
00610
00611 clk = NutClockGet(NUT_HWCLK_PERIPHERAL);
00612 cs = inr(USARTn_BASE + US_MR_OFF) & US_CLKS;
00613 if (cs == US_CLKS_MCK8) {
00614 clk /= 8;
00615 }
00616 else if (cs != US_CLKS_MCK) {
00617 clk = 0;
00618 }
00619 return clk / (16UL * (inr(USARTn_BASE + US_BRGR_OFF) & 0xFFFF));
00620 }
00621
00632 static int At91UsartSetSpeed(uint32_t rate)
00633 {
00634 At91UsartDisable();
00635 outr(USARTn_BASE + US_BRGR_OFF, (NutClockGet(NUT_HWCLK_PERIPHERAL) / (8 * (rate)) + 1) / 2);
00636 At91UsartEnable();
00637
00638 return 0;
00639 }
00640
00649 static uint8_t At91UsartGetDataBits(void)
00650 {
00651 unsigned int val = inr(USARTn_BASE + US_MR_OFF);
00652
00653 if ((val & US_PAR) == US_PAR_MULTIDROP) {
00654 val = 9;
00655 }
00656 else {
00657 val &= US_CHRL;
00658 if (val == US_CHRL_5) {
00659 val = 5;
00660 }
00661 else if (val == US_CHRL_6) {
00662 val = 6;
00663 }
00664 else if (val == US_CHRL_7) {
00665 val = 7;
00666 }
00667 else {
00668 val = 8;
00669 }
00670 }
00671 return (uint8_t)val;
00672 }
00673
00682 static int At91UsartSetDataBits(uint8_t bits)
00683 {
00684 unsigned int val = inr(USARTn_BASE + US_MR_OFF);
00685
00686 if (bits == 9) {
00687 val &= ~US_PAR;
00688 val |= US_PAR_MULTIDROP;
00689 }
00690 else {
00691 val &= ~US_CHRL;
00692 if (bits == 5) {
00693 val |= US_CHRL_5;
00694 }
00695 else if (bits == 6) {
00696 val |= US_CHRL_6;
00697 }
00698 else if (bits == 7) {
00699 val |= US_CHRL_7;
00700 }
00701 else if (bits == 8) {
00702 val |= US_CHRL_8;
00703 }
00704 }
00705
00706 At91UsartDisable();
00707 outr(USARTn_BASE + US_MR_OFF, val);
00708 At91UsartEnable();
00709
00710
00711
00712
00713 if (At91UsartGetDataBits() != bits) {
00714 return -1;
00715 }
00716 return 0;
00717 }
00718
00727 static uint8_t At91UsartGetParity(void)
00728 {
00729 unsigned int val = inr(USARTn_BASE + US_MR_OFF) & US_PAR;
00730
00731 if ((val & US_PAR) == US_PAR_MULTIDROP) {
00732 val = 9;
00733 }
00734 else {
00735 if (val == US_PAR_ODD) {
00736 val = 1;
00737 }
00738 else if (val == US_PAR_EVEN) {
00739 val = 2;
00740 }
00741 else {
00742 val = 0;
00743 }
00744 }
00745 return (uint8_t)val;
00746 }
00747
00758 static int At91UsartSetParity(uint8_t mode)
00759 {
00760 unsigned int val = inr(USARTn_BASE + US_MR_OFF) & ~US_PAR;
00761
00762 switch (mode) {
00763 case 0:
00764 val |= US_PAR_NO;
00765 break;
00766 case 1:
00767 val |= US_PAR_ODD;
00768 break;
00769 case 2:
00770 val |= US_PAR_EVEN;
00771 break;
00772 }
00773 At91UsartDisable();
00774 outr(USARTn_BASE + US_MR_OFF, val);
00775 At91UsartEnable();
00776
00777
00778
00779
00780 if (At91UsartGetParity() != mode) {
00781 return -1;
00782 }
00783 return 0;
00784 }
00785
00794 static uint8_t At91UsartGetStopBits(void)
00795 {
00796 unsigned int val = inr(USARTn_BASE + US_MR_OFF) & US_NBSTOP;
00797 if (val == US_NBSTOP_1) {
00798 val = 1;
00799 }
00800 else if (val == US_NBSTOP_2) {
00801 val = 2;
00802 }
00803 else {
00804 val = 3;
00805 }
00806 return (uint8_t)val;
00807 }
00808
00817 static int At91UsartSetStopBits(uint8_t bits)
00818 {
00819 unsigned int val = inr(USARTn_BASE + US_MR_OFF) & ~US_NBSTOP;
00820
00821 switch(bits) {
00822 case 1:
00823 val |= US_NBSTOP_1;
00824 break;
00825 case 2:
00826 val |= US_NBSTOP_2;
00827 break;
00828 case 3:
00829 val |= US_NBSTOP_1_5;
00830 break;
00831 }
00832 At91UsartDisable();
00833 outr(USARTn_BASE + US_MR_OFF, val);
00834 At91UsartEnable();
00835
00836
00837
00838
00839 if (At91UsartGetStopBits() != bits) {
00840 return -1;
00841 }
00842 return 0;
00843 }
00844
00850 static uint32_t At91UsartGetStatus(void)
00851 {
00852 uint32_t rc = 0;
00853 #if USE_BUILT_IN_HARDWARE_HANDSHAKE
00854 uint32_t csr = inr(USARTn_BASE + US_CSR_OFF);
00855 #endif
00856
00857
00858
00859
00860 if ((rx_errors & US_FRAME) != 0) {
00861 rc |= UART_FRAMINGERROR;
00862 }
00863 if ((rx_errors & US_OVRE) != 0) {
00864 rc |= UART_OVERRUNERROR;
00865 }
00866 if ((rx_errors & US_PARE) != 0) {
00867 rc |= UART_PARITYERROR;
00868 }
00869
00870
00871
00872
00873
00874 if (flow_control) {
00875 if (flow_control & XOFF_SENT) {
00876 rc |= UART_RXDISABLED;
00877 }
00878 if (flow_control & XOFF_RCVD) {
00879 rc |= UART_TXDISABLED;
00880 }
00881 }
00882
00883
00884
00885
00886 #if USE_BUILT_IN_HARDWARE_HANDSHAKE
00887
00888 #elif defined(UART_RTS_BIT)
00889
00890 #elif defined(UART_USES_NPL)
00891 if (bit_is_set(NPL_RSCR, NPL_RSRTS_BIT)) {
00892 rc |= UART_RTSDISABLED;
00893 if (rts_control) {
00894 rc |= UART_RXDISABLED;
00895 }
00896 } else {
00897 rc |= UART_RTSENABLED;
00898 }
00899 #endif
00900
00901
00902
00903
00904 #if USE_BUILT_IN_HARDWARE_HANDSHAKE
00905 if (csr & US_CTS) {
00906 rc |= UART_CTSDISABLED;
00907 if (cts_sense) {
00908 rc |= UART_RXDISABLED;
00909 }
00910 } else {
00911 rc |= UART_CTSENABLED;
00912 }
00913 #else
00914 if (UART_CTS_IS_ON()) {
00915 rc |= UART_CTSENABLED;
00916 } else {
00917 rc |= UART_CTSDISABLED;
00918 if (cts_sense) {
00919 rc |= UART_RXDISABLED;
00920 }
00921 }
00922 #endif
00923
00924
00925
00926
00927 #if 0
00928
00929 if (csr & US_RI) {
00930 rc |= UART_RIDISABLED;
00931 } else {
00932 rc |= UART_RIENABLED;
00933 }
00934 if (csr & US_DSR) {
00935 rc |= UART_DSRDISABLED;
00936 } else {
00937 rc |= UART_DSRENABLED;
00938 }
00939 if (csr & US_DCD) {
00940 rc |= UART_DCDDISABLED;
00941 } else {
00942 rc |= UART_DCDENABLED;
00943 }
00944 #endif
00945
00946
00947
00948
00949
00950 if ((rc & UART_RXDISABLED) == 0) {
00951 rc |= UART_RXENABLED;
00952 }
00953 if ((rc & UART_TXDISABLED) == 0) {
00954 rc |= UART_TXENABLED;
00955 }
00956
00957
00958
00959
00960 if (tx_aframe) {
00961 rc |= UART_TXADDRFRAME;
00962 } else {
00963 rc |= UART_TXNORMFRAME;
00964 }
00965 return rc;
00966 }
00967
00975 static int At91UsartSetStatus(uint32_t flags)
00976 {
00977
00978
00979
00980 if (flow_control) {
00981
00982
00983 NutIrqDisable(&SIG_UART);
00984
00985
00986
00987
00988
00989 if (flags & UART_RXENABLED) {
00990 flow_control &= ~XOFF_SENT;
00991 } else if (flags & UART_RXDISABLED) {
00992 flow_control |= XOFF_SENT;
00993 }
00994
00995
00996
00997
00998
00999 if (flags & UART_TXENABLED) {
01000 flow_control &= ~XOFF_RCVD;
01001 } else if (flags & UART_TXDISABLED) {
01002 flow_control |= XOFF_RCVD;
01003 }
01004 NutIrqEnable(&SIG_UART);
01005 }
01006
01007
01008
01009
01010 #if USE_BUILT_IN_HARDWARE_HANDSHAKE
01011
01012 if (rts_control) {
01013 if (flags & UART_RXDISABLED) {
01014 outr(USARTn_BASE + US_CR_OFF, US_RTSDIS);
01015 }
01016 if (flags & UART_RXENABLED) {
01017 outr(USARTn_BASE + US_CR_OFF, US_RTSEN);
01018 }
01019 }
01020 if (flags & UART_RTSDISABLED) {
01021 outr(USARTn_BASE + US_CR_OFF, US_RTSDIS);
01022 }
01023 if (flags & UART_RTSENABLED) {
01024 outr(USARTn_BASE + US_CR_OFF, US_RTSEN);
01025 }
01026 #else
01027
01028 if (rts_control) {
01029 if (flags & UART_RXDISABLED) {
01030 UART_RTS_OFF();
01031 }
01032 if (flags & UART_RXENABLED) {
01033 UART_RTS_ON();
01034 }
01035 }
01036 if (flags & UART_RTSDISABLED) {
01037 UART_RTS_OFF();
01038 }
01039 if (flags & UART_RTSENABLED) {
01040 UART_RTS_ON();
01041 }
01042 #endif
01043
01044
01045
01046
01047
01048 #if USE_BUILT_IN_MODEM_CONTROL
01049
01050 if (flags & UART_DTRDISABLED) {
01051 outr(USARTn_BASE + US_CR_OFF, US_DTRDIS);
01052 }
01053 if (flags & UART_DTRENABLED) {
01054 outr(USARTn_BASE + US_CR_OFF, US_DTREN);
01055 }
01056 #endif
01057
01058
01059
01060
01061 if (flags & UART_TXADDRFRAME) {
01062 tx_aframe = 1;
01063 }
01064 if (flags & UART_TXNORMFRAME) {
01065 tx_aframe = 0;
01066 }
01067
01068
01069
01070
01071 if (flags & UART_ERRORS) {
01072 outr(USARTn_BASE + US_CR_OFF, US_RSTSTA);
01073 }
01074
01075
01076
01077
01078 if ((At91UsartGetStatus() & ~UART_ERRORS) != flags) {
01079 return -1;
01080 }
01081 return 0;
01082 }
01083
01095 static uint8_t At91UsartGetClockMode(void)
01096 {
01097 return 0;
01098 }
01099
01113 static int At91UsartSetClockMode(uint8_t mode)
01114 {
01115 return -1;
01116 }
01117
01126 static uint32_t At91UsartGetFlowControl(void)
01127 {
01128 uint32_t rc = 0;
01129
01130 if (flow_control) {
01131 rc |= USART_MF_XONXOFF;
01132 } else {
01133 rc &= ~USART_MF_XONXOFF;
01134 }
01135
01136 #if defined(UART_RTS_BIT) || defined(UART_USES_NPL) || defined(UART_HARDWARE_HANDSHAKE)
01137 if (rts_control) {
01138 rc |= USART_MF_RTSCONTROL;
01139 } else {
01140 rc &= ~USART_MF_RTSCONTROL;
01141 }
01142 #endif
01143
01144 #if defined(UART_CTS_BIT) || defined(UART_USES_NPL) || defined(UART_HARDWARE_HANDSHAKE)
01145 if (cts_sense) {
01146 rc |= USART_MF_CTSSENSE;
01147 } else {
01148 rc &= ~USART_MF_CTSSENSE;
01149 }
01150 #endif
01151
01152 if (hdx_control) {
01153 rc |= USART_MF_HALFDUPLEX;
01154 } else {
01155 rc &= ~USART_MF_HALFDUPLEX;
01156 }
01157 return rc;
01158 }
01159
01170 static int At91UsartSetFlowControl(uint32_t flags)
01171 {
01172 #if USE_BUILT_IN_HARDWARE_HANDSHAKE
01173 uint32_t mr = inr(USARTn_BASE + US_MR_OFF) & ~US_MODE;
01174 #endif
01175
01176
01177
01178
01179 NutIrqDisable(&SIG_UART);
01180 if (flags & USART_MF_XONXOFF) {
01181 if(flow_control == 0) {
01182 flow_control = 1 | XOFF_SENT;
01183 }
01184 } else {
01185 flow_control = 0;
01186 }
01187 NutIrqEnable(&SIG_UART);
01188
01189
01190
01191
01192 if (flags & USART_MF_RTSCONTROL) {
01193 rts_control = 1;
01194 UART_RTS_PIN_ENABLE();
01195 UART_RTS_OFF();
01196 #if USE_BUILT_IN_HARDWARE_HANDSHAKE
01197 outr(USARTn_BASE + US_MR_OFF, mr | US_MODE_HWHANDSHAKE);
01198 cts_sense = 1;
01199 #endif
01200 } else if (rts_control) {
01201 rts_control = 0;
01202 UART_RTS_ON();
01203 #if USE_BUILT_IN_HARDWARE_HANDSHAKE
01204 outr(USARTn_BASE + US_MR_OFF, mr);
01205 cts_sense = 0;
01206 #endif
01207 }
01208
01209
01210
01211
01212 if (flags & USART_MF_CTSSENSE) {
01213 cts_sense = 1;
01214 UART_CTS_PIN_ENABLE();
01215 #if USE_BUILT_IN_HARDWARE_HANDSHAKE
01216 rts_control = 1;
01217 outr(USARTn_BASE + US_MR_OFF, mr | US_MODE_HWHANDSHAKE);
01218 #endif
01219 } else if (cts_sense) {
01220 cts_sense = 0;
01221 #if USE_BUILT_IN_HARDWARE_HANDSHAKE
01222 rts_control = 0;
01223 outr(USARTn_BASE + US_MR_OFF, mr);
01224 #endif
01225 }
01226
01227
01228
01229
01230 if (flags & USART_MF_HALFDUPLEX) {
01231
01232 hdx_control = 1;
01233
01234 UART_HDX_PIN_ENABLE();
01235 UART_HDX_RX();
01236 #if USE_BUILT_IN_HALF_DUPLEX
01237
01238 outr(USARTn_BASE + US_MR_OFF, mr | US_MODE_RS485);
01239 #else
01240
01241 outr(USARTn_BASE + US_CR_OFF, US_RXEN | US_TXDIS);
01242
01243 outr(USARTn_BASE + US_IDR_OFF, US_TXEMPTY);
01244 #endif
01245 }
01246 else if (hdx_control) {
01247 hdx_control = 0;
01248 #if USE_BUILT_IN_HALF_DUPLEX
01249
01250 outr(USARTn_BASE + US_MR_OFF, inr(USARTn_BASE + US_MR_OFF) & ~US_MODE);
01251 #else
01252
01253 outr(USARTn_BASE + US_CR_OFF, US_RXEN | US_TXEN);
01254
01255 outr(USARTn_BASE + US_IDR_OFF, US_TXEMPTY);
01256 #endif
01257 }
01258
01259
01260 return 0;
01261 }
01262
01270 static void At91UsartTxStart(void)
01271 {
01272 #if USE_BUILT_IN_HALF_DUPLEX == 0
01273 if (hdx_control) {
01274 #if defined(UART_HDX_BIT) || defined(UART_USES_NPL)
01275 UART_HDX_TX();
01276 #endif
01277
01278 outr(USARTn_BASE + US_CR_OFF, US_RXDIS | US_TXEN);
01279 }
01280 #endif
01281
01282 outr(USARTn_BASE + US_IER_OFF, US_TXRDY);
01283 }
01284
01293 static void At91UsartRxStart(void)
01294 {
01295
01296
01297
01298 if (flow_control && (flow_control & XOFF_SENT) != 0) {
01299 NutIrqDisable(&SIG_UART);
01300 if ((inr(USARTn_BASE + US_CSR_OFF) & US_TXRDY)) {
01301 outr(USARTn_BASE + US_THR_OFF, ASCII_XON);
01302 flow_control &= ~XON_PENDING;
01303 } else {
01304 flow_control |= XON_PENDING;
01305 }
01306 flow_control &= ~(XOFF_SENT | XOFF_PENDING);
01307 NutIrqEnable(&SIG_UART);
01308 }
01309
01310
01311 if (rts_control) {
01312 UART_RTS_ON();
01313 }
01314 }
01315
01316
01317
01318
01319
01320
01321
01322
01323
01324 static int At91UsartInit(void)
01325 {
01326
01327
01328
01329 if (NutRegisterIrqHandler(&SIG_UART, At91UsartInterrupt, &dcb_usart)) {
01330 return -1;
01331 }
01332
01333
01334
01335
01336 #if defined(UART_CTS_BIT) && defined(UART_CTS_SIGNAL)
01337 if (NutRegisterIrqHandler(&UART_CTS_SIGNAL, At91UsartCts, NULL)) {
01338 return -1;
01339 }
01340 #elif defined(UART_USES_NPL)
01341 if (NplRegisterIrqHandler(&sig_RSCTS, At91UsartCts, NULL)) {
01342 return -1;
01343 }
01344 #endif
01345
01346
01347 #if defined(US_ID)
01348 #if defined(PS_PCER)
01349 outr(PS_PCER, _BV(US_ID));
01350 #elif defined(PMC_PCER)
01351 outr(PMC_PCER, _BV(US_ID));
01352 #endif
01353 #endif
01354
01355
01356 UART_RXTX_PINS_ENABLE();
01357
01358
01359 outr(USARTn_BASE + US_CR_OFF, US_RSTRX | US_RSTTX | US_RXDIS | US_TXDIS);
01360
01361 outr(USARTn_BASE + US_IDR_OFF, 0xFFFFFFFF);
01362
01363 #if defined(US_RCR_OFF) && defined(US_TCR_OFF)
01364
01365 outr(USARTn_BASE + US_RCR_OFF, 0);
01366 outr(USARTn_BASE + US_TCR_OFF, 0);
01367 #endif
01368
01369
01370 outr(USARTn_BASE + US_BRGR_OFF, (NutArchClockGet(NUT_HWCLK_PERIPHERAL) / (8 * (UART_INIT_BAUDRATE)) + 1) / 2);
01371
01372
01373 outr(USARTn_BASE + US_MR_OFF, US_CHMODE_NORMAL | US_CHRL_8 | US_PAR_NO | US_NBSTOP_1);
01374
01375 return 0;
01376 }
01377
01378
01379
01380
01381
01382
01383
01384
01385
01386 static int At91UsartDeinit(void)
01387 {
01388
01389 NutRegisterIrqHandler(&SIG_UART, 0, 0);
01390
01391
01392 outr(USARTn_BASE + US_CR_OFF, US_RSTRX | US_RSTTX | US_RXDIS | US_TXDIS);
01393
01394 outr(USARTn_BASE + US_IDR_OFF, 0xFFFFFFFF);
01395
01396
01397 #if defined (US_ID)
01398 #if defined(PS_PCDR)
01399 outr(PS_PCDR, _BV(US_ID));
01400 #elif defined(PMC_PCDR)
01401 outr(PMC_PCDR, _BV(US_ID));
01402 #endif
01403 #endif
01404
01405
01406
01407
01408
01409
01410 hdx_control = 0;
01411 UART_HDX_RX();
01412 cts_sense = 0;
01413 rts_control = 0;
01414
01415 return 0;
01416 }
01417