summaryrefslogtreecommitdiff
path: root/nuttx/drivers/wireless/cc3000/evnt_handler.c
diff options
context:
space:
mode:
Diffstat (limited to 'nuttx/drivers/wireless/cc3000/evnt_handler.c')
-rw-r--r--nuttx/drivers/wireless/cc3000/evnt_handler.c1687
1 files changed, 843 insertions, 844 deletions
diff --git a/nuttx/drivers/wireless/cc3000/evnt_handler.c b/nuttx/drivers/wireless/cc3000/evnt_handler.c
index c4a362e0b..f430c820e 100644
--- a/nuttx/drivers/wireless/cc3000/evnt_handler.c
+++ b/nuttx/drivers/wireless/cc3000/evnt_handler.c
@@ -1,844 +1,843 @@
-/*****************************************************************************
-*
-* evnt_handler.c - CC3000 Host Driver Implementation.
-* Copyright (C) 2011 Texas Instruments Incorporated - http://www.ti.com/
-*
-* Redistribution and use in source and binary forms, with or without
-* modification, are permitted provided that the following conditions
-* are met:
-*
-* Redistributions of source code must retain the above copyright
-* notice, this list of conditions and the following disclaimer.
-*
-* Redistributions in binary form must reproduce the above copyright
-* notice, this list of conditions and the following disclaimer in the
-* documentation and/or other materials provided with the
-* distribution.
-*
-* Neither the name of Texas Instruments Incorporated nor the names of
-* its contributors may be used to endorse or promote products derived
-* from this software without specific prior written permission.
-*
-* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
-* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
-* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
-* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
-* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
-* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
-* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
-* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
-* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
-* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
-* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-*
-*****************************************************************************/
-//*****************************************************************************
-//
-//! \addtogroup evnt_handler_api
-//! @{
-//
-//******************************************************************************
-
-//******************************************************************************
-// INCLUDE FILES
-//******************************************************************************
-
-#include <string.h>
-#include <nuttx/cc3000/cc3000_common.h>
-#include <nuttx/cc3000/hci.h>
-#include <nuttx/cc3000/evnt_handler.h>
-#include <nuttx/cc3000/wlan.h>
-#include <nuttx/cc3000/socket.h>
-#include <nuttx/cc3000/netapp.h>
-#include <nuttx/cc3000/spi.h>
-
-
-
-//*****************************************************************************
-// COMMON DEFINES
-//*****************************************************************************
-
-#define FLOW_CONTROL_EVENT_HANDLE_OFFSET (0)
-#define FLOW_CONTROL_EVENT_BLOCK_MODE_OFFSET (1)
-#define FLOW_CONTROL_EVENT_FREE_BUFFS_OFFSET (2)
-#define FLOW_CONTROL_EVENT_SIZE (4)
-
-#define BSD_RSP_PARAMS_SOCKET_OFFSET (0)
-#define BSD_RSP_PARAMS_STATUS_OFFSET (4)
-
-#define GET_HOST_BY_NAME_RETVAL_OFFSET (0)
-#define GET_HOST_BY_NAME_ADDR_OFFSET (4)
-
-#define ACCEPT_SD_OFFSET (0)
-#define ACCEPT_RETURN_STATUS_OFFSET (4)
-#define ACCEPT_ADDRESS__OFFSET (8)
-
-#define SL_RECEIVE_SD_OFFSET (0)
-#define SL_RECEIVE_NUM_BYTES_OFFSET (4)
-#define SL_RECEIVE__FLAGS__OFFSET (8)
-
-
-#define SELECT_STATUS_OFFSET (0)
-#define SELECT_READFD_OFFSET (4)
-#define SELECT_WRITEFD_OFFSET (8)
-#define SELECT_EXFD_OFFSET (12)
-
-
-#define NETAPP_IPCONFIG_IP_OFFSET (0)
-#define NETAPP_IPCONFIG_SUBNET_OFFSET (4)
-#define NETAPP_IPCONFIG_GW_OFFSET (8)
-#define NETAPP_IPCONFIG_DHCP_OFFSET (12)
-#define NETAPP_IPCONFIG_DNS_OFFSET (16)
-#define NETAPP_IPCONFIG_MAC_OFFSET (20)
-#define NETAPP_IPCONFIG_SSID_OFFSET (26)
-
-#define NETAPP_IPCONFIG_IP_LENGTH (4)
-#define NETAPP_IPCONFIG_MAC_LENGTH (6)
-#define NETAPP_IPCONFIG_SSID_LENGTH (32)
-
-
-#define NETAPP_PING_PACKETS_SENT_OFFSET (0)
-#define NETAPP_PING_PACKETS_RCVD_OFFSET (4)
-#define NETAPP_PING_MIN_RTT_OFFSET (8)
-#define NETAPP_PING_MAX_RTT_OFFSET (12)
-#define NETAPP_PING_AVG_RTT_OFFSET (16)
-
-#define GET_SCAN_RESULTS_TABlE_COUNT_OFFSET (0)
-#define GET_SCAN_RESULTS_SCANRESULT_STATUS_OFFSET (4)
-#define GET_SCAN_RESULTS_ISVALID_TO_SSIDLEN_OFFSET (8)
-#define GET_SCAN_RESULTS_FRAME_TIME_OFFSET (10)
-#define GET_SCAN_RESULTS_SSID_MAC_LENGTH (38)
-
-
-
-//*****************************************************************************
-// GLOBAL VARAIABLES
-//*****************************************************************************
-
-unsigned long socket_active_status = SOCKET_STATUS_INIT_VAL;
-
-
-//*****************************************************************************
-// Prototypes for the static functions
-//*****************************************************************************
-
-static long hci_event_unsol_flowcontrol_handler(char *pEvent);
-
-static void update_socket_active_status(char *resp_params);
-
-
-//*****************************************************************************
-//
-//! hci_unsol_handle_patch_request
-//!
-//! @param event_hdr event header
-//!
-//! @return none
-//!
-//! @brief Handle unsolicited event from type patch request
-//
-//*****************************************************************************
-void hci_unsol_handle_patch_request(char *event_hdr)
-{
- char *params = (char *)(event_hdr) + HCI_EVENT_HEADER_SIZE;
- unsigned long ucLength = 0;
- char *patch;
-
- switch (*params)
- {
- case HCI_EVENT_PATCHES_DRV_REQ:
-
- if (tSLInformation.sDriverPatches)
- {
- patch = tSLInformation.sDriverPatches(&ucLength);
-
- if (patch)
- {
- hci_patch_send(HCI_EVENT_PATCHES_DRV_REQ,
- tSLInformation.pucTxCommandBuffer, patch, ucLength);
- return;
- }
- }
-
- // Send 0 length Patches response event
- hci_patch_send(HCI_EVENT_PATCHES_DRV_REQ,
- tSLInformation.pucTxCommandBuffer, 0, 0);
- break;
-
- case HCI_EVENT_PATCHES_FW_REQ:
-
- if (tSLInformation.sFWPatches)
- {
- patch = tSLInformation.sFWPatches(&ucLength);
-
- // Build and send a patch
- if (patch)
- {
- hci_patch_send(HCI_EVENT_PATCHES_FW_REQ,
- tSLInformation.pucTxCommandBuffer, patch, ucLength);
- return;
- }
- }
-
- // Send 0 length Patches response event
- hci_patch_send(HCI_EVENT_PATCHES_FW_REQ,
- tSLInformation.pucTxCommandBuffer, 0, 0);
- break;
-
- case HCI_EVENT_PATCHES_BOOTLOAD_REQ:
-
- if (tSLInformation.sBootLoaderPatches)
- {
- patch = tSLInformation.sBootLoaderPatches(&ucLength);
-
- if (patch)
- {
- hci_patch_send(HCI_EVENT_PATCHES_BOOTLOAD_REQ,
- tSLInformation.pucTxCommandBuffer, patch, ucLength);
- return;
- }
- }
-
- // Send 0 length Patches response event
- hci_patch_send(HCI_EVENT_PATCHES_BOOTLOAD_REQ,
- tSLInformation.pucTxCommandBuffer, 0, 0);
- break;
- }
-}
-
-
-
-//*****************************************************************************
-//
-//! hci_event_handler
-//!
-//! @param pRetParams incoming data buffer
-//! @param from from information (in case of data received)
-//! @param fromlen from information length (in case of data received)
-//!
-//! @return none
-//!
-//! @brief Parse the incoming events packets and issues corresponding
-//! event handler from global array of handlers pointers
-//
-//*****************************************************************************
-
-
-unsigned char *
-hci_event_handler(void *pRetParams, unsigned char *from, unsigned char *fromlen)
-{
- unsigned char *pucReceivedData, ucArgsize;
- unsigned short usLength;
- unsigned char *pucReceivedParams;
- unsigned short usReceivedEventOpcode = 0;
- unsigned long retValue32;
- unsigned char * RecvParams;
- unsigned char *RetParams;
-
-
- while (1)
- {
- if (tSLInformation.usEventOrDataReceived != 0)
- {
- pucReceivedData = (tSLInformation.pucReceivedData);
-
- if (*pucReceivedData == HCI_TYPE_EVNT)
- {
- // Event Received
- STREAM_TO_UINT16((char *)pucReceivedData, HCI_EVENT_OPCODE_OFFSET,
- usReceivedEventOpcode);
- pucReceivedParams = pucReceivedData + HCI_EVENT_HEADER_SIZE;
- RecvParams = pucReceivedParams;
- RetParams = (unsigned char *)pRetParams;
-
- // In case unsolicited event received - here the handling finished
- if (hci_unsol_event_handler((char *)pucReceivedData) == 0)
- {
- STREAM_TO_UINT8(pucReceivedData, HCI_DATA_LENGTH_OFFSET, usLength);
-
- switch(usReceivedEventOpcode)
- {
- case HCI_CMND_READ_BUFFER_SIZE:
- {
- STREAM_TO_UINT8((char *)pucReceivedParams, 0,
- tSLInformation.usNumberOfFreeBuffers);
- STREAM_TO_UINT16((char *)pucReceivedParams, 1,
- tSLInformation.usSlBufferLength);
- }
- break;
-
- case HCI_CMND_WLAN_CONFIGURE_PATCH:
- case HCI_NETAPP_DHCP:
- case HCI_NETAPP_PING_SEND:
- case HCI_NETAPP_PING_STOP:
- case HCI_NETAPP_ARP_FLUSH:
- case HCI_NETAPP_SET_DEBUG_LEVEL:
- case HCI_NETAPP_SET_TIMERS:
- case HCI_EVNT_NVMEM_READ:
- case HCI_EVNT_NVMEM_CREATE_ENTRY:
- case HCI_CMND_NVMEM_WRITE_PATCH:
- case HCI_NETAPP_PING_REPORT:
- case HCI_EVNT_MDNS_ADVERTISE:
-
- STREAM_TO_UINT8(pucReceivedData, HCI_EVENT_STATUS_OFFSET
- ,*(unsigned char *)pRetParams);
- break;
-
- case HCI_CMND_SETSOCKOPT:
- case HCI_CMND_WLAN_CONNECT:
- case HCI_CMND_WLAN_IOCTL_STATUSGET:
- case HCI_EVNT_WLAN_IOCTL_ADD_PROFILE:
- case HCI_CMND_WLAN_IOCTL_DEL_PROFILE:
- case HCI_CMND_WLAN_IOCTL_SET_CONNECTION_POLICY:
- case HCI_CMND_WLAN_IOCTL_SET_SCANPARAM:
- case HCI_CMND_WLAN_IOCTL_SIMPLE_CONFIG_START:
- case HCI_CMND_WLAN_IOCTL_SIMPLE_CONFIG_STOP:
- case HCI_CMND_WLAN_IOCTL_SIMPLE_CONFIG_SET_PREFIX:
- case HCI_CMND_EVENT_MASK:
- case HCI_EVNT_WLAN_DISCONNECT:
- case HCI_EVNT_SOCKET:
- case HCI_EVNT_BIND:
- case HCI_CMND_LISTEN:
- case HCI_EVNT_CLOSE_SOCKET:
- case HCI_EVNT_CONNECT:
- case HCI_EVNT_NVMEM_WRITE:
-
- STREAM_TO_UINT32((char *)pucReceivedParams,0
- ,*(unsigned long *)pRetParams);
- break;
-
- case HCI_EVNT_READ_SP_VERSION:
-
- STREAM_TO_UINT8(pucReceivedData, HCI_EVENT_STATUS_OFFSET
- ,*(unsigned char *)pRetParams);
- pRetParams = ((char *)pRetParams) + 1;
- STREAM_TO_UINT32((char *)pucReceivedParams, 0, retValue32);
- UINT32_TO_STREAM((unsigned char *)pRetParams, retValue32);
- break;
-
- case HCI_EVNT_BSD_GETHOSTBYNAME:
-
- STREAM_TO_UINT32((char *)pucReceivedParams
- ,GET_HOST_BY_NAME_RETVAL_OFFSET,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 4;
- STREAM_TO_UINT32((char *)pucReceivedParams
- ,GET_HOST_BY_NAME_ADDR_OFFSET,*(unsigned long *)pRetParams);
- break;
-
- case HCI_EVNT_ACCEPT:
- {
- STREAM_TO_UINT32((char *)pucReceivedParams,ACCEPT_SD_OFFSET
- ,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 4;
- STREAM_TO_UINT32((char *)pucReceivedParams
- ,ACCEPT_RETURN_STATUS_OFFSET,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 4;
-
- //This argument returns in network order
- memcpy((unsigned char *)pRetParams,
- pucReceivedParams + ACCEPT_ADDRESS__OFFSET, sizeof(sockaddr));
- break;
- }
-
- case HCI_EVNT_RECV:
- case HCI_EVNT_RECVFROM:
- {
- STREAM_TO_UINT32((char *)pucReceivedParams,SL_RECEIVE_SD_OFFSET ,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 4;
- STREAM_TO_UINT32((char *)pucReceivedParams,SL_RECEIVE_NUM_BYTES_OFFSET,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 4;
- STREAM_TO_UINT32((char *)pucReceivedParams,SL_RECEIVE__FLAGS__OFFSET,*(unsigned long *)pRetParams);
-
- if(((tBsdReadReturnParams *)pRetParams)->iNumberOfBytes == ERROR_SOCKET_INACTIVE)
- {
- set_socket_active_status(((tBsdReadReturnParams *)pRetParams)->iSocketDescriptor,SOCKET_STATUS_INACTIVE);
- }
- break;
- }
-
- case HCI_EVNT_SEND:
- case HCI_EVNT_SENDTO:
- {
- STREAM_TO_UINT32((char *)pucReceivedParams,SL_RECEIVE_SD_OFFSET ,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 4;
- STREAM_TO_UINT32((char *)pucReceivedParams,SL_RECEIVE_NUM_BYTES_OFFSET,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 4;
-
- break;
- }
-
- case HCI_EVNT_SELECT:
- {
- STREAM_TO_UINT32((char *)pucReceivedParams,SELECT_STATUS_OFFSET,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 4;
- STREAM_TO_UINT32((char *)pucReceivedParams,SELECT_READFD_OFFSET,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 4;
- STREAM_TO_UINT32((char *)pucReceivedParams,SELECT_WRITEFD_OFFSET,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 4;
- STREAM_TO_UINT32((char *)pucReceivedParams,SELECT_EXFD_OFFSET,*(unsigned long *)pRetParams);
- break;
- }
-
- case HCI_CMND_GETSOCKOPT:
-
- STREAM_TO_UINT8(pucReceivedData, HCI_EVENT_STATUS_OFFSET,((tBsdGetSockOptReturnParams *)pRetParams)->iStatus);
- //This argument returns in network order
- memcpy((unsigned char *)pRetParams, pucReceivedParams, 4);
- break;
-
- case HCI_CMND_WLAN_IOCTL_GET_SCAN_RESULTS:
-
- STREAM_TO_UINT32((char *)pucReceivedParams,GET_SCAN_RESULTS_TABlE_COUNT_OFFSET,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 4;
- STREAM_TO_UINT32((char *)pucReceivedParams,GET_SCAN_RESULTS_SCANRESULT_STATUS_OFFSET,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 4;
- STREAM_TO_UINT16((char *)pucReceivedParams,GET_SCAN_RESULTS_ISVALID_TO_SSIDLEN_OFFSET,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 2;
- STREAM_TO_UINT16((char *)pucReceivedParams,GET_SCAN_RESULTS_FRAME_TIME_OFFSET,*(unsigned long *)pRetParams);
- pRetParams = ((char *)pRetParams) + 2;
- memcpy((unsigned char *)pRetParams,
- (char *)(pucReceivedParams + GET_SCAN_RESULTS_FRAME_TIME_OFFSET + 2),
- GET_SCAN_RESULTS_SSID_MAC_LENGTH);
- break;
-
- case HCI_CMND_SIMPLE_LINK_START:
- break;
-
- case HCI_NETAPP_IPCONFIG:
-
- //Read IP address
- STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_IP_LENGTH);
- RecvParams += 4;
-
- //Read subnet
- STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_IP_LENGTH);
- RecvParams += 4;
-
- //Read default GW
- STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_IP_LENGTH);
- RecvParams += 4;
-
- //Read DHCP server
- STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_IP_LENGTH);
- RecvParams += 4;
-
- //Read DNS server
- STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_IP_LENGTH);
- RecvParams += 4;
-
- //Read Mac address
- STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_MAC_LENGTH);
- RecvParams += 6;
-
- //Read SSID
- STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_SSID_LENGTH);
-
- }
- }
-
- if (usReceivedEventOpcode == tSLInformation.usRxEventOpcode)
- {
- tSLInformation.usRxEventOpcode = 0;
- }
- }
- else
- {
- pucReceivedParams = pucReceivedData;
- STREAM_TO_UINT8((char *)pucReceivedData, HCI_PACKET_ARGSIZE_OFFSET, ucArgsize);
-
- STREAM_TO_UINT16((char *)pucReceivedData, HCI_PACKET_LENGTH_OFFSET, usLength);
-
- // Data received: note that the only case where from and from length
- // are not null is in recv from, so fill the args accordingly
- if (from)
- {
- STREAM_TO_UINT32((char *)(pucReceivedData + HCI_DATA_HEADER_SIZE), BSD_RECV_FROM_FROMLEN_OFFSET, *(unsigned long *)fromlen);
- memcpy(from, (pucReceivedData + HCI_DATA_HEADER_SIZE + BSD_RECV_FROM_FROM_OFFSET) ,*fromlen);
- }
-
- memcpy(pRetParams, pucReceivedParams + HCI_DATA_HEADER_SIZE + ucArgsize,
- usLength - ucArgsize);
-
- tSLInformation.usRxDataPending = 0;
- }
-
- tSLInformation.usEventOrDataReceived = 0;
-
- SpiResumeSpi();
-
- // Since we are going to TX - we need to handle this event after the
- // ResumeSPi since we need interrupts
- if ((*pucReceivedData == HCI_TYPE_EVNT) &&
- (usReceivedEventOpcode == HCI_EVNT_PATCHES_REQ))
- {
- hci_unsol_handle_patch_request((char *)pucReceivedData);
- }
-
- if ((tSLInformation.usRxEventOpcode == 0) && (tSLInformation.usRxDataPending == 0))
- {
- return NULL;
- }
- }
- }
-
-}
-
-//*****************************************************************************
-//
-//! hci_unsol_event_handler
-//!
-//! @param event_hdr event header
-//!
-//! @return 1 if event supported and handled
-//! 0 if event is not supported
-//!
-//! @brief Handle unsolicited events
-//
-//*****************************************************************************
-long
-hci_unsol_event_handler(char *event_hdr)
-{
- char * data = NULL;
- long event_type;
- unsigned long NumberOfReleasedPackets;
- unsigned long NumberOfSentPackets;
-
- STREAM_TO_UINT16(event_hdr, HCI_EVENT_OPCODE_OFFSET,event_type);
-
- if (event_type & HCI_EVNT_UNSOL_BASE)
- {
- switch(event_type)
- {
-
- case HCI_EVNT_DATA_UNSOL_FREE_BUFF:
- {
- hci_event_unsol_flowcontrol_handler(event_hdr);
-
- NumberOfReleasedPackets = tSLInformation.NumberOfReleasedPackets;
- NumberOfSentPackets = tSLInformation.NumberOfSentPackets;
-
- if (NumberOfReleasedPackets == NumberOfSentPackets)
- {
- if (tSLInformation.InformHostOnTxComplete)
- {
- tSLInformation.sWlanCB(HCI_EVENT_CC3000_CAN_SHUT_DOWN, NULL, 0);
- }
- }
- return 1;
-
- }
- }
- }
-
- if(event_type & HCI_EVNT_WLAN_UNSOL_BASE)
- {
- switch(event_type)
- {
- case HCI_EVNT_WLAN_KEEPALIVE:
- case HCI_EVNT_WLAN_UNSOL_CONNECT:
- case HCI_EVNT_WLAN_UNSOL_DISCONNECT:
- case HCI_EVNT_WLAN_UNSOL_INIT:
- case HCI_EVNT_WLAN_ASYNC_SIMPLE_CONFIG_DONE:
-
- if( tSLInformation.sWlanCB )
- {
- tSLInformation.sWlanCB(event_type, 0, 0);
- }
- break;
-
- case HCI_EVNT_WLAN_UNSOL_DHCP:
- {
- unsigned char params[NETAPP_IPCONFIG_MAC_OFFSET + 1]; // extra byte is for the status
- unsigned char *recParams = params;
-
- data = (char*)(event_hdr) + HCI_EVENT_HEADER_SIZE;
-
- //Read IP address
- STREAM_TO_STREAM(data,recParams,NETAPP_IPCONFIG_IP_LENGTH);
- data += 4;
- //Read subnet
- STREAM_TO_STREAM(data,recParams,NETAPP_IPCONFIG_IP_LENGTH);
- data += 4;
- //Read default GW
- STREAM_TO_STREAM(data,recParams,NETAPP_IPCONFIG_IP_LENGTH);
- data += 4;
- //Read DHCP server
- STREAM_TO_STREAM(data,recParams,NETAPP_IPCONFIG_IP_LENGTH);
- data += 4;
- //Read DNS server
- STREAM_TO_STREAM(data,recParams,NETAPP_IPCONFIG_IP_LENGTH);
- // read the status
- STREAM_TO_UINT8(event_hdr, HCI_EVENT_STATUS_OFFSET, *recParams);
-
-
- if( tSLInformation.sWlanCB )
- {
- tSLInformation.sWlanCB(event_type, (char *)params, sizeof(params));
- }
- }
- break;
-
- case HCI_EVNT_WLAN_ASYNC_PING_REPORT:
- {
- netapp_pingreport_args_t params;
- data = (char*)(event_hdr) + HCI_EVENT_HEADER_SIZE;
- STREAM_TO_UINT32(data, NETAPP_PING_PACKETS_SENT_OFFSET, params.packets_sent);
- STREAM_TO_UINT32(data, NETAPP_PING_PACKETS_RCVD_OFFSET, params.packets_received);
- STREAM_TO_UINT32(data, NETAPP_PING_MIN_RTT_OFFSET, params.min_round_time);
- STREAM_TO_UINT32(data, NETAPP_PING_MAX_RTT_OFFSET, params.max_round_time);
- STREAM_TO_UINT32(data, NETAPP_PING_AVG_RTT_OFFSET, params.avg_round_time);
-
- if( tSLInformation.sWlanCB )
- {
- tSLInformation.sWlanCB(event_type, (char *)&params, sizeof(params));
- }
- }
- break;
- case HCI_EVNT_BSD_TCP_CLOSE_WAIT:
- {
- if( tSLInformation.sWlanCB )
- {
- tSLInformation.sWlanCB(event_type, NULL, 0);
- }
- }
- break;
-
- //'default' case which means "event not supported"
- default:
- return (0);
- }
- return(1);
- }
-
- if ((event_type == HCI_EVNT_SEND) || (event_type == HCI_EVNT_SENDTO)
- || (event_type == HCI_EVNT_WRITE))
- {
- char *pArg;
- long status;
-
- pArg = M_BSD_RESP_PARAMS_OFFSET(event_hdr);
- STREAM_TO_UINT32(pArg, BSD_RSP_PARAMS_STATUS_OFFSET,status);
-
- if (ERROR_SOCKET_INACTIVE == status)
- {
- // The only synchronous event that can come from SL device in form of
- // command complete is "Command Complete" on data sent, in case SL device
- // was unable to transmit
- STREAM_TO_UINT8(event_hdr, HCI_EVENT_STATUS_OFFSET, tSLInformation.slTransmitDataError);
- update_socket_active_status(M_BSD_RESP_PARAMS_OFFSET(event_hdr));
-
- return (1);
- }
- else
- return (0);
- }
-
- return(0);
-}
-
-//*****************************************************************************
-//
-//! hci_unsolicited_event_handler
-//!
-//! @param None
-//!
-//! @return ESUCCESS if successful, EFAIL if an error occurred
-//!
-//! @brief Parse the incoming unsolicited event packets and issues
-//! corresponding event handler.
-//
-//*****************************************************************************
-long
-hci_unsolicited_event_handler(void)
-{
- unsigned long res = 0;
- unsigned char *pucReceivedData;
-
- if (tSLInformation.usEventOrDataReceived != 0)
- {
- pucReceivedData = (tSLInformation.pucReceivedData);
-
- if (*pucReceivedData == HCI_TYPE_EVNT)
- {
-
- // In case unsolicited event received - here the handling finished
- if (hci_unsol_event_handler((char *)pucReceivedData) == 1)
- {
-
- // There was an unsolicited event received - we can release the buffer
- // and clean the event received
- tSLInformation.usEventOrDataReceived = 0;
-
- res = 1;
- SpiResumeSpi();
- }
- }
- }
-
- return res;
-}
-
-//*****************************************************************************
-//
-//! set_socket_active_status
-//!
-//! @param Sd
-//! @param Status
-//! @return none
-//!
-//! @brief Check if the socket ID and status are valid and set
-//! accordingly the global socket status
-//
-//*****************************************************************************
-void set_socket_active_status(long Sd, long Status)
-{
- if(M_IS_VALID_SD(Sd) && M_IS_VALID_STATUS(Status))
- {
- socket_active_status &= ~(1 << Sd); /* clean socket's mask */
- socket_active_status |= (Status << Sd); /* set new socket's mask */
- }
-}
-
-
-//*****************************************************************************
-//
-//! hci_event_unsol_flowcontrol_handler
-//!
-//! @param pEvent pointer to the string contains parameters for IPERF
-//! @return ESUCCESS if successful, EFAIL if an error occurred
-//!
-//! @brief Called in case unsolicited event from type
-//! HCI_EVNT_DATA_UNSOL_FREE_BUFF has received.
-//! Keep track on the number of packets transmitted and update the
-//! number of free buffer in the SL device.
-//
-//*****************************************************************************
-long
-hci_event_unsol_flowcontrol_handler(char *pEvent)
-{
-
- long temp, value;
- unsigned short i;
- unsigned short pusNumberOfHandles=0;
- char *pReadPayload;
-
- STREAM_TO_UINT16((char *)pEvent,HCI_EVENT_HEADER_SIZE,pusNumberOfHandles);
- pReadPayload = ((char *)pEvent +
- HCI_EVENT_HEADER_SIZE + sizeof(pusNumberOfHandles));
- temp = 0;
-
- for(i = 0; i < pusNumberOfHandles ; i++)
- {
- STREAM_TO_UINT16(pReadPayload, FLOW_CONTROL_EVENT_FREE_BUFFS_OFFSET, value);
- temp += value;
- pReadPayload += FLOW_CONTROL_EVENT_SIZE;
- }
-
- tSLInformation.usNumberOfFreeBuffers += temp;
- tSLInformation.NumberOfReleasedPackets += temp;
-
- return(ESUCCESS);
-}
-
-//*****************************************************************************
-//
-//! get_socket_active_status
-//!
-//! @param Sd Socket IS
-//! @return Current status of the socket.
-//!
-//! @brief Retrieve socket status
-//
-//*****************************************************************************
-
-long
-get_socket_active_status(long Sd)
-{
- if(M_IS_VALID_SD(Sd))
- {
- return (socket_active_status & (1 << Sd)) ? SOCKET_STATUS_INACTIVE : SOCKET_STATUS_ACTIVE;
- }
- return SOCKET_STATUS_INACTIVE;
-}
-
-//*****************************************************************************
-//
-//! update_socket_active_status
-//!
-//! @param resp_params Socket IS
-//! @return Current status of the socket.
-//!
-//! @brief Retrieve socket status
-//
-//*****************************************************************************
-void
-update_socket_active_status(char *resp_params)
-{
- long status, sd;
-
- STREAM_TO_UINT32(resp_params, BSD_RSP_PARAMS_SOCKET_OFFSET,sd);
- STREAM_TO_UINT32(resp_params, BSD_RSP_PARAMS_STATUS_OFFSET,status);
-
- if(ERROR_SOCKET_INACTIVE == status)
- {
- set_socket_active_status(sd, SOCKET_STATUS_INACTIVE);
- }
-}
-
-
-//*****************************************************************************
-//
-//! SimpleLinkWaitEvent
-//!
-//! @param usOpcode command operation code
-//! @param pRetParams command return parameters
-//!
-//! @return none
-//!
-//! @brief Wait for event, pass it to the hci_event_handler and
-//! update the event opcode in a global variable.
-//
-//*****************************************************************************
-
-void
-SimpleLinkWaitEvent(unsigned short usOpcode, void *pRetParams)
-{
- // In the blocking implementation the control to caller will be returned only
- // after the end of current transaction
- tSLInformation.usRxEventOpcode = usOpcode;
- printf("Going to call hci_event_handler...\n");
- hci_event_handler(pRetParams, 0, 0);
-}
-
-//*****************************************************************************
-//
-//! SimpleLinkWaitData
-//!
-//! @param pBuf data buffer
-//! @param from from information
-//! @param fromlen from information length
-//!
-//! @return none
-//!
-//! @brief Wait for data, pass it to the hci_event_handler
-//! and update in a global variable that there is
-//! data to read.
-//
-//*****************************************************************************
-
-void
-SimpleLinkWaitData(unsigned char *pBuf, unsigned char *from,
- unsigned char *fromlen)
-{
- // In the blocking implementation the control to caller will be returned only
- // after the end of current transaction, i.e. only after data will be received
- tSLInformation.usRxDataPending = 1;
- hci_event_handler(pBuf, from, fromlen);
-}
-
-//*****************************************************************************
-//
-// Close the Doxygen group.
-//! @}
-//
-//*****************************************************************************
+/*****************************************************************************
+*
+* evnt_handler.c - CC3000 Host Driver Implementation.
+* Copyright (C) 2011 Texas Instruments Incorporated - http://www.ti.com/
+*
+* Redistribution and use in source and binary forms, with or without
+* modification, are permitted provided that the following conditions
+* are met:
+*
+* Redistributions of source code must retain the above copyright
+* notice, this list of conditions and the following disclaimer.
+*
+* Redistributions in binary form must reproduce the above copyright
+* notice, this list of conditions and the following disclaimer in the
+* documentation and/or other materials provided with the
+* distribution.
+*
+* Neither the name of Texas Instruments Incorporated nor the names of
+* its contributors may be used to endorse or promote products derived
+* from this software without specific prior written permission.
+*
+* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+*
+*****************************************************************************/
+//*****************************************************************************
+//
+//! \addtogroup evnt_handler_api
+//! @{
+//
+//******************************************************************************
+
+//******************************************************************************
+// INCLUDE FILES
+//******************************************************************************
+
+#include <string.h>
+#include <nuttx/cc3000/cc3000_common.h>
+#include <nuttx/cc3000/hci.h>
+#include <nuttx/cc3000/evnt_handler.h>
+#include <nuttx/cc3000/wlan.h>
+#include <nuttx/cc3000/socket.h>
+#include <nuttx/cc3000/netapp.h>
+#include <nuttx/cc3000/spi.h>
+
+
+
+//*****************************************************************************
+// COMMON DEFINES
+//*****************************************************************************
+
+#define FLOW_CONTROL_EVENT_HANDLE_OFFSET (0)
+#define FLOW_CONTROL_EVENT_BLOCK_MODE_OFFSET (1)
+#define FLOW_CONTROL_EVENT_FREE_BUFFS_OFFSET (2)
+#define FLOW_CONTROL_EVENT_SIZE (4)
+
+#define BSD_RSP_PARAMS_SOCKET_OFFSET (0)
+#define BSD_RSP_PARAMS_STATUS_OFFSET (4)
+
+#define GET_HOST_BY_NAME_RETVAL_OFFSET (0)
+#define GET_HOST_BY_NAME_ADDR_OFFSET (4)
+
+#define ACCEPT_SD_OFFSET (0)
+#define ACCEPT_RETURN_STATUS_OFFSET (4)
+#define ACCEPT_ADDRESS__OFFSET (8)
+
+#define SL_RECEIVE_SD_OFFSET (0)
+#define SL_RECEIVE_NUM_BYTES_OFFSET (4)
+#define SL_RECEIVE__FLAGS__OFFSET (8)
+
+
+#define SELECT_STATUS_OFFSET (0)
+#define SELECT_READFD_OFFSET (4)
+#define SELECT_WRITEFD_OFFSET (8)
+#define SELECT_EXFD_OFFSET (12)
+
+
+#define NETAPP_IPCONFIG_IP_OFFSET (0)
+#define NETAPP_IPCONFIG_SUBNET_OFFSET (4)
+#define NETAPP_IPCONFIG_GW_OFFSET (8)
+#define NETAPP_IPCONFIG_DHCP_OFFSET (12)
+#define NETAPP_IPCONFIG_DNS_OFFSET (16)
+#define NETAPP_IPCONFIG_MAC_OFFSET (20)
+#define NETAPP_IPCONFIG_SSID_OFFSET (26)
+
+#define NETAPP_IPCONFIG_IP_LENGTH (4)
+#define NETAPP_IPCONFIG_MAC_LENGTH (6)
+#define NETAPP_IPCONFIG_SSID_LENGTH (32)
+
+
+#define NETAPP_PING_PACKETS_SENT_OFFSET (0)
+#define NETAPP_PING_PACKETS_RCVD_OFFSET (4)
+#define NETAPP_PING_MIN_RTT_OFFSET (8)
+#define NETAPP_PING_MAX_RTT_OFFSET (12)
+#define NETAPP_PING_AVG_RTT_OFFSET (16)
+
+#define GET_SCAN_RESULTS_TABlE_COUNT_OFFSET (0)
+#define GET_SCAN_RESULTS_SCANRESULT_STATUS_OFFSET (4)
+#define GET_SCAN_RESULTS_ISVALID_TO_SSIDLEN_OFFSET (8)
+#define GET_SCAN_RESULTS_FRAME_TIME_OFFSET (10)
+#define GET_SCAN_RESULTS_SSID_MAC_LENGTH (38)
+
+
+
+//*****************************************************************************
+// GLOBAL VARAIABLES
+//*****************************************************************************
+
+unsigned long socket_active_status = SOCKET_STATUS_INIT_VAL;
+
+
+//*****************************************************************************
+// Prototypes for the static functions
+//*****************************************************************************
+
+static long hci_event_unsol_flowcontrol_handler(char *pEvent);
+
+static void update_socket_active_status(char *resp_params);
+
+
+//*****************************************************************************
+//
+//! hci_unsol_handle_patch_request
+//!
+//! @param event_hdr event header
+//!
+//! @return none
+//!
+//! @brief Handle unsolicited event from type patch request
+//
+//*****************************************************************************
+void hci_unsol_handle_patch_request(char *event_hdr)
+{
+ char *params = (char *)(event_hdr) + HCI_EVENT_HEADER_SIZE;
+ unsigned long ucLength = 0;
+ char *patch;
+
+ switch (*params)
+ {
+ case HCI_EVENT_PATCHES_DRV_REQ:
+
+ if (tSLInformation.sDriverPatches)
+ {
+ patch = tSLInformation.sDriverPatches(&ucLength);
+
+ if (patch)
+ {
+ hci_patch_send(HCI_EVENT_PATCHES_DRV_REQ,
+ tSLInformation.pucTxCommandBuffer, patch, ucLength);
+ return;
+ }
+ }
+
+ // Send 0 length Patches response event
+ hci_patch_send(HCI_EVENT_PATCHES_DRV_REQ,
+ tSLInformation.pucTxCommandBuffer, 0, 0);
+ break;
+
+ case HCI_EVENT_PATCHES_FW_REQ:
+
+ if (tSLInformation.sFWPatches)
+ {
+ patch = tSLInformation.sFWPatches(&ucLength);
+
+ // Build and send a patch
+ if (patch)
+ {
+ hci_patch_send(HCI_EVENT_PATCHES_FW_REQ,
+ tSLInformation.pucTxCommandBuffer, patch, ucLength);
+ return;
+ }
+ }
+
+ // Send 0 length Patches response event
+ hci_patch_send(HCI_EVENT_PATCHES_FW_REQ,
+ tSLInformation.pucTxCommandBuffer, 0, 0);
+ break;
+
+ case HCI_EVENT_PATCHES_BOOTLOAD_REQ:
+
+ if (tSLInformation.sBootLoaderPatches)
+ {
+ patch = tSLInformation.sBootLoaderPatches(&ucLength);
+
+ if (patch)
+ {
+ hci_patch_send(HCI_EVENT_PATCHES_BOOTLOAD_REQ,
+ tSLInformation.pucTxCommandBuffer, patch, ucLength);
+ return;
+ }
+ }
+
+ // Send 0 length Patches response event
+ hci_patch_send(HCI_EVENT_PATCHES_BOOTLOAD_REQ,
+ tSLInformation.pucTxCommandBuffer, 0, 0);
+ break;
+ }
+}
+
+
+
+//*****************************************************************************
+//
+//! hci_event_handler
+//!
+//! @param pRetParams incoming data buffer
+//! @param from from information (in case of data received)
+//! @param fromlen from information length (in case of data received)
+//!
+//! @return none
+//!
+//! @brief Parse the incoming events packets and issues corresponding
+//! event handler from global array of handlers pointers
+//
+//*****************************************************************************
+
+
+uint8_t *
+hci_event_handler(void *pRetParams, uint8_t *from, uint8_t *fromlen)
+{
+ uint8_t *pucReceivedData, ucArgsize;
+ uint16_t usLength;
+ uint8_t *pucReceivedParams;
+ uint16_t usReceivedEventOpcode = 0;
+ unsigned long retValue32;
+ uint8_t * RecvParams;
+ uint8_t *RetParams;
+
+
+ while (1)
+ {
+ if (tSLInformation.usEventOrDataReceived != 0)
+ {
+ pucReceivedData = (tSLInformation.pucReceivedData);
+
+ if (*pucReceivedData == HCI_TYPE_EVNT)
+ {
+ // Event Received
+ STREAM_TO_UINT16((char *)pucReceivedData, HCI_EVENT_OPCODE_OFFSET,
+ usReceivedEventOpcode);
+ pucReceivedParams = pucReceivedData + HCI_EVENT_HEADER_SIZE;
+ RecvParams = pucReceivedParams;
+ RetParams = (uint8_t *)pRetParams;
+
+ // In case unsolicited event received - here the handling finished
+ if (hci_unsol_event_handler((char *)pucReceivedData) == 0)
+ {
+ STREAM_TO_UINT8(pucReceivedData, HCI_DATA_LENGTH_OFFSET, usLength);
+
+ switch(usReceivedEventOpcode)
+ {
+ case HCI_CMND_READ_BUFFER_SIZE:
+ {
+ STREAM_TO_UINT8((char *)pucReceivedParams, 0,
+ tSLInformation.usNumberOfFreeBuffers);
+ STREAM_TO_UINT16((char *)pucReceivedParams, 1,
+ tSLInformation.usSlBufferLength);
+ }
+ break;
+
+ case HCI_CMND_WLAN_CONFIGURE_PATCH:
+ case HCI_NETAPP_DHCP:
+ case HCI_NETAPP_PING_SEND:
+ case HCI_NETAPP_PING_STOP:
+ case HCI_NETAPP_ARP_FLUSH:
+ case HCI_NETAPP_SET_DEBUG_LEVEL:
+ case HCI_NETAPP_SET_TIMERS:
+ case HCI_EVNT_NVMEM_READ:
+ case HCI_EVNT_NVMEM_CREATE_ENTRY:
+ case HCI_CMND_NVMEM_WRITE_PATCH:
+ case HCI_NETAPP_PING_REPORT:
+ case HCI_EVNT_MDNS_ADVERTISE:
+
+ STREAM_TO_UINT8(pucReceivedData, HCI_EVENT_STATUS_OFFSET
+ ,*(uint8_t *)pRetParams);
+ break;
+
+ case HCI_CMND_SETSOCKOPT:
+ case HCI_CMND_WLAN_CONNECT:
+ case HCI_CMND_WLAN_IOCTL_STATUSGET:
+ case HCI_EVNT_WLAN_IOCTL_ADD_PROFILE:
+ case HCI_CMND_WLAN_IOCTL_DEL_PROFILE:
+ case HCI_CMND_WLAN_IOCTL_SET_CONNECTION_POLICY:
+ case HCI_CMND_WLAN_IOCTL_SET_SCANPARAM:
+ case HCI_CMND_WLAN_IOCTL_SIMPLE_CONFIG_START:
+ case HCI_CMND_WLAN_IOCTL_SIMPLE_CONFIG_STOP:
+ case HCI_CMND_WLAN_IOCTL_SIMPLE_CONFIG_SET_PREFIX:
+ case HCI_CMND_EVENT_MASK:
+ case HCI_EVNT_WLAN_DISCONNECT:
+ case HCI_EVNT_SOCKET:
+ case HCI_EVNT_BIND:
+ case HCI_CMND_LISTEN:
+ case HCI_EVNT_CLOSE_SOCKET:
+ case HCI_EVNT_CONNECT:
+ case HCI_EVNT_NVMEM_WRITE:
+
+ STREAM_TO_UINT32((char *)pucReceivedParams,0
+ ,*(unsigned long *)pRetParams);
+ break;
+
+ case HCI_EVNT_READ_SP_VERSION:
+
+ STREAM_TO_UINT8(pucReceivedData, HCI_EVENT_STATUS_OFFSET
+ ,*(uint8_t *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 1;
+ STREAM_TO_UINT32((char *)pucReceivedParams, 0, retValue32);
+ UINT32_TO_STREAM((uint8_t *)pRetParams, retValue32);
+ break;
+
+ case HCI_EVNT_BSD_GETHOSTBYNAME:
+
+ STREAM_TO_UINT32((char *)pucReceivedParams
+ ,GET_HOST_BY_NAME_RETVAL_OFFSET,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 4;
+ STREAM_TO_UINT32((char *)pucReceivedParams
+ ,GET_HOST_BY_NAME_ADDR_OFFSET,*(unsigned long *)pRetParams);
+ break;
+
+ case HCI_EVNT_ACCEPT:
+ {
+ STREAM_TO_UINT32((char *)pucReceivedParams,ACCEPT_SD_OFFSET
+ ,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 4;
+ STREAM_TO_UINT32((char *)pucReceivedParams
+ ,ACCEPT_RETURN_STATUS_OFFSET,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 4;
+
+ //This argument returns in network order
+ memcpy((uint8_t *)pRetParams,
+ pucReceivedParams + ACCEPT_ADDRESS__OFFSET, sizeof(sockaddr));
+ break;
+ }
+
+ case HCI_EVNT_RECV:
+ case HCI_EVNT_RECVFROM:
+ {
+ STREAM_TO_UINT32((char *)pucReceivedParams,SL_RECEIVE_SD_OFFSET ,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 4;
+ STREAM_TO_UINT32((char *)pucReceivedParams,SL_RECEIVE_NUM_BYTES_OFFSET,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 4;
+ STREAM_TO_UINT32((char *)pucReceivedParams,SL_RECEIVE__FLAGS__OFFSET,*(unsigned long *)pRetParams);
+
+ if(((tBsdReadReturnParams *)pRetParams)->iNumberOfBytes == ERROR_SOCKET_INACTIVE)
+ {
+ set_socket_active_status(((tBsdReadReturnParams *)pRetParams)->iSocketDescriptor,SOCKET_STATUS_INACTIVE);
+ }
+ break;
+ }
+
+ case HCI_EVNT_SEND:
+ case HCI_EVNT_SENDTO:
+ {
+ STREAM_TO_UINT32((char *)pucReceivedParams,SL_RECEIVE_SD_OFFSET ,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 4;
+ STREAM_TO_UINT32((char *)pucReceivedParams,SL_RECEIVE_NUM_BYTES_OFFSET,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 4;
+
+ break;
+ }
+
+ case HCI_EVNT_SELECT:
+ {
+ STREAM_TO_UINT32((char *)pucReceivedParams,SELECT_STATUS_OFFSET,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 4;
+ STREAM_TO_UINT32((char *)pucReceivedParams,SELECT_READFD_OFFSET,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 4;
+ STREAM_TO_UINT32((char *)pucReceivedParams,SELECT_WRITEFD_OFFSET,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 4;
+ STREAM_TO_UINT32((char *)pucReceivedParams,SELECT_EXFD_OFFSET,*(unsigned long *)pRetParams);
+ break;
+ }
+
+ case HCI_CMND_GETSOCKOPT:
+
+ STREAM_TO_UINT8(pucReceivedData, HCI_EVENT_STATUS_OFFSET,((tBsdGetSockOptReturnParams *)pRetParams)->iStatus);
+ //This argument returns in network order
+ memcpy((uint8_t *)pRetParams, pucReceivedParams, 4);
+ break;
+
+ case HCI_CMND_WLAN_IOCTL_GET_SCAN_RESULTS:
+
+ STREAM_TO_UINT32((char *)pucReceivedParams,GET_SCAN_RESULTS_TABlE_COUNT_OFFSET,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 4;
+ STREAM_TO_UINT32((char *)pucReceivedParams,GET_SCAN_RESULTS_SCANRESULT_STATUS_OFFSET,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 4;
+ STREAM_TO_UINT16((char *)pucReceivedParams,GET_SCAN_RESULTS_ISVALID_TO_SSIDLEN_OFFSET,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 2;
+ STREAM_TO_UINT16((char *)pucReceivedParams,GET_SCAN_RESULTS_FRAME_TIME_OFFSET,*(unsigned long *)pRetParams);
+ pRetParams = ((char *)pRetParams) + 2;
+ memcpy((uint8_t *)pRetParams,
+ (char *)(pucReceivedParams + GET_SCAN_RESULTS_FRAME_TIME_OFFSET + 2),
+ GET_SCAN_RESULTS_SSID_MAC_LENGTH);
+ break;
+
+ case HCI_CMND_SIMPLE_LINK_START:
+ break;
+
+ case HCI_NETAPP_IPCONFIG:
+
+ //Read IP address
+ STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_IP_LENGTH);
+ RecvParams += 4;
+
+ //Read subnet
+ STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_IP_LENGTH);
+ RecvParams += 4;
+
+ //Read default GW
+ STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_IP_LENGTH);
+ RecvParams += 4;
+
+ //Read DHCP server
+ STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_IP_LENGTH);
+ RecvParams += 4;
+
+ //Read DNS server
+ STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_IP_LENGTH);
+ RecvParams += 4;
+
+ //Read Mac address
+ STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_MAC_LENGTH);
+ RecvParams += 6;
+
+ //Read SSID
+ STREAM_TO_STREAM(RecvParams,RetParams,NETAPP_IPCONFIG_SSID_LENGTH);
+
+ }
+ }
+
+ if (usReceivedEventOpcode == tSLInformation.usRxEventOpcode)
+ {
+ tSLInformation.usRxEventOpcode = 0;
+ }
+ }
+ else
+ {
+ pucReceivedParams = pucReceivedData;
+ STREAM_TO_UINT8((char *)pucReceivedData, HCI_PACKET_ARGSIZE_OFFSET, ucArgsize);
+
+ STREAM_TO_UINT16((char *)pucReceivedData, HCI_PACKET_LENGTH_OFFSET, usLength);
+
+ // Data received: note that the only case where from and from length
+ // are not null is in recv from, so fill the args accordingly
+ if (from)
+ {
+ STREAM_TO_UINT32((char *)(pucReceivedData + HCI_DATA_HEADER_SIZE), BSD_RECV_FROM_FROMLEN_OFFSET, *(unsigned long *)fromlen);
+ memcpy(from, (pucReceivedData + HCI_DATA_HEADER_SIZE + BSD_RECV_FROM_FROM_OFFSET) ,*fromlen);
+ }
+
+ memcpy(pRetParams, pucReceivedParams + HCI_DATA_HEADER_SIZE + ucArgsize,
+ usLength - ucArgsize);
+
+ tSLInformation.usRxDataPending = 0;
+ }
+
+ tSLInformation.usEventOrDataReceived = 0;
+
+ SpiResumeSpi();
+
+ // Since we are going to TX - we need to handle this event after the
+ // ResumeSPi since we need interrupts
+ if ((*pucReceivedData == HCI_TYPE_EVNT) &&
+ (usReceivedEventOpcode == HCI_EVNT_PATCHES_REQ))
+ {
+ hci_unsol_handle_patch_request((char *)pucReceivedData);
+ }
+
+ if ((tSLInformation.usRxEventOpcode == 0) && (tSLInformation.usRxDataPending == 0))
+ {
+ return NULL;
+ }
+ }
+ }
+
+}
+
+//*****************************************************************************
+//
+//! hci_unsol_event_handler
+//!
+//! @param event_hdr event header
+//!
+//! @return 1 if event supported and handled
+//! 0 if event is not supported
+//!
+//! @brief Handle unsolicited events
+//
+//*****************************************************************************
+long
+hci_unsol_event_handler(char *event_hdr)
+{
+ char * data = NULL;
+ long event_type;
+ unsigned long NumberOfReleasedPackets;
+ unsigned long NumberOfSentPackets;
+
+ STREAM_TO_UINT16(event_hdr, HCI_EVENT_OPCODE_OFFSET,event_type);
+
+ if (event_type & HCI_EVNT_UNSOL_BASE)
+ {
+ switch(event_type)
+ {
+
+ case HCI_EVNT_DATA_UNSOL_FREE_BUFF:
+ {
+ hci_event_unsol_flowcontrol_handler(event_hdr);
+
+ NumberOfReleasedPackets = tSLInformation.NumberOfReleasedPackets;
+ NumberOfSentPackets = tSLInformation.NumberOfSentPackets;
+
+ if (NumberOfReleasedPackets == NumberOfSentPackets)
+ {
+ if (tSLInformation.InformHostOnTxComplete)
+ {
+ tSLInformation.sWlanCB(HCI_EVENT_CC3000_CAN_SHUT_DOWN, NULL, 0);
+ }
+ }
+ return 1;
+
+ }
+ }
+ }
+
+ if(event_type & HCI_EVNT_WLAN_UNSOL_BASE)
+ {
+ switch(event_type)
+ {
+ case HCI_EVNT_WLAN_KEEPALIVE:
+ case HCI_EVNT_WLAN_UNSOL_CONNECT:
+ case HCI_EVNT_WLAN_UNSOL_DISCONNECT:
+ case HCI_EVNT_WLAN_UNSOL_INIT:
+ case HCI_EVNT_WLAN_ASYNC_SIMPLE_CONFIG_DONE:
+
+ if( tSLInformation.sWlanCB )
+ {
+ tSLInformation.sWlanCB(event_type, 0, 0);
+ }
+ break;
+
+ case HCI_EVNT_WLAN_UNSOL_DHCP:
+ {
+ uint8_t params[NETAPP_IPCONFIG_MAC_OFFSET + 1]; // extra byte is for the status
+ uint8_t *recParams = params;
+
+ data = (char*)(event_hdr) + HCI_EVENT_HEADER_SIZE;
+
+ //Read IP address
+ STREAM_TO_STREAM(data,recParams,NETAPP_IPCONFIG_IP_LENGTH);
+ data += 4;
+ //Read subnet
+ STREAM_TO_STREAM(data,recParams,NETAPP_IPCONFIG_IP_LENGTH);
+ data += 4;
+ //Read default GW
+ STREAM_TO_STREAM(data,recParams,NETAPP_IPCONFIG_IP_LENGTH);
+ data += 4;
+ //Read DHCP server
+ STREAM_TO_STREAM(data,recParams,NETAPP_IPCONFIG_IP_LENGTH);
+ data += 4;
+ //Read DNS server
+ STREAM_TO_STREAM(data,recParams,NETAPP_IPCONFIG_IP_LENGTH);
+ // read the status
+ STREAM_TO_UINT8(event_hdr, HCI_EVENT_STATUS_OFFSET, *recParams);
+
+
+ if( tSLInformation.sWlanCB )
+ {
+ tSLInformation.sWlanCB(event_type, (char *)params, sizeof(params));
+ }
+ }
+ break;
+
+ case HCI_EVNT_WLAN_ASYNC_PING_REPORT:
+ {
+ netapp_pingreport_args_t params;
+ data = (char*)(event_hdr) + HCI_EVENT_HEADER_SIZE;
+ STREAM_TO_UINT32(data, NETAPP_PING_PACKETS_SENT_OFFSET, params.packets_sent);
+ STREAM_TO_UINT32(data, NETAPP_PING_PACKETS_RCVD_OFFSET, params.packets_received);
+ STREAM_TO_UINT32(data, NETAPP_PING_MIN_RTT_OFFSET, params.min_round_time);
+ STREAM_TO_UINT32(data, NETAPP_PING_MAX_RTT_OFFSET, params.max_round_time);
+ STREAM_TO_UINT32(data, NETAPP_PING_AVG_RTT_OFFSET, params.avg_round_time);
+
+ if( tSLInformation.sWlanCB )
+ {
+ tSLInformation.sWlanCB(event_type, (char *)&params, sizeof(params));
+ }
+ }
+ break;
+ case HCI_EVNT_BSD_TCP_CLOSE_WAIT:
+ {
+ if( tSLInformation.sWlanCB )
+ {
+ tSLInformation.sWlanCB(event_type, NULL, 0);
+ }
+ }
+ break;
+
+ //'default' case which means "event not supported"
+ default:
+ return (0);
+ }
+ return(1);
+ }
+
+ if ((event_type == HCI_EVNT_SEND) || (event_type == HCI_EVNT_SENDTO)
+ || (event_type == HCI_EVNT_WRITE))
+ {
+ char *pArg;
+ long status;
+
+ pArg = M_BSD_RESP_PARAMS_OFFSET(event_hdr);
+ STREAM_TO_UINT32(pArg, BSD_RSP_PARAMS_STATUS_OFFSET,status);
+
+ if (ERROR_SOCKET_INACTIVE == status)
+ {
+ // The only synchronous event that can come from SL device in form of
+ // command complete is "Command Complete" on data sent, in case SL device
+ // was unable to transmit
+ STREAM_TO_UINT8(event_hdr, HCI_EVENT_STATUS_OFFSET, tSLInformation.slTransmitDataError);
+ update_socket_active_status(M_BSD_RESP_PARAMS_OFFSET(event_hdr));
+
+ return (1);
+ }
+ else
+ return (0);
+ }
+
+ return(0);
+}
+
+//*****************************************************************************
+//
+//! hci_unsolicited_event_handler
+//!
+//! @param None
+//!
+//! @return ESUCCESS if successful, EFAIL if an error occurred
+//!
+//! @brief Parse the incoming unsolicited event packets and issues
+//! corresponding event handler.
+//
+//*****************************************************************************
+long
+hci_unsolicited_event_handler(void)
+{
+ unsigned long res = 0;
+ uint8_t *pucReceivedData;
+
+ if (tSLInformation.usEventOrDataReceived != 0)
+ {
+ pucReceivedData = (tSLInformation.pucReceivedData);
+
+ if (*pucReceivedData == HCI_TYPE_EVNT)
+ {
+
+ // In case unsolicited event received - here the handling finished
+ if (hci_unsol_event_handler((char *)pucReceivedData) == 1)
+ {
+
+ // There was an unsolicited event received - we can release the buffer
+ // and clean the event received
+ tSLInformation.usEventOrDataReceived = 0;
+
+ res = 1;
+ SpiResumeSpi();
+ }
+ }
+ }
+
+ return res;
+}
+
+//*****************************************************************************
+//
+//! set_socket_active_status
+//!
+//! @param Sd
+//! @param Status
+//! @return none
+//!
+//! @brief Check if the socket ID and status are valid and set
+//! accordingly the global socket status
+//
+//*****************************************************************************
+void set_socket_active_status(long Sd, long Status)
+{
+ if(M_IS_VALID_SD(Sd) && M_IS_VALID_STATUS(Status))
+ {
+ socket_active_status &= ~(1 << Sd); /* clean socket's mask */
+ socket_active_status |= (Status << Sd); /* set new socket's mask */
+ }
+}
+
+
+//*****************************************************************************
+//
+//! hci_event_unsol_flowcontrol_handler
+//!
+//! @param pEvent pointer to the string contains parameters for IPERF
+//! @return ESUCCESS if successful, EFAIL if an error occurred
+//!
+//! @brief Called in case unsolicited event from type
+//! HCI_EVNT_DATA_UNSOL_FREE_BUFF has received.
+//! Keep track on the number of packets transmitted and update the
+//! number of free buffer in the SL device.
+//
+//*****************************************************************************
+long
+hci_event_unsol_flowcontrol_handler(char *pEvent)
+{
+
+ long temp, value;
+ uint16_t i;
+ uint16_t pusNumberOfHandles=0;
+ char *pReadPayload;
+
+ STREAM_TO_UINT16((char *)pEvent,HCI_EVENT_HEADER_SIZE,pusNumberOfHandles);
+ pReadPayload = ((char *)pEvent +
+ HCI_EVENT_HEADER_SIZE + sizeof(pusNumberOfHandles));
+ temp = 0;
+
+ for(i = 0; i < pusNumberOfHandles ; i++)
+ {
+ STREAM_TO_UINT16(pReadPayload, FLOW_CONTROL_EVENT_FREE_BUFFS_OFFSET, value);
+ temp += value;
+ pReadPayload += FLOW_CONTROL_EVENT_SIZE;
+ }
+
+ tSLInformation.usNumberOfFreeBuffers += temp;
+ tSLInformation.NumberOfReleasedPackets += temp;
+
+ return(ESUCCESS);
+}
+
+//*****************************************************************************
+//
+//! get_socket_active_status
+//!
+//! @param Sd Socket IS
+//! @return Current status of the socket.
+//!
+//! @brief Retrieve socket status
+//
+//*****************************************************************************
+
+long
+get_socket_active_status(long Sd)
+{
+ if(M_IS_VALID_SD(Sd))
+ {
+ return (socket_active_status & (1 << Sd)) ? SOCKET_STATUS_INACTIVE : SOCKET_STATUS_ACTIVE;
+ }
+ return SOCKET_STATUS_INACTIVE;
+}
+
+//*****************************************************************************
+//
+//! update_socket_active_status
+//!
+//! @param resp_params Socket IS
+//! @return Current status of the socket.
+//!
+//! @brief Retrieve socket status
+//
+//*****************************************************************************
+void
+update_socket_active_status(char *resp_params)
+{
+ long status, sd;
+
+ STREAM_TO_UINT32(resp_params, BSD_RSP_PARAMS_SOCKET_OFFSET,sd);
+ STREAM_TO_UINT32(resp_params, BSD_RSP_PARAMS_STATUS_OFFSET,status);
+
+ if(ERROR_SOCKET_INACTIVE == status)
+ {
+ set_socket_active_status(sd, SOCKET_STATUS_INACTIVE);
+ }
+}
+
+
+//*****************************************************************************
+//
+//! SimpleLinkWaitEvent
+//!
+//! @param usOpcode command operation code
+//! @param pRetParams command return parameters
+//!
+//! @return none
+//!
+//! @brief Wait for event, pass it to the hci_event_handler and
+//! update the event opcode in a global variable.
+//
+//*****************************************************************************
+
+void
+SimpleLinkWaitEvent(uint16_t usOpcode, void *pRetParams)
+{
+ // In the blocking implementation the control to caller will be returned only
+ // after the end of current transaction
+ tSLInformation.usRxEventOpcode = usOpcode;
+ hci_event_handler(pRetParams, 0, 0);
+}
+
+//*****************************************************************************
+//
+//! SimpleLinkWaitData
+//!
+//! @param pBuf data buffer
+//! @param from from information
+//! @param fromlen from information length
+//!
+//! @return none
+//!
+//! @brief Wait for data, pass it to the hci_event_handler
+//! and update in a global variable that there is
+//! data to read.
+//
+//*****************************************************************************
+
+void
+SimpleLinkWaitData(uint8_t *pBuf, uint8_t *from,
+ uint8_t *fromlen)
+{
+ // In the blocking implementation the control to caller will be returned only
+ // after the end of current transaction, i.e. only after data will be received
+ tSLInformation.usRxDataPending = 1;
+ hci_event_handler(pBuf, from, fromlen);
+}
+
+//*****************************************************************************
+//
+// Close the Doxygen group.
+//! @}
+//
+//*****************************************************************************