David Fletcher / Mbed 2 deprecated cc3100_test

Dependencies:   mbed

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers cc3100_socket.cpp Source File

cc3100_socket.cpp

00001 /*
00002  * socket.c - CC31xx/CC32xx Host Driver Implementation
00003  *
00004  * Copyright (C) 2014 Texas Instruments Incorporated - http://www.ti.com/ 
00005  * 
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 
00040 /*****************************************************************************/
00041 /* Include files                                                             */
00042 /*****************************************************************************/
00043 #include "cc3100_simplelink.h"
00044 #include "cc3100_protocol.h"
00045 #include "cc3100_driver.h"
00046 
00047 
00048 /*******************************************************************************/
00049 /* Functions prototypes                                                        */
00050 /*******************************************************************************/
00051 void   _sl_BuildAddress(const SlSockAddr_t *addr, _i16 addrlen, _SocketAddrCommand_u    *pCmd);
00052 void   _sl_ParseAddress(_SocketAddrResponse_u *pRsp, SlSockAddr_t *addr, SlSocklen_t *addrlen);
00053 void   _sl_HandleAsync_Connect(void *pVoidBuf);
00054 void   _sl_HandleAsync_Accept(void *pVoidBuf);
00055 void   _sl_HandleAsync_Select(void *pVoidBuf);
00056 _u16   _sl_TruncatePayloadByProtocol(const _i16 pSd,const _u16 length);  
00057 
00058 /*******************************************************************************/
00059 /* Functions                                                                   */
00060 /*******************************************************************************/
00061 
00062 /* ******************************************************************************/
00063 /*  _sl_BuildAddress */
00064 /* ******************************************************************************/
00065 void _sl_BuildAddress(const SlSockAddr_t *addr, _i16 addrlen, _SocketAddrCommand_u    *pCmd)
00066 {
00067 
00068     /*  Note: parsing of family and port in the generic way for all IPV4, IPV6 and EUI48 */
00069     /*  is possible as _i32 as these parameters are in the same offset and size for these */
00070     /*  three families. */
00071     pCmd->IpV4.FamilyAndFlags = (addr->sa_family << 4) & 0xF0;
00072     pCmd->IpV4.port = ((SlSockAddrIn_t *)addr)->sin_port;
00073 
00074     if(SL_AF_INET == addr->sa_family)
00075     {
00076         pCmd->IpV4.address  = ((SlSockAddrIn_t *)addr)->sin_addr.s_addr;
00077     }
00078     else if (SL_AF_INET6_EUI_48 == addr->sa_family )
00079     {
00080         sl_Memcpy( pCmd->IpV6EUI48.address,((SlSockAddrIn6_t *)addr)->sin6_addr._S6_un._S6_u8, 6);
00081     }
00082 #ifdef SL_SUPPORT_IPV6
00083     else
00084     {
00085         sl_Memcpy(pCmd->IpV6.address, ((sockaddr_in6 *)addr)->sin6_addr._S6_un._S6_u32, 16 );
00086     }
00087 #endif
00088 }
00089 
00090 /* ******************************************************************************/
00091 /*  _sl_TruncatePayloadByProtocol */
00092 /* ******************************************************************************/
00093 _u16 _sl_TruncatePayloadByProtocol(const _i16 sd,const _u16 length)
00094 {
00095    _u16 maxLength; 
00096    
00097    switch(sd & SL_SOCKET_PAYLOAD_TYPE_MASK)
00098    {
00099       case SL_SOCKET_PAYLOAD_TYPE_UDP_IPV4:
00100          maxLength = 1472;
00101       break;
00102       
00103       case SL_SOCKET_PAYLOAD_TYPE_TCP_IPV4:
00104          maxLength = 1460;
00105       break;
00106       
00107       case SL_SOCKET_PAYLOAD_TYPE_UDP_IPV6:
00108          maxLength = 1452;
00109       break;
00110       
00111       case SL_SOCKET_PAYLOAD_TYPE_TCP_IPV6:
00112           maxLength = 1440;
00113       break;
00114       case SL_SOCKET_PAYLOAD_TYPE_TCP_IPV4_SECURE:
00115       case SL_SOCKET_PAYLOAD_TYPE_UDP_IPV4_SECURE:
00116           maxLength = 1402;
00117       break;
00118       case SL_SOCKET_PAYLOAD_TYPE_UDP_IPV6_SECURE:
00119       case SL_SOCKET_PAYLOAD_TYPE_TCP_IPV6_SECURE:
00120          maxLength = 1396;
00121       break;
00122       case SL_SOCKET_PAYLOAD_TYPE_RAW_TRANCEIVER:
00123            maxLength = 1476;
00124       break;
00125      case SL_SOCKET_PAYLOAD_TYPE_RAW_PACKET:
00126            maxLength = 1514;
00127       break;
00128      case SL_SOCKET_PAYLOAD_TYPE_RAW_IP4:
00129            maxLength = 1480;
00130       break;
00131       default:
00132            maxLength = 1440;
00133       break;
00134    }
00135    
00136    if( length > maxLength )
00137    {
00138       return maxLength;
00139    }
00140    else
00141    {
00142       return length;
00143    }
00144 }
00145 
00146 /*******************************************************************************/
00147 /*  _sl_ParseAddress */
00148 /*******************************************************************************/
00149 void _sl_ParseAddress(_SocketAddrResponse_u    *pRsp, SlSockAddr_t *addr, SlSocklen_t *addrlen)
00150 {
00151     /*  Note: parsing of family and port in the generic way for all IPV4, IPV6 and EUI48 */
00152     /*  is possible as long as these parameters are in the same offset and size for these */
00153     /*  three families. */
00154     addr->sa_family                 = pRsp->IpV4.family;
00155     ((SlSockAddrIn_t *)addr)->sin_port = pRsp->IpV4.port;
00156 
00157     *addrlen = (SL_AF_INET == addr->sa_family) ? sizeof(SlSockAddrIn_t) : sizeof(SlSockAddrIn6_t);
00158 
00159     if(SL_AF_INET == addr->sa_family)
00160     {
00161         ((SlSockAddrIn_t *)addr)->sin_addr.s_addr  = pRsp->IpV4.address;
00162     }
00163     else if (SL_AF_INET6_EUI_48 == addr->sa_family )
00164     {
00165         sl_Memcpy(((SlSockAddrIn6_t *)addr)->sin6_addr._S6_un._S6_u8, pRsp->IpV6EUI48.address, 6);
00166     }
00167 #ifdef SL_SUPPORT_IPV6
00168     else
00169     {
00170         sl_Memcpy(((sockaddr_in6 *)addr)->sin6_addr._S6_un._S6_u32, pRsp->IpV6.address, 16);
00171     }
00172 #endif
00173 }
00174 
00175 /*******************************************************************************/
00176 /* sl_Socket */
00177 /*******************************************************************************/
00178 typedef union
00179 {
00180     _u32                Dummy;
00181     _SocketCommand_t    Cmd;
00182     _SocketResponse_t   Rsp;
00183 }_SlSockSocketMsg_u;
00184 
00185 const _SlCmdCtrl_t _SlSockSocketCmdCtrl =
00186 {
00187     SL_OPCODE_SOCKET_SOCKET,
00188     sizeof(_SocketCommand_t),
00189     sizeof(_SocketResponse_t)
00190 };
00191 
00192 #if _SL_INCLUDE_FUNC(sl_Socket)
00193 _i16 sl_Socket(_i16 Domain, _i16 Type, _i16 Protocol)
00194 {
00195     _SlSockSocketMsg_u  Msg;
00196 
00197     Msg.Cmd.Domain      = (_u8)Domain;
00198     Msg.Cmd.Type        = (_u8)Type;
00199     Msg.Cmd.Protocol    = (_u8)Protocol;
00200 
00201     VERIFY_RET_OK(_SlDrvCmdOp((_SlCmdCtrl_t *)&_SlSockSocketCmdCtrl, &Msg, NULL));
00202 
00203     if( Msg.Rsp.statusOrLen < 0 )
00204     {
00205         return( Msg.Rsp.statusOrLen );
00206     }
00207     else
00208     {
00209     return (_i16)((_u8)Msg.Rsp.sd);
00210 }
00211 }
00212 #endif
00213 
00214 /*******************************************************************************/
00215 /*  sl_Close  */
00216 /*******************************************************************************/
00217 typedef union
00218 {
00219     _CloseCommand_t     Cmd;
00220     _SocketResponse_t   Rsp;
00221 }_SlSockCloseMsg_u;
00222 
00223 const _SlCmdCtrl_t _SlSockCloseCmdCtrl =
00224 {
00225     SL_OPCODE_SOCKET_CLOSE,
00226     sizeof(_CloseCommand_t),
00227     sizeof(_SocketResponse_t)
00228 };
00229 
00230 #if _SL_INCLUDE_FUNC(sl_Close)
00231 _i16 sl_Close(_i16 sd)
00232 {
00233     _SlSockCloseMsg_u   Msg;
00234 
00235     Msg.Cmd.sd = (_u8)sd;
00236 
00237     VERIFY_RET_OK(_SlDrvCmdOp((_SlCmdCtrl_t *)&_SlSockCloseCmdCtrl, &Msg, NULL));
00238 
00239     return Msg.Rsp.statusOrLen;
00240 }
00241 #endif
00242 
00243 /*******************************************************************************/
00244 /*  sl_Bind */
00245 /*******************************************************************************/
00246 typedef union
00247 {
00248     _SocketAddrCommand_u    Cmd;
00249     _SocketResponse_t       Rsp;
00250 }_SlSockBindMsg_u;
00251 
00252 #if _SL_INCLUDE_FUNC(sl_Bind)
00253 _i16 sl_Bind(_i16 sd, const SlSockAddr_t *addr, _i16 addrlen)
00254 {
00255     _SlSockBindMsg_u    Msg;
00256     _SlCmdCtrl_t         CmdCtrl = {0, 0, sizeof(_SocketResponse_t)};
00257 
00258     switch(addr->sa_family)
00259     {
00260         case SL_AF_INET :
00261             CmdCtrl.Opcode = SL_OPCODE_SOCKET_BIND;
00262             CmdCtrl.TxDescLen = sizeof(_SocketAddrIPv4Command_t);
00263             break;
00264         case SL_AF_INET6_EUI_48:
00265             CmdCtrl.Opcode = SL_OPCODE_SOCKET_BIND_V6;
00266             CmdCtrl.TxDescLen = sizeof(_SocketAddrIPv6EUI48Command_t);
00267             break;
00268 #ifdef SL_SUPPORT_IPV6
00269         case AF_INET6:
00270             CmdCtrl.Opcode = SL_OPCODE_SOCKET_BIND_V6;
00271             CmdCtrl.TxDescLen = sizeof(_SocketAddrIPv6Command_t);
00272             break;
00273 #endif
00274         case SL_AF_RF   :
00275         default:
00276             return SL_RET_CODE_INVALID_INPUT;
00277     }
00278 
00279     Msg.Cmd.IpV4.lenOrPadding = 0;
00280     Msg.Cmd.IpV4.sd = (_u8)sd;
00281 
00282     _sl_BuildAddress(addr, addrlen, &Msg.Cmd);
00283 
00284     VERIFY_RET_OK(_SlDrvCmdOp((_SlCmdCtrl_t *)&CmdCtrl, &Msg, NULL));
00285 
00286     return Msg.Rsp.statusOrLen;
00287 }
00288 #endif
00289 
00290 /*******************************************************************************/
00291 /*  sl_Sendto */
00292 /*******************************************************************************/
00293 typedef union
00294 {
00295     _SocketAddrCommand_u    Cmd;
00296     /*  no response for 'sendto' commands*/
00297 }_SlSendtoMsg_u;
00298 
00299 #if _SL_INCLUDE_FUNC(sl_SendTo)
00300 _i16 sl_SendTo(_i16 sd, const void *pBuf, _i16 Len, _i16 flags, const SlSockAddr_t *to, SlSocklen_t tolen)
00301 {
00302     _SlSendtoMsg_u   Msg;
00303     _SlCmdCtrl_t     CmdCtrl = {0, 0, 0};
00304     _SlCmdExt_t      CmdExt;
00305     _u16           ChunkLen;
00306     _i16              RetVal;
00307 
00308     CmdExt.TxPayloadLen = (_u16)Len;
00309     CmdExt.RxPayloadLen = 0;
00310     CmdExt.pTxPayload = (_u8 *)pBuf;
00311     CmdExt.pRxPayload = NULL;
00312 
00313 
00314     switch(to->sa_family)
00315     {
00316         case SL_AF_INET:
00317             CmdCtrl.Opcode = SL_OPCODE_SOCKET_SENDTO;
00318             CmdCtrl.TxDescLen = sizeof(_SocketAddrIPv4Command_t);
00319             break;
00320         case SL_AF_INET6_EUI_48:
00321             CmdCtrl.Opcode = SL_OPCODE_SOCKET_BIND_V6;
00322             CmdCtrl.TxDescLen = sizeof(_SocketAddrIPv6EUI48Command_t);
00323             break;
00324 #ifdef SL_SUPPORT_IPV6
00325         case AF_INET6:
00326             CmdCtrl.Opcode = SL_OPCODE_SOCKET_SENDTO_V6;
00327             CmdCtrl.TxDescLen = sizeof(_SocketAddrIPv6Command_t);
00328             break;
00329 #endif
00330         case SL_AF_RF:
00331         default:
00332             return SL_RET_CODE_INVALID_INPUT;
00333     }
00334 
00335     ChunkLen = _sl_TruncatePayloadByProtocol(sd,Len);
00336     Msg.Cmd.IpV4.lenOrPadding = ChunkLen;
00337     CmdExt.TxPayloadLen = ChunkLen;
00338 
00339     Msg.Cmd.IpV4.sd = (_u8)sd;
00340 
00341     _sl_BuildAddress(to, tolen, &Msg.Cmd);
00342 
00343     Msg.Cmd.IpV4.FamilyAndFlags |= flags & 0x0F;
00344 
00345     do
00346     {
00347         RetVal = _SlDrvDataWriteOp((_SlSd_t)sd, &CmdCtrl, &Msg, &CmdExt);
00348 
00349         if(SL_OS_RET_CODE_OK == RetVal)
00350         {
00351             CmdExt.pTxPayload += ChunkLen;
00352             ChunkLen = (_u16)((_u8 *)pBuf + Len - CmdExt.pTxPayload);
00353             ChunkLen = _sl_TruncatePayloadByProtocol(sd,ChunkLen);
00354             CmdExt.TxPayloadLen = ChunkLen;
00355             Msg.Cmd.IpV4.lenOrPadding = ChunkLen;
00356         }
00357         else
00358         {
00359             return RetVal;
00360         }
00361     }while(ChunkLen > 0);
00362 
00363     return (_i16)Len;
00364 }
00365 #endif
00366 
00367 /*******************************************************************************/
00368 /*  sl_Recvfrom */
00369 /*******************************************************************************/
00370 typedef union
00371 {
00372     _sendRecvCommand_t      Cmd;
00373     _SocketAddrResponse_u   Rsp;
00374 }_SlRecvfromMsg_u;
00375 
00376 const _SlCmdCtrl_t _SlRecvfomCmdCtrl =
00377 {
00378     SL_OPCODE_SOCKET_RECVFROM,
00379     sizeof(_sendRecvCommand_t),
00380     sizeof(_SocketAddrResponse_u)
00381 };
00382 
00383 #if _SL_INCLUDE_FUNC(sl_RecvFrom)
00384 _i16 sl_RecvFrom(_i16 sd, void *buf, _i16 Len, _i16 flags, SlSockAddr_t *from, SlSocklen_t *fromlen)
00385 {
00386     _SlRecvfromMsg_u    Msg;
00387     _SlCmdExt_t         CmdExt;
00388     _i16                 RetVal;
00389 
00390     CmdExt.TxPayloadLen = 0;
00391     CmdExt.RxPayloadLen = Len;
00392     CmdExt.pTxPayload = NULL;
00393     CmdExt.pRxPayload = (_u8 *)buf;
00394 
00395 
00396     Msg.Cmd.sd = (_u8)sd;
00397     Msg.Cmd.StatusOrLen = Len;
00398     /*  no size truncation in recv path */
00399     CmdExt.RxPayloadLen = Msg.Cmd.StatusOrLen;
00400 
00401     if(sizeof(SlSockAddrIn_t) == *fromlen)
00402     {
00403         Msg.Cmd.FamilyAndFlags = SL_AF_INET;
00404     }
00405     else if (sizeof(SlSockAddrIn6_t) == *fromlen)
00406     {
00407         Msg.Cmd.FamilyAndFlags = SL_AF_INET6;
00408     }
00409     else
00410     {
00411         return SL_RET_CODE_INVALID_INPUT;
00412     }
00413 
00414     Msg.Cmd.FamilyAndFlags = (Msg.Cmd.FamilyAndFlags << 4) & 0xF0;
00415     Msg.Cmd.FamilyAndFlags |= flags & 0x0F;
00416 
00417     RetVal = _SlDrvDataReadOp((_SlSd_t)sd, (_SlCmdCtrl_t *)&_SlRecvfomCmdCtrl, &Msg, &CmdExt);
00418     if( RetVal != SL_OS_RET_CODE_OK )
00419     {
00420     return RetVal;
00421     }
00422 
00423     RetVal = Msg.Rsp.IpV4.statusOrLen;
00424 
00425     if(RetVal >= 0)
00426     {
00427         VERIFY_PROTOCOL(sd == Msg.Rsp.IpV4.sd);
00428 #if 0
00429         _sl_ParseAddress(&Msg.Rsp, from, fromlen);
00430 #else
00431         from->sa_family = Msg.Rsp.IpV4.family;
00432         if(SL_AF_INET == from->sa_family)
00433         {
00434             ((SlSockAddrIn_t *)from)->sin_port = Msg.Rsp.IpV4.port;
00435             ((SlSockAddrIn_t *)from)->sin_addr.s_addr = Msg.Rsp.IpV4.address;
00436             *fromlen = sizeof(SlSockAddrIn_t);
00437         }
00438         else if (SL_AF_INET6_EUI_48 == from->sa_family )
00439          {
00440             ((SlSockAddrIn6_t *)from)->sin6_port  = Msg.Rsp.IpV6EUI48.port;
00441             sl_Memcpy(((SlSockAddrIn6_t *)from)->sin6_addr._S6_un._S6_u8, Msg.Rsp.IpV6EUI48.address, 6);
00442          }
00443 #ifdef SL_SUPPORT_IPV6
00444         else if(AF_INET6 == from->sa_family)
00445         {
00446             VERIFY_PROTOCOL(*fromlen >= sizeof(sockaddr_in6));
00447 
00448             ((sockaddr_in6 *)from)->sin6_port = Msg.Rsp.IpV6.port;
00449             sl_Memcpy(((sockaddr_in6 *)from)->sin6_addr._S6_un._S6_u32, Msg.Rsp.IpV6.address, 16);
00450             *fromlen = sizeof(sockaddr_in6);
00451         }
00452 #endif
00453 #endif
00454     }
00455 
00456     return (_i16)RetVal;
00457 }
00458 #endif
00459 
00460 /*******************************************************************************/
00461 /*  sl_Connect */
00462 /*******************************************************************************/
00463 typedef union
00464 {
00465     _SocketAddrCommand_u    Cmd;
00466     _SocketResponse_t       Rsp;
00467 }_SlSockConnectMsg_u;
00468 
00469 #if _SL_INCLUDE_FUNC(sl_Connect)
00470 _i16 sl_Connect(_i16 sd, const SlSockAddr_t *addr, _i16 addrlen)
00471 {
00472     _SlSockConnectMsg_u  Msg;
00473     _SlReturnVal_t       RetVal;
00474     _SlCmdCtrl_t         CmdCtrl = {0, 0, sizeof(_SocketResponse_t)};
00475     _SocketResponse_t    AsyncRsp;
00476     _u8 ObjIdx = MAX_CONCURRENT_ACTIONS;
00477 
00478 
00479     switch(addr->sa_family)
00480     {
00481         case SL_AF_INET :
00482             CmdCtrl.Opcode = SL_OPCODE_SOCKET_CONNECT;
00483             CmdCtrl.TxDescLen = sizeof(_SocketAddrIPv4Command_t);
00484             break;
00485         case  SL_AF_INET6_EUI_48:
00486             CmdCtrl.Opcode = SL_OPCODE_SOCKET_CONNECT_V6;
00487             CmdCtrl.TxDescLen = sizeof(_SocketAddrIPv6EUI48Command_t);
00488             break;
00489 #ifdef SL_SUPPORT_IPV6
00490         case AF_INET6:
00491             CmdCtrl.Opcode = SL_OPCODE_SOCKET_CONNECT_V6;
00492             CmdCtrl.TxDescLen = sizeof(_SocketAddrIPv6Command_t);
00493             break;
00494 #endif
00495         case SL_AF_RF   :
00496         default:
00497             return SL_RET_CODE_INVALID_INPUT;
00498     }
00499 
00500     Msg.Cmd.IpV4.lenOrPadding = 0;
00501     Msg.Cmd.IpV4.sd = (_u8)sd;
00502 
00503     _sl_BuildAddress(addr, addrlen, &Msg.Cmd);
00504 
00505     /* Use Obj to issue the command, if not available try later */
00506     ObjIdx = (_u8)_SlDrvWaitForPoolObj(CONNECT_ID, (_u8)(sd  & BSD_SOCKET_ID_MASK));
00507 
00508     if (MAX_CONCURRENT_ACTIONS == ObjIdx)
00509     {
00510         return SL_POOL_IS_EMPTY;
00511     }
00512     OSI_RET_OK_CHECK(sl_LockObjLock(&g_pCB->ProtectionLockObj, SL_OS_WAIT_FOREVER));
00513 
00514     g_pCB->ObjPool[ObjIdx].pRespArgs =  (_u8 *)&AsyncRsp;
00515 
00516     OSI_RET_OK_CHECK(sl_LockObjUnlock(&g_pCB->ProtectionLockObj));
00517     
00518     /* send the command */
00519     VERIFY_RET_OK(_SlDrvCmdOp((_SlCmdCtrl_t *)&CmdCtrl, &Msg, NULL));
00520     VERIFY_PROTOCOL(Msg.Rsp.sd == sd)
00521 
00522     RetVal = Msg.Rsp.statusOrLen;
00523 
00524     if(SL_RET_CODE_OK == RetVal)
00525     {
00526         /*  wait for async and get Data Read parameters */
00527         OSI_RET_OK_CHECK(sl_SyncObjWait(&g_pCB->ObjPool[ObjIdx].SyncObj, SL_OS_WAIT_FOREVER));
00528 
00529         VERIFY_PROTOCOL(AsyncRsp.sd == sd);
00530 
00531         RetVal = AsyncRsp.statusOrLen;
00532     }
00533     _SlDrvReleasePoolObj(ObjIdx);
00534     return RetVal;
00535 }
00536 #endif
00537 
00538 /*******************************************************************************/
00539 /*   _sl_HandleAsync_Connect */
00540 /*******************************************************************************/
00541 void _sl_HandleAsync_Connect(void *pVoidBuf)
00542 {
00543     _SocketResponse_t          *pMsgArgs   = (_SocketResponse_t *)_SL_RESP_ARGS_START(pVoidBuf);
00544 
00545     OSI_RET_OK_CHECK(sl_LockObjLock(&g_pCB->ProtectionLockObj, SL_OS_WAIT_FOREVER));
00546 
00547     VERIFY_PROTOCOL((pMsgArgs->sd & BSD_SOCKET_ID_MASK) <= SL_MAX_SOCKETS);
00548     VERIFY_SOCKET_CB(NULL != g_pCB->ObjPool[g_pCB->FunctionParams.AsyncExt.ActionIndex].pRespArgs);
00549 
00550     ((_SocketResponse_t *)(g_pCB->ObjPool[g_pCB->FunctionParams.AsyncExt.ActionIndex].pRespArgs))->sd = pMsgArgs->sd;
00551     ((_SocketResponse_t *)(g_pCB->ObjPool[g_pCB->FunctionParams.AsyncExt.ActionIndex].pRespArgs))->statusOrLen = pMsgArgs->statusOrLen;
00552 
00553     OSI_RET_OK_CHECK(sl_SyncObjSignal(&g_pCB->ObjPool[g_pCB->FunctionParams.AsyncExt.ActionIndex].SyncObj));
00554     OSI_RET_OK_CHECK(sl_LockObjUnlock(&g_pCB->ProtectionLockObj));
00555     return;
00556 }
00557 
00558 /*******************************************************************************/
00559 /*  sl_Send */
00560 /*******************************************************************************/
00561 typedef union
00562 {
00563     _sendRecvCommand_t    Cmd;
00564     /*  no response for 'sendto' commands*/
00565 }_SlSendMsg_u;
00566 
00567 const _SlCmdCtrl_t _SlSendCmdCtrl =
00568 {
00569     SL_OPCODE_SOCKET_SEND,
00570     sizeof(_sendRecvCommand_t),
00571     0
00572 };
00573 
00574 #if _SL_INCLUDE_FUNC(sl_Send)
00575 _i16 sl_Send(_i16 sd, const void *pBuf, _i16 Len, _i16 flags)
00576 {
00577     _SlSendMsg_u   Msg;
00578     _SlCmdExt_t    CmdExt;
00579     _u16         ChunkLen;
00580     _i16            RetVal;
00581     _u32         tempVal;
00582     _u8  runSingleChunk = FALSE; 
00583 
00584     CmdExt.TxPayloadLen = Len;
00585     CmdExt.RxPayloadLen = 0;
00586     CmdExt.pTxPayload = (_u8 *)pBuf;
00587 
00588     /* Only for RAW transceiver type socket, relay the flags parameter in the 2 bytes (4 byte aligned) before the actual payload */
00589     if ((sd & SL_SOCKET_PAYLOAD_TYPE_MASK) == SL_SOCKET_PAYLOAD_TYPE_RAW_TRANCEIVER)
00590     {
00591         tempVal = flags;
00592         CmdExt.pRxPayload = (_u8 *)&tempVal;
00593         CmdExt.RxPayloadLen = 4;
00594         g_pCB->RelayFlagsViaRxPayload = TRUE;
00595         runSingleChunk = TRUE;
00596     }
00597     else
00598     {
00599         CmdExt.pRxPayload = NULL;
00600     }
00601 
00602     ChunkLen = _sl_TruncatePayloadByProtocol(sd,Len);
00603     CmdExt.TxPayloadLen = ChunkLen;
00604 
00605     Msg.Cmd.StatusOrLen = ChunkLen;
00606     Msg.Cmd.sd = (_u8)sd;
00607     Msg.Cmd.FamilyAndFlags |= flags & 0x0F;
00608 
00609     do
00610     {
00611         RetVal = _SlDrvDataWriteOp((_u8)sd, (_SlCmdCtrl_t *)&_SlSendCmdCtrl, &Msg, &CmdExt);
00612         if(SL_OS_RET_CODE_OK == RetVal)
00613         {
00614             CmdExt.pTxPayload += ChunkLen;
00615             ChunkLen = (_u8 *)pBuf + Len - CmdExt.pTxPayload;
00616             ChunkLen = _sl_TruncatePayloadByProtocol(sd,ChunkLen);
00617             CmdExt.TxPayloadLen = ChunkLen;
00618             Msg.Cmd.StatusOrLen = ChunkLen;
00619         }
00620         else
00621         {
00622             return RetVal;
00623         }
00624     }while((ChunkLen > 0) && (runSingleChunk==FALSE));
00625     
00626     return (_i16)Len;
00627 }
00628 #endif
00629 
00630 /*******************************************************************************/
00631 /*  sl_Listen */
00632 /*******************************************************************************/
00633 typedef union
00634 {
00635     _ListenCommand_t    Cmd;
00636     _BasicResponse_t    Rsp;
00637 }_SlListenMsg_u;
00638 
00639 const _SlCmdCtrl_t _SlListenCmdCtrl =
00640 {
00641     SL_OPCODE_SOCKET_LISTEN,
00642     sizeof(_ListenCommand_t),
00643     sizeof(_BasicResponse_t),
00644 };
00645 
00646 #if _SL_INCLUDE_FUNC(sl_Listen)
00647 _i16 sl_Listen(_i16 sd, _i16 backlog)
00648 {
00649     _SlListenMsg_u  Msg;
00650 
00651     Msg.Cmd.sd = (_u8)sd;
00652     Msg.Cmd.backlog = (_u8)backlog;
00653 
00654     VERIFY_RET_OK(_SlDrvCmdOp((_SlCmdCtrl_t *)&_SlListenCmdCtrl, &Msg, NULL));
00655 
00656     return (_i16)Msg.Rsp.status;
00657 }
00658 #endif
00659 
00660 /*******************************************************************************/
00661 /*  sl_Accept */
00662 /*******************************************************************************/
00663 typedef union
00664 {
00665     _AcceptCommand_t    Cmd;
00666     _SocketResponse_t   Rsp;
00667 }_SlSockAcceptMsg_u;
00668 
00669 const _SlCmdCtrl_t _SlAcceptCmdCtrl =
00670 {
00671     SL_OPCODE_SOCKET_ACCEPT,
00672     sizeof(_AcceptCommand_t),
00673     sizeof(_BasicResponse_t),
00674 };
00675 
00676 #if _SL_INCLUDE_FUNC(sl_Accept)
00677 _i16 sl_Accept(_i16 sd, SlSockAddr_t *addr, SlSocklen_t *addrlen)
00678 {
00679     _SlSockAcceptMsg_u      Msg;
00680     _SlReturnVal_t          RetVal;
00681     _SocketAddrResponse_u   AsyncRsp;
00682 
00683     _u8 ObjIdx = MAX_CONCURRENT_ACTIONS;
00684 
00685 
00686     Msg.Cmd.sd = (_u8)sd;
00687     Msg.Cmd.family = (sizeof(SlSockAddrIn_t) == *addrlen) ? SL_AF_INET : SL_AF_INET6;
00688 
00689     /* Use Obj to issue the command, if not available try later */
00690     ObjIdx = (_u8)_SlDrvWaitForPoolObj(ACCEPT_ID, (_u8)(sd  & BSD_SOCKET_ID_MASK));
00691     
00692     if (MAX_CONCURRENT_ACTIONS == ObjIdx)
00693     {
00694         return SL_POOL_IS_EMPTY;
00695     }
00696     
00697     OSI_RET_OK_CHECK(sl_LockObjLock(&g_pCB->ProtectionLockObj, SL_OS_WAIT_FOREVER));
00698 
00699     g_pCB->ObjPool[ObjIdx].pRespArgs = (_u8 *)&AsyncRsp;
00700 
00701     OSI_RET_OK_CHECK(sl_LockObjUnlock(&g_pCB->ProtectionLockObj));
00702     /* send the command */
00703     VERIFY_RET_OK(_SlDrvCmdOp((_SlCmdCtrl_t *)&_SlAcceptCmdCtrl, &Msg, NULL));
00704     VERIFY_PROTOCOL(Msg.Rsp.sd == sd);
00705 
00706     RetVal = Msg.Rsp.statusOrLen;
00707 
00708     if(SL_OS_RET_CODE_OK == RetVal)
00709     {
00710         /*  wait for async and get Data Read parameters */
00711         OSI_RET_OK_CHECK(sl_SyncObjWait(&g_pCB->ObjPool[ObjIdx].SyncObj, SL_OS_WAIT_FOREVER));
00712 
00713         VERIFY_PROTOCOL(AsyncRsp.IpV4.sd == sd);
00714 
00715         RetVal = AsyncRsp.IpV4.statusOrLen;
00716         if( (NULL != addr) && (NULL != addrlen) )  
00717         {
00718 #if 0 /*  Kept for backup */
00719             _sl_ParseAddress(&AsyncRsp, addr, addrlen);
00720 #else
00721            addr->sa_family = AsyncRsp.IpV4.family;
00722 
00723             if(SL_AF_INET == addr->sa_family)
00724             {
00725               if( *addrlen == sizeof( SlSockAddrIn_t ) )
00726               {
00727                 ((SlSockAddrIn_t *)addr)->sin_port         = AsyncRsp.IpV4.port;
00728                 ((SlSockAddrIn_t *)addr)->sin_addr.s_addr  = AsyncRsp.IpV4.address;
00729               }
00730               else
00731               {
00732                 *addrlen = 0;
00733               }
00734             }
00735             else if (SL_AF_INET6_EUI_48 == addr->sa_family )
00736             {
00737                 if( *addrlen == sizeof( SlSockAddrIn6_t ) )
00738               {
00739                 ((SlSockAddrIn6_t *)addr)->sin6_port                   = AsyncRsp.IpV6EUI48.port    ;
00740                 /*  will be called from here and from _sl_BuildAddress*/
00741                 sl_Memcpy(((SlSockAddrIn6_t *)addr)->sin6_addr._S6_un._S6_u8, AsyncRsp.IpV6EUI48.address, 6);
00742               }
00743               else
00744               {
00745                 *addrlen = 0;
00746               }
00747             }
00748 #ifdef SL_SUPPORT_IPV6
00749             else
00750             {
00751               if( *addrlen == sizeof( sockaddr_in6 ) )
00752               {
00753                 ((sockaddr_in6 *)addr)->sin6_port                   = AsyncRsp.IpV6.port    ;
00754                 sl_Memcpy(((sockaddr_in6 *)addr)->sin6_addr._S6_un._S6_u32, AsyncRsp.IpV6.address, 16);
00755               }
00756               else
00757               {
00758                 *addrlen = 0;
00759               }
00760             }
00761 #endif
00762 #endif          
00763         }
00764     }
00765 
00766     _SlDrvReleasePoolObj(ObjIdx);
00767     return (_i16)RetVal;
00768 }
00769 #endif
00770 
00771 
00772 /*******************************************************************************/
00773 /*  sl_Htonl */
00774 /*******************************************************************************/
00775 _u32 sl_Htonl( _u32 val )
00776 {
00777   _u32 i = 1; 
00778   _i8 *p = (_i8 *)&i;  
00779   if (p[0] == 1) /* little endian */
00780   {
00781     p[0] = ((_i8* )&val)[3];
00782     p[1] = ((_i8* )&val)[2];
00783     p[2] = ((_i8* )&val)[1];
00784     p[3] = ((_i8* )&val)[0];
00785     return i;
00786   }
00787   else /* big endian */
00788   {
00789     return val; 
00790   }
00791 }
00792 
00793 /*******************************************************************************/
00794 /*  sl_Htonl */
00795 /*******************************************************************************/
00796 _u16 sl_Htons( _u16 val )
00797 {
00798   _i16 i = 1; 
00799   _i8 *p = (_i8 *)&i;  
00800   if (p[0] == 1) /* little endian */
00801   {
00802     p[0] = ((_i8* )&val)[1];
00803     p[1] = ((_i8* )&val)[0];
00804     return i;
00805   }
00806   else /* big endian */
00807   {
00808     return val; 
00809   }
00810 }
00811 
00812 /*******************************************************************************/
00813 /*   _sl_HandleAsync_Accept */
00814 /*******************************************************************************/
00815 void _sl_HandleAsync_Accept(void *pVoidBuf)
00816 {
00817     _SocketAddrResponse_u      *pMsgArgs   = (_SocketAddrResponse_u *)_SL_RESP_ARGS_START(pVoidBuf);
00818 
00819     OSI_RET_OK_CHECK(sl_LockObjLock(&g_pCB->ProtectionLockObj, SL_OS_WAIT_FOREVER));
00820 
00821     VERIFY_PROTOCOL(( pMsgArgs->IpV4.sd & BSD_SOCKET_ID_MASK) <= SL_MAX_SOCKETS);
00822     VERIFY_SOCKET_CB(NULL != g_pCB->ObjPool[g_pCB->FunctionParams.AsyncExt.ActionIndex].pRespArgs);
00823 
00824     sl_Memcpy(g_pCB->ObjPool[g_pCB->FunctionParams.AsyncExt.ActionIndex].pRespArgs, pMsgArgs,sizeof(_SocketAddrResponse_u));
00825     OSI_RET_OK_CHECK(sl_SyncObjSignal(&g_pCB->ObjPool[g_pCB->FunctionParams.AsyncExt.ActionIndex].SyncObj));
00826 
00827     OSI_RET_OK_CHECK(sl_LockObjUnlock(&g_pCB->ProtectionLockObj));
00828     return;
00829 }
00830 
00831 /*******************************************************************************/
00832 /*  sl_Recv */
00833 /*******************************************************************************/
00834 typedef union
00835 {
00836     _sendRecvCommand_t  Cmd;
00837     _SocketResponse_t   Rsp;    
00838 }_SlRecvMsg_u;
00839 
00840 const _SlCmdCtrl_t _SlRecvCmdCtrl =
00841 {
00842     SL_OPCODE_SOCKET_RECV,
00843     sizeof(_sendRecvCommand_t),
00844     sizeof(_SocketResponse_t)
00845 };
00846 
00847 #if _SL_INCLUDE_FUNC(sl_Recv)
00848 _i16 sl_Recv(_i16 sd, void *pBuf, _i16 Len, _i16 flags)
00849 {
00850     _SlRecvMsg_u    Msg;
00851     _SlCmdExt_t     CmdExt;
00852     _SlReturnVal_t status;
00853 
00854     CmdExt.TxPayloadLen = 0;
00855     CmdExt.RxPayloadLen = Len;
00856     CmdExt.pTxPayload = NULL;
00857     CmdExt.pRxPayload = (_u8 *)pBuf;
00858 
00859     Msg.Cmd.sd = (_u8)sd;
00860     Msg.Cmd.StatusOrLen = Len;
00861 
00862     /*  no size truncation in recv path */
00863     CmdExt.RxPayloadLen = Msg.Cmd.StatusOrLen;
00864 
00865     Msg.Cmd.FamilyAndFlags = flags & 0x0F;
00866 
00867     status = _SlDrvDataReadOp((_SlSd_t)sd, (_SlCmdCtrl_t *)&_SlRecvCmdCtrl, &Msg, &CmdExt);
00868     if( status != SL_OS_RET_CODE_OK )
00869     {
00870     return status;
00871     }
00872      
00873     /*  if the Device side sends less than expected it is not the Driver's role */
00874     /*  the returned value could be smaller than the requested size */
00875     return (_i16)Msg.Rsp.statusOrLen;
00876 }
00877 #endif
00878 
00879 /*******************************************************************************/
00880 /*  sl_SetSockOpt */
00881 /*******************************************************************************/
00882 typedef union
00883 {
00884     _setSockOptCommand_t    Cmd;
00885     _SocketResponse_t       Rsp;    
00886 }_SlSetSockOptMsg_u;
00887 
00888 const _SlCmdCtrl_t _SlSetSockOptCmdCtrl =
00889 {
00890     SL_OPCODE_SOCKET_SETSOCKOPT,
00891     sizeof(_setSockOptCommand_t),
00892     sizeof(_SocketResponse_t)
00893 };
00894 
00895 #if _SL_INCLUDE_FUNC(sl_SetSockOpt)
00896 _i16 sl_SetSockOpt(_i16 sd, _i16 level, _i16 optname, const void *optval, SlSocklen_t optlen)
00897 {
00898     _SlSetSockOptMsg_u    Msg;
00899     _SlCmdExt_t           CmdExt;
00900 
00901     CmdExt.TxPayloadLen = optlen;
00902     CmdExt.RxPayloadLen = 0;
00903     CmdExt.pTxPayload = (_u8 *)optval;
00904     CmdExt.pRxPayload = NULL;
00905 
00906     Msg.Cmd.sd = (_u8)sd;
00907     Msg.Cmd.level = (_u8)level;
00908     Msg.Cmd.optionLen = (_u8)optlen;
00909     Msg.Cmd.optionName = (_u8)optname;
00910 
00911     VERIFY_RET_OK(_SlDrvCmdOp((_SlCmdCtrl_t *)&_SlSetSockOptCmdCtrl, &Msg, &CmdExt));
00912 
00913     return (_i16)Msg.Rsp.statusOrLen;
00914 }
00915 #endif
00916 
00917 /*******************************************************************************/
00918 /*  sl_GetSockOpt */
00919 /*******************************************************************************/
00920 typedef union
00921 {
00922     _getSockOptCommand_t    Cmd;
00923     _getSockOptResponse_t   Rsp;    
00924 }_SlGetSockOptMsg_u;
00925 
00926 const _SlCmdCtrl_t _SlGetSockOptCmdCtrl =
00927 {
00928     SL_OPCODE_SOCKET_GETSOCKOPT,
00929     sizeof(_getSockOptCommand_t),
00930     sizeof(_getSockOptResponse_t)
00931 };
00932 
00933 #if _SL_INCLUDE_FUNC(sl_GetSockOpt)
00934 _i16 sl_GetSockOpt(_i16 sd, _i16 level, _i16 optname, void *optval, SlSocklen_t *optlen)
00935 {
00936     _SlGetSockOptMsg_u    Msg;
00937     _SlCmdExt_t           CmdExt;
00938 
00939     if (*optlen == 0)
00940     {
00941         return SL_EZEROLEN;
00942     }
00943     CmdExt.TxPayloadLen = 0;
00944     CmdExt.RxPayloadLen = *optlen;
00945     CmdExt.pTxPayload = NULL;
00946     CmdExt.pRxPayload = (unsigned char*)optval;//(unsigned char*) added
00947     CmdExt.ActualRxPayloadLen = 0;
00948 
00949     Msg.Cmd.sd = (_u8)sd;
00950     Msg.Cmd.level = (_u8)level;
00951     Msg.Cmd.optionLen = (_u8)(*optlen);
00952     Msg.Cmd.optionName = (_u8)optname;
00953 
00954     VERIFY_RET_OK(_SlDrvCmdOp((_SlCmdCtrl_t *)&_SlGetSockOptCmdCtrl, &Msg, &CmdExt));
00955 
00956     if (CmdExt.RxPayloadLen < CmdExt.ActualRxPayloadLen) 
00957     {
00958         *optlen = Msg.Rsp.optionLen;
00959        return SL_ESMALLBUF;
00960     }
00961     else
00962     {
00963         *optlen = (_u8)CmdExt.ActualRxPayloadLen;
00964     }
00965     return (_i16)Msg.Rsp.status;
00966 }
00967 #endif
00968 
00969 /*******************************************************************************/
00970 /*  sl_Select */
00971 /* ******************************************************************************/
00972 typedef union
00973 {
00974     _SelectCommand_t   Cmd;
00975     _BasicResponse_t   Rsp;    
00976 }_SlSelectMsg_u;
00977 
00978 const _SlCmdCtrl_t _SlSelectCmdCtrl =
00979 {
00980     SL_OPCODE_SOCKET_SELECT,
00981     sizeof(_SelectCommand_t),
00982     sizeof(_BasicResponse_t)
00983 };
00984 
00985 #if _SL_INCLUDE_FUNC(sl_Select)
00986 _i16 sl_Select(_i16 nfds, SlFdSet_t *readsds, SlFdSet_t *writesds, SlFdSet_t *exceptsds, struct SlTimeval_t *timeout)
00987 {
00988     _SlSelectMsg_u          Msg;
00989     _SelectAsyncResponse_t  AsyncRsp;
00990     _u8 ObjIdx = MAX_CONCURRENT_ACTIONS;
00991 
00992     Msg.Cmd.nfds          = (_u8)nfds;
00993     Msg.Cmd.readFdsCount  = 0;
00994     Msg.Cmd.writeFdsCount = 0;
00995     
00996     Msg.Cmd.readFds = 0;
00997     Msg.Cmd.writeFds = 0; 
00998     
00999     if( readsds )
01000     {
01001        Msg.Cmd.readFds       = (_u16)readsds->fd_array[0];  
01002     }
01003     if( writesds )
01004     {
01005        Msg.Cmd.writeFds      = (_u16)writesds->fd_array[0]; 
01006     }
01007     if( NULL == timeout )
01008     {
01009         Msg.Cmd.tv_sec = 0xffff;
01010         Msg.Cmd.tv_usec = 0xffff;
01011     }
01012     else
01013     {
01014         if( 0xffff <= timeout->tv_sec ) 
01015         {
01016             Msg.Cmd.tv_sec = 0xffff;
01017         }
01018         else
01019         {
01020             Msg.Cmd.tv_sec = (_u16)timeout->tv_sec;
01021         }
01022         timeout->tv_usec = timeout->tv_usec >> 10;  /*  convert to milliseconds */
01023         if( 0xffff <= timeout->tv_usec )    
01024         {
01025             Msg.Cmd.tv_usec = 0xffff;
01026         }
01027         else
01028         {
01029             Msg.Cmd.tv_usec = (_u16)timeout->tv_usec;
01030         }
01031     }
01032 
01033     /* Use Obj to issue the command, if not available try later */
01034     ObjIdx = (_u8)_SlDrvWaitForPoolObj(SELECT_ID, SL_MAX_SOCKETS);
01035 
01036     if (MAX_CONCURRENT_ACTIONS == ObjIdx)
01037     {
01038         return SL_POOL_IS_EMPTY;
01039     }
01040     OSI_RET_OK_CHECK(sl_LockObjLock(&g_pCB->ProtectionLockObj, SL_OS_WAIT_FOREVER));
01041 
01042     g_pCB->ObjPool[ObjIdx].pRespArgs =  (_u8 *)&AsyncRsp;
01043 
01044     OSI_RET_OK_CHECK(sl_LockObjUnlock(&g_pCB->ProtectionLockObj));
01045     /* send the command */
01046     VERIFY_RET_OK(_SlDrvCmdOp((_SlCmdCtrl_t *)&_SlSelectCmdCtrl, &Msg, NULL));
01047 
01048     if(SL_OS_RET_CODE_OK == (_i16)Msg.Rsp.status)
01049     {
01050         OSI_RET_OK_CHECK(sl_SyncObjWait(&g_pCB->ObjPool[ObjIdx].SyncObj, SL_OS_WAIT_FOREVER));
01051         Msg.Rsp.status = AsyncRsp.status;
01052 
01053         if(  ((_i16)Msg.Rsp.status) >= 0 )
01054         {
01055             if( readsds )
01056             {
01057                readsds->fd_array[0]  = AsyncRsp.readFds;
01058             }
01059             if( writesds )
01060             {
01061                writesds->fd_array[0] = AsyncRsp.writeFds;      
01062             }
01063         }
01064     }
01065 
01066     _SlDrvReleasePoolObj(ObjIdx);
01067     return (_i16)Msg.Rsp.status;
01068 }
01069 
01070 /*  Select helper functions */
01071 /*******************************************************************************/
01072 /*  SL_FD_SET */
01073 /* ******************************************************************************/
01074 void SL_FD_SET(_i16 fd, SlFdSet_t *fdset)
01075 {
01076    fdset->fd_array[0] |=  (1<< (fd & BSD_SOCKET_ID_MASK));
01077 }
01078 /*******************************************************************************/
01079 /*  SL_FD_CLR */
01080 /*******************************************************************************/
01081 void SL_FD_CLR(_i16 fd, SlFdSet_t *fdset)
01082 {
01083   fdset->fd_array[0] &=  ~(1<< (fd & BSD_SOCKET_ID_MASK));
01084 }
01085 /*******************************************************************************/
01086 /*  SL_FD_ISSET */
01087 /*******************************************************************************/
01088 _i16  SL_FD_ISSET(_i16 fd, SlFdSet_t *fdset)
01089 {
01090   if( fdset->fd_array[0] & (1<< (fd & BSD_SOCKET_ID_MASK)) )
01091   {
01092     return 1;
01093   }
01094   return 0;
01095 }
01096 /*******************************************************************************/
01097 /*  SL_FD_ZERO */
01098 /*******************************************************************************/  
01099 void SL_FD_ZERO(SlFdSet_t *fdset)
01100 {
01101   fdset->fd_array[0] = 0;
01102 }
01103 
01104 #endif
01105 
01106 /*******************************************************************************/
01107 /*   _sl_HandleAsync_Select */
01108 /*******************************************************************************/
01109 void _sl_HandleAsync_Select(void *pVoidBuf)
01110 {
01111     _SelectAsyncResponse_t     *pMsgArgs   = (_SelectAsyncResponse_t *)_SL_RESP_ARGS_START(pVoidBuf);
01112 
01113     OSI_RET_OK_CHECK(sl_LockObjLock(&g_pCB->ProtectionLockObj, SL_OS_WAIT_FOREVER));
01114 
01115     VERIFY_SOCKET_CB(NULL != g_pCB->ObjPool[g_pCB->FunctionParams.AsyncExt.ActionIndex].pRespArgs);
01116 
01117     sl_Memcpy(g_pCB->ObjPool[g_pCB->FunctionParams.AsyncExt.ActionIndex].pRespArgs, pMsgArgs, sizeof(_SelectAsyncResponse_t));
01118     OSI_RET_OK_CHECK(sl_SyncObjSignal(&g_pCB->ObjPool[g_pCB->FunctionParams.AsyncExt.ActionIndex].SyncObj));
01119 
01120     OSI_RET_OK_CHECK(sl_LockObjUnlock(&g_pCB->ProtectionLockObj));
01121     return;
01122 }
01123 
01124