David Fletcher / CC3000HostDriver

Dependents:   CC3000Test

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers hci.cpp Source File

hci.cpp

00001 /*****************************************************************************
00002 *
00003 *  hci.c  - CC3000 Host Driver Implementation.
00004 *  Copyright (C) 2011 Texas Instruments Incorporated - http://www.ti.com/
00005 *
00006 *  Redistribution and use in source and binary forms, with or without
00007 *  modification, are permitted provided that the following conditions
00008 *  are met:
00009 *
00010 *    Redistributions of source code must retain the above copyright
00011 *    notice, this list of conditions and the following disclaimer.
00012 *
00013 *    Redistributions in binary form must reproduce the above copyright
00014 *    notice, this list of conditions and the following disclaimer in the
00015 *    documentation and/or other materials provided with the   
00016 *    distribution.
00017 *
00018 *    Neither the name of Texas Instruments Incorporated nor the names of
00019 *    its contributors may be used to endorse or promote products derived
00020 *    from this software without specific prior written permission.
00021 *
00022 *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 
00023 *  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 
00024 *  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
00025 *  A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 
00026 *  OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 
00027 *  SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 
00028 *  LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
00029 *  DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
00030 *  THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 
00031 *  (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 
00032 *  OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00033 *
00034 *****************************************************************************/
00035 
00036 //*****************************************************************************
00037 //
00038 //! \addtogroup hci_app
00039 //! @{
00040 //
00041 //*****************************************************************************
00042 
00043 #include "cc3000_common.h"
00044 #include "hci.h"
00045 #include "mbed.h"
00046 #include "spi.h"
00047 #include "evnt_handler.h"
00048 #include "wlan.h"
00049 
00050 #define SL_PATCH_PORTION_SIZE        (1000)
00051 
00052 
00053 //*****************************************************************************
00054 //
00055 //!  hci_command_send
00056 //!
00057 //!  @param  usOpcode     command operation code
00058 //!  @param  pucBuff      pointer to the command's arguments buffer
00059 //!  @param  ucArgsLength length of the arguments
00060 //!
00061 //!  @return              none
00062 //!
00063 //!  @brief               Initiate an HCI command.
00064 //
00065 //*****************************************************************************
00066 unsigned short 
00067 hci_command_send(unsigned short usOpcode, unsigned char *pucBuff, unsigned char ucArgsLength)
00068 { 
00069     unsigned char *stream;
00070     
00071     stream = (pucBuff + SPI_HEADER_SIZE);
00072     
00073     UINT8_TO_STREAM(stream, HCI_TYPE_CMND);
00074     stream = UINT16_TO_STREAM(stream, usOpcode);
00075     UINT8_TO_STREAM(stream, ucArgsLength);
00076     
00077     //Update the opcode of the event we will be waiting for
00078     SpiWrite(pucBuff, ucArgsLength + SIMPLE_LINK_HCI_CMND_HEADER_SIZE);
00079     
00080     return(0);
00081 }
00082 
00083 //*****************************************************************************
00084 //
00085 //!  hci_data_send
00086 //!
00087 //!  @param  usOpcode        command operation code
00088 //!     @param  ucArgs                     pointer to the command's arguments buffer
00089 //!  @param  usArgsLength    length of the arguments
00090 //!  @param  ucTail          pointer to the data buffer
00091 //!  @param  usTailLength    buffer length
00092 //!
00093 //!  @return none
00094 //!
00095 //!  @brief              Initiate an HCI data write operation
00096 //
00097 //*****************************************************************************
00098 long
00099 hci_data_send(unsigned char ucOpcode, 
00100                             unsigned char *ucArgs,
00101                             unsigned short usArgsLength, 
00102                             unsigned short usDataLength,
00103                             const unsigned char *ucTail,
00104                             unsigned short usTailLength)
00105 {
00106     unsigned char *stream;
00107     
00108     stream = ((ucArgs) + SPI_HEADER_SIZE);
00109     
00110     UINT8_TO_STREAM(stream, HCI_TYPE_DATA);
00111     UINT8_TO_STREAM(stream, ucOpcode);
00112     UINT8_TO_STREAM(stream, usArgsLength);
00113     stream = UINT16_TO_STREAM(stream, usArgsLength + usDataLength + usTailLength);
00114     
00115     // Send the packet over the SPI
00116     SpiWrite(ucArgs, SIMPLE_LINK_HCI_DATA_HEADER_SIZE + usArgsLength + usDataLength + usTailLength);
00117     
00118     return(ESUCCESS);
00119 }
00120 
00121 
00122 //*****************************************************************************
00123 //
00124 //!  hci_data_command_send
00125 //!
00126 //!  @param  usOpcode      command operation code
00127 //!  @param  pucBuff       pointer to the data buffer
00128 //!  @param  ucArgsLength  arguments length
00129 //!  @param  ucDataLength  data length
00130 //!
00131 //!  @return none
00132 //!
00133 //!  @brief              Prepeare HCI header and initiate an HCI data write operation
00134 //
00135 //*****************************************************************************
00136 void hci_data_command_send(unsigned short usOpcode, unsigned char *pucBuff,
00137                      unsigned char ucArgsLength,unsigned short ucDataLength)
00138 { 
00139      unsigned char *stream = (pucBuff + SPI_HEADER_SIZE);
00140     
00141     UINT8_TO_STREAM(stream, HCI_TYPE_DATA);
00142     UINT8_TO_STREAM(stream, usOpcode);
00143     UINT8_TO_STREAM(stream, ucArgsLength);
00144     stream = UINT16_TO_STREAM(stream, ucArgsLength + ucDataLength);
00145     
00146     // Send the command over SPI on data channel
00147     SpiWrite(pucBuff, ucArgsLength + ucDataLength + SIMPLE_LINK_HCI_DATA_CMND_HEADER_SIZE);
00148     
00149     return;
00150 }
00151 
00152 //*****************************************************************************
00153 //
00154 //!  hci_patch_send
00155 //!
00156 //!  @param  usOpcode      command operation code
00157 //!  @param  pucBuff       pointer to the command's arguments buffer
00158 //!  @param  patch         pointer to patch content buffer 
00159 //!  @param  usDataLength  data length
00160 //!
00161 //!  @return              none
00162 //!
00163 //!  @brief               Prepeare HCI header and initiate an HCI patch write operation
00164 //
00165 //*****************************************************************************
00166 void
00167 hci_patch_send(unsigned char ucOpcode, unsigned char *pucBuff, char *patch, unsigned short usDataLength)
00168 { 
00169      unsigned char *data_ptr = (pucBuff + SPI_HEADER_SIZE);
00170     unsigned short usTransLength;
00171     unsigned char *stream = (pucBuff + SPI_HEADER_SIZE);
00172     
00173     UINT8_TO_STREAM(stream, HCI_TYPE_PATCH);
00174     UINT8_TO_STREAM(stream, ucOpcode);
00175     stream = UINT16_TO_STREAM(stream, usDataLength + SIMPLE_LINK_HCI_PATCH_HEADER_SIZE);
00176     
00177     if (usDataLength <= SL_PATCH_PORTION_SIZE)
00178     {
00179         UINT16_TO_STREAM(stream, usDataLength);
00180         stream = UINT16_TO_STREAM(stream, usDataLength);
00181         memcpy((pucBuff + SPI_HEADER_SIZE) + HCI_PATCH_HEADER_SIZE, patch, usDataLength);
00182         
00183         // Update the opcode of the event we will be waiting for
00184         SpiWrite(pucBuff, usDataLength + HCI_PATCH_HEADER_SIZE);
00185     }
00186     else
00187     {
00188         
00189         usTransLength = (usDataLength/SL_PATCH_PORTION_SIZE);
00190         UINT16_TO_STREAM(stream, usDataLength + SIMPLE_LINK_HCI_PATCH_HEADER_SIZE + usTransLength*SIMPLE_LINK_HCI_PATCH_HEADER_SIZE);
00191         stream = UINT16_TO_STREAM(stream, SL_PATCH_PORTION_SIZE);
00192         memcpy(pucBuff + SPI_HEADER_SIZE + HCI_PATCH_HEADER_SIZE, patch, SL_PATCH_PORTION_SIZE);
00193         usDataLength -= SL_PATCH_PORTION_SIZE;
00194         patch += SL_PATCH_PORTION_SIZE;
00195         
00196         // Update the opcode of the event we will be waiting for
00197         SpiWrite(pucBuff, SL_PATCH_PORTION_SIZE + HCI_PATCH_HEADER_SIZE);
00198         
00199         while (usDataLength)
00200         {
00201             if (usDataLength <= SL_PATCH_PORTION_SIZE)
00202             {
00203                 usTransLength = usDataLength;
00204                 usDataLength = 0;
00205                 
00206             }
00207             else
00208             {
00209                 usTransLength = SL_PATCH_PORTION_SIZE;
00210                 usDataLength -= usTransLength;
00211             }
00212             
00213             *(unsigned short *)data_ptr = usTransLength;
00214             memcpy(data_ptr + SIMPLE_LINK_HCI_PATCH_HEADER_SIZE, patch, usTransLength);
00215             patch += usTransLength;
00216             
00217             // Update the opcode of the event we will be waiting for
00218             SpiWrite((unsigned char *)data_ptr, usTransLength + sizeof(usTransLength));
00219         }
00220     }
00221 }
00222 
00223 //*****************************************************************************
00224 //
00225 // Close the Doxygen group.
00226 //! @}
00227 //
00228 //
00229 //*****************************************************************************
00230