CC3000HostDriver for device TI CC3000 some changes were made due to mbed compiler and the use of void*
Embed:
(wiki syntax)
Show/hide line numbers
spi.cpp
00001 00002 /***************************************************************************** 00003 * 00004 * spi.c - CC3000 Host Driver Implementation. 00005 * Copyright (C) 2011 Texas Instruments Incorporated - http://www.ti.com/ 00006 * 00007 * Redistribution and use in source and binary forms, with or without 00008 * modification, are permitted provided that the following conditions 00009 * are met: 00010 * 00011 * Redistributions of source code must retain the above copyright 00012 * notice, this list of conditions and the following disclaimer. 00013 * 00014 * Redistributions in binary form must reproduce the above copyright 00015 * notice, this list of conditions and the following disclaimer in the 00016 * documentation and/or other materials provided with the 00017 * distribution. 00018 * 00019 * Neither the name of Texas Instruments Incorporated nor the names of 00020 * its contributors may be used to endorse or promote products derived 00021 * from this software without specific prior written permission. 00022 * 00023 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 00024 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 00025 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 00026 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 00027 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 00028 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 00029 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 00030 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 00031 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 00032 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 00033 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00034 * 00035 *****************************************************************************/ 00036 00037 //***************************************************************************** 00038 // 00039 //! \addtogroup link_buff_api 00040 //! @{ 00041 // 00042 //***************************************************************************** 00043 #include "hci.h" 00044 #include "spi.h" 00045 #include "evnt_handler.h" 00046 #include "mbed.h" 00047 #include "CC3000Core.h" 00048 //#include "board.h" 00049 //#include <msp430.h> 00050 00051 SPI spi(p5, p6, p7); // mosi, miso, sclk 00052 DigitalOut cs(p8); // chip select 00053 00054 00055 #define READ 3 00056 #define WRITE 1 00057 00058 #define HI(value) (((value) & 0xFF00) >> 8) 00059 #define LO(value) ((value) & 0x00FF) 00060 00061 #define ASSERT_CS() (cs = 0)//(RF_CS_OUT &= ~RF_CS) 00062 00063 #define DEASSERT_CS() (cs = 1)//(RF_CS_OUT |= RF_CS) 00064 00065 #define HEADERS_SIZE_EVNT (SPI_HEADER_SIZE + 5) 00066 00067 #define SPI_HEADER_SIZE (5) 00068 00069 #define eSPI_STATE_POWERUP (0) 00070 #define eSPI_STATE_INITIALIZED (1) 00071 #define eSPI_STATE_IDLE (2) 00072 #define eSPI_STATE_WRITE_IRQ (3) 00073 #define eSPI_STATE_WRITE_FIRST_PORTION (4) 00074 #define eSPI_STATE_WRITE_EOT (5) 00075 #define eSPI_STATE_READ_IRQ (6) 00076 #define eSPI_STATE_READ_FIRST_PORTION (7) 00077 #define eSPI_STATE_READ_EOT (8) 00078 00079 00080 typedef struct 00081 { 00082 gcSpiHandleRx SPIRxHandler; 00083 unsigned short usTxPacketLength; 00084 unsigned short usRxPacketLength; 00085 unsigned long ulSpiState; 00086 unsigned char *pTxPacket; 00087 unsigned char *pRxPacket; 00088 00089 }tSpiInformation; 00090 00091 00092 tSpiInformation sSpiInformation; 00093 00094 00095 // buffer for 5 bytes of SPI HEADER 00096 unsigned char tSpiReadHeader[] = {READ, 0, 0, 0, 0}; 00097 00098 00099 void SpiWriteDataSynchronous(unsigned char *data, unsigned short size); 00100 void SpiWriteAsync(const unsigned char *data, unsigned short size); 00101 void SpiPauseSpi(void); 00102 void SpiResumeSpi(void); 00103 void SSIContReadOperation(void); 00104 00105 // The magic number that resides at the end of the TX/RX buffer (1 byte after 00106 // the allocated size) for the purpose of detection of the overrun. The location 00107 // of the memory where the magic number resides shall never be written. In case 00108 // it is written - the overrun occurred and either receive function or send 00109 // function will stuck forever. 00110 #define CC3000_BUFFER_MAGIC_NUMBER (0xDE) 00111 00112 /////////////////////////////////////////////////////////////////////////////////////////////////////////// 00113 //__no_init is used to prevent the buffer initialization in order to prevent hardware WDT expiration /// 00114 // before entering to 'main()'. /// 00115 //for every IDE, different syntax exists : 1. __CCS__ for CCS v5 /// 00116 // 2. __IAR_SYSTEMS_ICC__ for IAR Embedded Workbench /// 00117 // *CCS does not initialize variables - therefore, __no_init is not needed. /// 00118 /////////////////////////////////////////////////////////////////////////////////////////////////////////// 00119 00120 //#ifdef __CCS__ 00121 char spi_buffer[CC3000_RX_BUFFER_SIZE]; 00122 00123 //#elif __IAR_SYSTEMS_ICC__ 00124 //__no_init char spi_buffer[CC3000_RX_BUFFER_SIZE]; 00125 //#endif 00126 00127 //#ifdef __CCS__ 00128 unsigned char wlan_tx_buffer[CC3000_TX_BUFFER_SIZE]; 00129 00130 //#elif __IAR_SYSTEMS_ICC__ 00131 //__no_init unsigned char wlan_tx_buffer[CC3000_TX_BUFFER_SIZE]; 00132 //#endif 00133 00134 //***************************************************************************** 00135 // 00136 //! SpiCleanGPIOISR 00137 //! 00138 //! \param none 00139 //! 00140 //! \return none 00141 //! 00142 //! \brief This function get the reason for the GPIO interrupt and clear 00143 //! corresponding interrupt flag 00144 // 00145 //***************************************************************************** 00146 void 00147 SpiCleanGPIOISR(void) 00148 { 00149 WlanInterruptDisable(); 00150 //SPI_IFG_PORT &= ~SPI_IRQ_PIN; 00151 } 00152 00153 //***************************************************************************** 00154 // 00155 //! SpiClose 00156 //! 00157 //! @param none 00158 //! 00159 //! @return none 00160 //! 00161 //! @brief Close Spi interface 00162 // 00163 //***************************************************************************** 00164 void 00165 SpiClose(void) 00166 { 00167 if (sSpiInformation.pRxPacket) 00168 { 00169 sSpiInformation.pRxPacket = 0; 00170 } 00171 00172 // Disable Interrupt 00173 tSLInformation.WlanInterruptDisable(); 00174 } 00175 00176 00177 //***************************************************************************** 00178 // 00179 //! SpiOpen 00180 //! 00181 //! @param none 00182 //! 00183 //! @return none 00184 //! 00185 //! @brief Open Spi interface 00186 // 00187 //***************************************************************************** 00188 void 00189 SpiOpen(gcSpiHandleRx pfRxHandler) 00190 { 00191 sSpiInformation.ulSpiState = eSPI_STATE_POWERUP; 00192 sSpiInformation.SPIRxHandler = pfRxHandler; 00193 sSpiInformation.usTxPacketLength = 0; 00194 sSpiInformation.pTxPacket = NULL; 00195 sSpiInformation.pRxPacket = (unsigned char *)spi_buffer; 00196 sSpiInformation.usRxPacketLength = 0; 00197 spi_buffer[CC3000_RX_BUFFER_SIZE - 1] = CC3000_BUFFER_MAGIC_NUMBER; 00198 wlan_tx_buffer[CC3000_TX_BUFFER_SIZE - 1] = CC3000_BUFFER_MAGIC_NUMBER; 00199 00200 // Enable interrupt on WLAN IRQ pin 00201 tSLInformation.WlanInterruptEnable(); 00202 } 00203 00204 //***************************************************************************** 00205 // 00206 //! init_spi 00207 //! 00208 //! @param none 00209 //! 00210 //! @return none 00211 //! 00212 //! @brief initializes an SPI interface 00213 // 00214 //***************************************************************************** 00215 00216 int init_spi(void) 00217 { 00218 00219 spi.frequency(16000000); 00220 spi.format(8, 1); 00221 cs = 1; 00222 00223 //UCB0CTL1 |= UCSWRST; // Put state machine in reset 00224 //UCB0CTL0 = UCMSB + UCMST + UCMODE_0 + UCSYNC; // 3-pin, 8-bit SPI master 00225 00226 //UCB0CTL1 = UCSWRST + UCSSEL_2; // Use SMCLK, keep RESET 00227 00228 // Set SPI clock 00229 //UCB0CTL1 |= UCSWRST; // Put state machine in reset 00230 //UCB0BR0 = 2; // f_UCxCLK = 25MHz/2 = 12.5MHz 00231 //UCB0BR1 = 0; 00232 //UCB0CTL1 &= ~UCSWRST; 00233 00234 return(ESUCCESS); 00235 } 00236 00237 //***************************************************************************** 00238 // 00239 //! SpiFirstWrite 00240 //! 00241 //! @param ucBuf buffer to write 00242 //! @param usLength buffer's length 00243 //! 00244 //! @return none 00245 //! 00246 //! @brief enter point for first write flow 00247 // 00248 //***************************************************************************** 00249 long 00250 SpiFirstWrite(unsigned char *ucBuf, unsigned short usLength) 00251 { 00252 // workaround for first transaction 00253 ASSERT_CS(); 00254 00255 // Assuming we are running on 24 MHz ~50 micro delay is 1200 cycles; 00256 //__delay_cycles(1200); 00257 wait_us(50); 00258 00259 // SPI writes first 4 bytes of data 00260 SpiWriteDataSynchronous(ucBuf, 4); 00261 00262 //__delay_cycles(1200); 00263 wait_us(50); 00264 SpiWriteDataSynchronous(ucBuf + 4, usLength - 4); 00265 00266 // From this point on - operate in a regular way 00267 sSpiInformation.ulSpiState = eSPI_STATE_IDLE; 00268 00269 DEASSERT_CS(); 00270 00271 return(0); 00272 } 00273 00274 00275 //***************************************************************************** 00276 // 00277 //! SpiWrite 00278 //! 00279 //! @param pUserBuffer buffer to write 00280 //! @param usLength buffer's length 00281 //! 00282 //! @return none 00283 //! 00284 //! @brief Spi write operation 00285 // 00286 //***************************************************************************** 00287 long 00288 SpiWrite(unsigned char *pUserBuffer, unsigned short usLength) 00289 { 00290 unsigned char ucPad = 0; 00291 00292 // Figure out the total length of the packet in order to figure out if there 00293 // is padding or not 00294 if(!(usLength & 0x0001)) 00295 { 00296 ucPad++; 00297 } 00298 00299 pUserBuffer[0] = WRITE; 00300 pUserBuffer[1] = HI(usLength + ucPad); 00301 pUserBuffer[2] = LO(usLength + ucPad); 00302 pUserBuffer[3] = 0; 00303 pUserBuffer[4] = 0; 00304 00305 usLength += (SPI_HEADER_SIZE + ucPad); 00306 00307 // The magic number that resides at the end of the TX/RX buffer (1 byte after 00308 // the allocated size) for the purpose of detection of the overrun. If the 00309 // magic number is overwritten - buffer overrun occurred - and we will stuck 00310 // here forever! 00311 if (wlan_tx_buffer[CC3000_TX_BUFFER_SIZE - 1] != CC3000_BUFFER_MAGIC_NUMBER) 00312 { 00313 while (1) 00314 { 00315 printf("Buffer over run\r\n"); 00316 }// ; 00317 } 00318 00319 if (sSpiInformation.ulSpiState == eSPI_STATE_POWERUP) 00320 { 00321 while (sSpiInformation.ulSpiState != eSPI_STATE_INITIALIZED) 00322 ; 00323 } 00324 00325 if (sSpiInformation.ulSpiState == eSPI_STATE_INITIALIZED) 00326 { 00327 // This is time for first TX/RX transactions over SPI: the IRQ is down - 00328 // so need to send read buffer size command 00329 SpiFirstWrite(pUserBuffer, usLength); 00330 00331 } 00332 else 00333 { 00334 // We need to prevent here race that can occur in case 2 back to back 00335 // packets are sent to the device, so the state will move to IDLE and once 00336 //again to not IDLE due to IRQ 00337 tSLInformation.WlanInterruptDisable(); 00338 00339 while (sSpiInformation.ulSpiState != eSPI_STATE_IDLE) 00340 { 00341 printf("Wait for eSPI_STATE_IDLE\r\n"); 00342 } 00343 00344 sSpiInformation.ulSpiState = eSPI_STATE_WRITE_IRQ; 00345 sSpiInformation.pTxPacket = pUserBuffer; 00346 sSpiInformation.usTxPacketLength = usLength; 00347 00348 // Assert the CS line and wait till SSI IRQ line is active and then 00349 // initialize write operation 00350 ASSERT_CS(); 00351 00352 // Re-enable IRQ - if it was not disabled - this is not a problem... 00353 tSLInformation.WlanInterruptEnable(); 00354 00355 // check for a missing interrupt between the CS assertion and enabling back the interrupts 00356 if (tSLInformation.ReadWlanInterruptPin() == 0) 00357 { 00358 SpiWriteDataSynchronous(sSpiInformation.pTxPacket, sSpiInformation.usTxPacketLength); 00359 00360 sSpiInformation.ulSpiState = eSPI_STATE_IDLE; 00361 00362 DEASSERT_CS(); 00363 } 00364 } 00365 00366 // Due to the fact that we are currently implementing a blocking situation 00367 // here we will wait till end of transaction 00368 while (eSPI_STATE_IDLE != sSpiInformation.ulSpiState) 00369 ; 00370 00371 return(0); 00372 } 00373 00374 00375 //***************************************************************************** 00376 // 00377 //! SpiWriteDataSynchronous 00378 //! 00379 //! @param data buffer to write 00380 //! @param size buffer's size 00381 //! 00382 //! @return none 00383 //! 00384 //! @brief Spi write operation 00385 // 00386 //***************************************************************************** 00387 void 00388 SpiWriteDataSynchronous(unsigned char *data, unsigned short size) 00389 { 00390 while (size) 00391 { 00392 00393 //while (!(TXBufferIsEmpty())); 00394 //UCB0TXBUF = *data; 00395 spi.write(*data); 00396 //while (!(RXBufferIsEmpty())); 00397 //spi.write(0x00); 00398 //UCB0RXBUF; 00399 size --; 00400 //printf("data %x\r\n",*data); 00401 data++; 00402 } 00403 } 00404 00405 //***************************************************************************** 00406 // 00407 //! SpiReadDataSynchronous 00408 //! 00409 //! @param data buffer to read 00410 //! @param size buffer's size 00411 //! 00412 //! @return none 00413 //! 00414 //! @brief Spi read operation 00415 // 00416 //***************************************************************************** 00417 void 00418 SpiReadDataSynchronous(unsigned char *data, unsigned short size) 00419 { 00420 00421 unsigned char *data_to_send = tSpiReadHeader; 00422 //printf("SPI Read..\r\n"); 00423 for (int i = 0; i < size; i ++) 00424 { 00425 //while (!(TXBufferIsEmpty())); 00426 //Dummy write to trigger the clock 00427 //UCB0TXBUF = data_to_send[0]; 00428 //spi.write(data_to_send[0]); 00429 //while (!(RXBufferIsEmpty())); 00430 data[i] = spi.write(data_to_send[0]); 00431 //data[i] = UCB0RXBUF; 00432 //printf("SPI Read..%x\r\n",data[i]); 00433 } 00434 } 00435 00436 00437 //***************************************************************************** 00438 // 00439 //! SpiReadHeader 00440 //! 00441 //! \param buffer 00442 //! 00443 //! \return none 00444 //! 00445 //! \brief This function enter point for read flow: first we read minimal 5 00446 //! SPI header bytes and 5 Event Data bytes 00447 // 00448 //***************************************************************************** 00449 void 00450 SpiReadHeader(void) 00451 { 00452 SpiReadDataSynchronous(sSpiInformation.pRxPacket, 10); 00453 } 00454 00455 00456 //***************************************************************************** 00457 // 00458 //! SpiReadDataCont 00459 //! 00460 //! @param None 00461 //! 00462 //! @return None 00463 //! 00464 //! @brief This function processes received SPI Header and in accordance with 00465 //! it - continues reading the packet 00466 // 00467 //***************************************************************************** 00468 long 00469 SpiReadDataCont(void) 00470 { 00471 long data_to_recv; 00472 unsigned char *evnt_buff, type; 00473 00474 //determine what type of packet we have 00475 evnt_buff = sSpiInformation.pRxPacket; 00476 data_to_recv = 0; 00477 STREAM_TO_UINT8((char *)(evnt_buff + SPI_HEADER_SIZE), HCI_PACKET_TYPE_OFFSET, type); 00478 00479 switch(type) 00480 { 00481 case HCI_TYPE_DATA: 00482 { 00483 // We need to read the rest of data.. 00484 STREAM_TO_UINT16((char *)(evnt_buff + SPI_HEADER_SIZE), HCI_DATA_LENGTH_OFFSET, data_to_recv); 00485 if (!((HEADERS_SIZE_EVNT + data_to_recv) & 1)) 00486 { 00487 data_to_recv++; 00488 } 00489 00490 if (data_to_recv) 00491 { 00492 SpiReadDataSynchronous(evnt_buff + 10, data_to_recv); 00493 } 00494 break; 00495 } 00496 case HCI_TYPE_EVNT: 00497 { 00498 // Calculate the rest length of the data 00499 STREAM_TO_UINT8((char *)(evnt_buff + SPI_HEADER_SIZE), 00500 HCI_EVENT_LENGTH_OFFSET, data_to_recv); 00501 data_to_recv -= 1; 00502 00503 // Add padding byte if needed 00504 if ((HEADERS_SIZE_EVNT + data_to_recv) & 1) 00505 { 00506 00507 data_to_recv++; 00508 } 00509 00510 if (data_to_recv) 00511 { 00512 SpiReadDataSynchronous(evnt_buff + 10, data_to_recv); 00513 } 00514 00515 sSpiInformation.ulSpiState = eSPI_STATE_READ_EOT; 00516 break; 00517 } 00518 } 00519 00520 return (0); 00521 } 00522 00523 00524 //***************************************************************************** 00525 // 00526 //! SpiPauseSpi 00527 //! 00528 //! @param none 00529 //! 00530 //! @return none 00531 //! 00532 //! @brief Spi pause operation 00533 // 00534 //***************************************************************************** 00535 00536 void 00537 SpiPauseSpi(void) 00538 { 00539 WlanInterruptDisable(); 00540 //SPI_IRQ_IE &= ~SPI_IRQ_PIN; 00541 } 00542 00543 00544 //***************************************************************************** 00545 // 00546 //! SpiResumeSpi 00547 //! 00548 //! @param none 00549 //! 00550 //! @return none 00551 //! 00552 //! @brief Spi resume operation 00553 // 00554 //***************************************************************************** 00555 00556 void 00557 SpiResumeSpi(void) 00558 { 00559 WlanInterruptEnable(); 00560 //SPI_IRQ_IE |= SPI_IRQ_PIN; 00561 } 00562 00563 00564 //***************************************************************************** 00565 // 00566 //! SpiTriggerRxProcessing 00567 //! 00568 //! @param none 00569 //! 00570 //! @return none 00571 //! 00572 //! @brief Spi RX processing 00573 // 00574 //***************************************************************************** 00575 void 00576 SpiTriggerRxProcessing(void) 00577 { 00578 00579 // Trigger Rx processing 00580 SpiPauseSpi(); 00581 DEASSERT_CS(); 00582 00583 // The magic number that resides at the end of the TX/RX buffer (1 byte after 00584 // the allocated size) for the purpose of detection of the overrun. If the 00585 // magic number is overwritten - buffer overrun occurred - and we will stuck 00586 // here forever! 00587 if (sSpiInformation.pRxPacket[CC3000_RX_BUFFER_SIZE - 1] != CC3000_BUFFER_MAGIC_NUMBER) 00588 { 00589 while (1) 00590 printf("Buffer Over run....\r\n"); 00591 ; 00592 } 00593 00594 sSpiInformation.ulSpiState = eSPI_STATE_IDLE; 00595 sSpiInformation.SPIRxHandler(sSpiInformation.pRxPacket + SPI_HEADER_SIZE); 00596 } 00597 00598 //***************************************************************************** 00599 // 00600 //! IntSpiGPIOHandler 00601 //! 00602 //! @param none 00603 //! 00604 //! @return none 00605 //! 00606 //! @brief GPIO A interrupt handler. When the external SSI WLAN device is 00607 //! ready to interact with Host CPU it generates an interrupt signal. 00608 //! After that Host CPU has registered this interrupt request 00609 //! it set the corresponding /CS in active state. 00610 // 00611 //***************************************************************************** 00612 //#pragma vector=PORT2_VECTOR 00613 //__interrupt void IntSpiGPIOHandler(void) 00614 void IntSpiGPIOHandler(void) 00615 { 00616 //switch(__even_in_range(P2IV, P2IV_P2IFG7)) 00617 //printf("IRQ ISR\r\n"); 00618 //{ 00619 //case event: 00620 if (sSpiInformation.ulSpiState == eSPI_STATE_POWERUP) 00621 { 00622 //This means IRQ line was low call a callback of HCI Layer to inform 00623 //on event 00624 sSpiInformation.ulSpiState = eSPI_STATE_INITIALIZED; 00625 } 00626 else if (sSpiInformation.ulSpiState == eSPI_STATE_IDLE) 00627 { 00628 sSpiInformation.ulSpiState = eSPI_STATE_READ_IRQ; 00629 00630 /* IRQ line goes down - we are start reception */ 00631 ASSERT_CS(); 00632 00633 // Wait for TX/RX Compete which will come as DMA interrupt 00634 SpiReadHeader(); 00635 00636 sSpiInformation.ulSpiState = eSPI_STATE_READ_EOT; 00637 00638 SSIContReadOperation(); 00639 } 00640 else if (sSpiInformation.ulSpiState == eSPI_STATE_WRITE_IRQ) 00641 { 00642 SpiWriteDataSynchronous(sSpiInformation.pTxPacket, sSpiInformation.usTxPacketLength); 00643 00644 sSpiInformation.ulSpiState = eSPI_STATE_IDLE; 00645 00646 DEASSERT_CS(); 00647 } 00648 // break; 00649 //default: 00650 // break; 00651 //} 00652 00653 } 00654 00655 //***************************************************************************** 00656 // 00657 //! SSIContReadOperation 00658 //! 00659 //! @param none 00660 //! 00661 //! @return none 00662 //! 00663 //! @brief SPI read operation 00664 // 00665 //***************************************************************************** 00666 00667 void 00668 SSIContReadOperation(void) 00669 { 00670 // The header was read - continue with the payload read 00671 if (!SpiReadDataCont()) 00672 { 00673 // All the data was read - finalize handling by switching to the task 00674 // and calling from task Event Handler 00675 SpiTriggerRxProcessing(); 00676 } 00677 } 00678 00679 00680 //***************************************************************************** 00681 // 00682 //! TXBufferIsEmpty 00683 //! 00684 //! @param 00685 //! 00686 //! @return returns 1 if buffer is empty, 0 otherwise 00687 //! 00688 //! @brief Indication if TX SPI buffer is empty 00689 // 00690 //***************************************************************************** 00691 00692 long TXBufferIsEmpty(void) 00693 { 00694 //return (UCB0IFG&UCTXIFG); 00695 return (1); 00696 } 00697 00698 //***************************************************************************** 00699 // 00700 //! RXBufferIsEmpty 00701 //! 00702 //! @param none 00703 //! 00704 //! @return returns 1 if buffer is empty, 0 otherwise 00705 //! 00706 //! @brief Indication if RX SPI buffer is empty 00707 // 00708 //***************************************************************************** 00709 00710 long RXBufferIsEmpty(void) 00711 { 00712 //return (UCB0IFG&UCRXIFG); 00713 return (0); 00714 } 00715 00716 //***************************************************************************** 00717 // 00718 // Close the Doxygen group. 00719 //! @} 00720 // 00721 //***************************************************************************** 00722
Generated on Tue Jul 12 2022 19:26:44 by 1.7.2