1 /*******************************************************************************
2 ################################################################################
3 # Copyright (c) [2017-2019] [Radisys] #
5 # Licensed under the Apache License, Version 2.0 (the "License"); #
6 # you may not use this file except in compliance with the License. #
7 # You may obtain a copy of the License at #
9 # http://www.apache.org/licenses/LICENSE-2.0 #
11 # Unless required by applicable law or agreed to in writing, software #
12 # distributed under the License is distributed on an "AS IS" BASIS, #
13 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. #
14 # See the License for the specific language governing permissions and #
15 # limitations under the License. #
16 ################################################################################
17 *******************************************************************************/
20 /********************************************************************20**
22 Name: common Internet socket library
26 Desc: common library for Internet sockets,
27 always link this library with following libraries:
33 *********************************************************************21*/
37 * This software may be combined with the following TRILLIUM
40 * part no. description
41 * -------- ----------------------------------------------
42 * 1000151 TCAP over TCP/IP
46 /* header include files (.h) */
48 #include "envopt.h" /* environment options */
49 #include "envdep.h" /* environment dependent */
50 #include "envind.h" /* environment independent */
52 #include "gen.h" /* general */
53 #include "ssi.h" /* system services interface */
54 #include "cm_inet.h" /* socket library file */
56 /*cm_inet_c_001.main_35 : Updated for C++ compilation */
59 #endif /* __cplusplus */
61 /* environment dependent include files */
73 #if (!defined(SS_VW) && !defined(SS_PS))
80 #include <sys/types.h>
84 #include <sys/socket.h>
85 #include <sys/ioctl.h>
88 #include <sys/times.h>
91 #include <selectLib.h>
94 #if (!defined (SS_PS) && !defined(HPOS))
95 #include <sys/select.h>
100 #include <sys/filio.h>
101 #endif /* SS_LINUX */
102 #endif /* SS_PS && HPOS */
104 #include <sys/time.h>
108 #include <netinet/in.h>
109 #include <arpa/inet.h>
110 #include <netinet/tcp.h>
111 #ifdef IPV6_SUPPORTED
113 /* cm_inet_c_001.main_54: Fix for vxworks 6.7 adding the new header includes */
114 #if (defined(SS_VW) && defined(SS_VW6_7))
115 #include <ipcom_inet.h>
116 #include <ipcom_sock6.h>
117 #include <netinet/icmp6.h>
119 #include <netinet/icmp6.h>
122 #endif /* IPV6_SUPPORTED */
126 /*cm_inet_c_001.main_38 Updated for TUCL 2.1 Release (Kernel SCTP Support) */
128 #include <netinet/sctp.h>
131 /* cm_inet_c_001.main_58: Added new header files to support filteration
132 * of ICMP messages */
134 #ifdef CM_ICMP_FILTER_SUPPORT
135 #include <asm/types.h>
136 #include <linux/icmp.h>
139 /* cm_inet_c_001.main_62:Warning fix */
140 #if (!defined(SS_VW) && !defined(SS_PS) && !defined(WIN32))
145 #endif /* __cplusplus */
146 /* header/extern include files (.x) */
148 #include "gen.x" /* general */
149 #include "ssi.x" /* system services interface */
150 #include "cm_inet.x" /* socket library file */
151 #include "cm_lib.x" /* lib library file */
159 /* BSD and Winsock error handling is different */
161 #define INET_ERR SOCKET_ERROR
162 #define INET_ERR_CODE WSAGetLastError()
163 #define ERR_INPROGRESS WSAEINPROGRESS
164 #define ERR_ISCONN WSAEISCONN
165 #define ERR_WOULDBLOCK WSAEWOULDBLOCK
166 #define ERR_INADDRNONE INADDR_NONE
167 #define ERR_NOTCONN WSAENOTCONN
168 #define ERR_ALREADY WSAEALREADY
169 #define ERR_AGAIN WSAEWOULDBLOCK
170 #define ERR_INVAL WSAEINVAL
171 #define ERR_CONNREFUSED WSAECONNREFUSED
172 #define ERR_PIPE WSAENOTCONN
173 /* Changed ERR_TIMEOUT for pSos compilation */
174 #define ERR_TIMEDOUT WSAETIMEDOUT
175 #define ERR_CONNRESET WSAECONNRESET
176 #define ERR_CONNABORTED WSAECONNABORTED
177 /* cm_inet_c_001.main_36 Do select again in case of interrupt */
178 #define ERR_EINTR WSAEINTR
179 /* cm_inet_c_001.main_37 network unreacheble error is added */
180 #define ERR_NETUNREACH WSAENETUNREACH
181 /* cm_inet_c_001.main_61: host unreachable is added */
182 #define ERR_HOSTUNREACH WSAEHOSTUNREACH
185 #define INET_ERR_CODE errno
186 #define ERR_INPROGRESS EINPROGRESS
187 #define ERR_ISCONN EISCONN
188 #define ERR_WOULDBLOCK EWOULDBLOCK
189 #define ERR_INADDRNONE -1
190 #define ERR_NOTCONN ENOTCONN
191 #define ERR_ALREADY EALREADY
192 #define ERR_AGAIN EAGAIN
193 /* cm_inet_c_001.main_36 Do select again in case of interrupt */
194 #define ERR_EINTR EINTR
195 /* EINVAL is not mapped because it is a valid error code here */
197 #define ERR_CONNREFUSED ECONNREFUSED
198 #define ERR_PIPE EPIPE
199 /* Changed ERR_TIMEOUT for pSos compilation */
200 #define ERR_TIMEDOUT ETIMEDOUT
201 #define ERR_CONNRESET ECONNRESET
202 #define ERR_CONNABORTED ECONNABORTED
203 /* cm_inet_c_001.main_37 network unreacheble error is added */
204 #define ERR_NETUNREACH ENETUNREACH
205 /* cm_inet_c_001.main_61: host unreachable is added */
206 #define ERR_HOSTUNREACH EHOSTUNREACH
210 #define MIN_BACK_LOG 0
212 /* added a win2k specific defines in. */
215 #ifndef SIO_UDP_CONNRESET
216 #define SIO_UDP_CONNRESET _WSAIOW(IOC_VENDOR, 12)
219 #define MAX_BACK_LOG 1
221 #define MAX_BACK_LOG 5
224 #ifdef IPV6_OPTS_SUPPORTED
225 #ifndef IPV6_SUPPORTED
226 #error "Enable IPV6_SUPPORTED flag if IPV6_OPTS_SUPPORTED is defined."
228 #if (!defined(SS_LINUX) && !defined(_XPG4_2))
229 #error "Enable _XPG4_2 or SS_LINUX if IPV6_OPTS_SUPPORTED is defined."
230 #endif /* SS_LINUX || _XPG4_2 */
231 #endif /* IPV6_OPTS_SUPPORTED */
234 #if (!defined(SS_LINUX) && !defined(_XPG4_2))
235 #error "Enable _XPG4_2 or SS_LINUX if LOCAL_INTF is defined."
236 #endif /* SS_LINUX || _XPG4_2 */
237 #endif /* LOCAL_INTF */
243 /* forward references */
245 /* added !(defined(CMINETFLATBUF) */
246 #if (!(defined(WIN32)) && !(defined(CMINETFLATBUF)))
247 /* Added another function parameter */
248 PRIVATE S16 buildRecvBuf ARGS((CmInetMemInfo *info, MsgLen len,
249 CmInetIovec rxArr[], Buffer *dBuf[], U16 maxSize,
250 struct msghdr *msg, Bool isStrmMsg));
251 PRIVATE S16 buildRecvMsg ARGS((CmInetMemInfo *info, CmInetIovec rxArr[],
252 S16 numBduf, MsgLen msgLen, Buffer *dBufs[],
254 /* cm_inet_c_001.main_50 - Added parameter to get length of dbufs packed for partial
257 PRIVATE S16 buildSendIovec ARGS((Buffer *mBuf, MsgLen msgLen,
258 CmInetIovec txArr[], S16 numDBuf,
259 S16 *numIovElems, U32 *strtEndDBufNum,
261 #endif /* (defined(WIN32)) && !(defined(CMINETFLATBUF)) */
263 /* prototypes of new functions needed to send and
264 * process after receiving the extension headers through ancillary data */
266 #ifdef IPV6_SUPPORTED
267 #ifdef IPV6_OPTS_SUPPORTED
268 PRIVATE S16 cmInet6BuildSendHBHOpts ARGS((CmInetIpv6HBHHdrArr *hbhOptsArr,
269 U8 *cmsgBuf, U32 *curMsgIdx,
271 PRIVATE S16 cmInet6BuildSendRouteOpts ARGS((CmInetIpv6RtHdr *rtOptsArr,
272 U8 *cmsgBuf, U32 *curMsgIdx));
274 PRIVATE S16 cmInet6BuildRecvRtHdr ARGS((U8 *cmsgData, U32 rtDataLen,
275 CmInetIpv6RtHdr0 *rtHdr0,
276 CmInetIpv6RtHdr *rtOptsArr,
277 CmInetMemInfo *info));
278 PRIVATE S16 cmInet6BuildRecvHopOptsArr ARGS((U8 *cmsgData, U32 hbhDataLen,
279 CmInetIpv6HBHHdrArr *hbhOptsArr,
280 U8 hdrId, CmInetMemInfo *info));
281 PRIVATE S16 cmInet6GetHopLimitValue ARGS((U8 *cmsgData, U32 hopLimitDataLen,
282 CmInetIpv6HdrParm *ipv6HdrParam));
285 PRIVATE S16 cmInetBuildSendHoplimit ARGS((U32 hoplimit, U8 *cmsgBuf,
287 #endif /* SS_LINUX */
289 PRIVATE S16 cmInet6BuildSendPktinfo ARGS((CmInetIpAddr6 *srcAddr,
290 U8 *cmsgBuf, U32 *curMsgIdx,
292 #endif /* LOCAL_INTF */
293 #endif /* IPV6_OPTS_SUPPORTED */
294 #endif /* IPV6_SUPPORTED */
296 /* public variable declarations */
298 /* private variable declarations */
301 /* Global buffer for debug prints */
302 /*cm_inet_c_001.main_62:Warning fix*/
303 Txt prntBuf[CMINET_PRNT_BUF_SIZE];
304 #endif /* CMINETDBG */
306 /* cm_inet_c_001.main_60 POLL Specific Functions defined */
312 * Desc: Poll on pollfdarr
314 * Ret: Number of File Descriptor Selected
323 PUBLIC S16 cmInetPoll
325 CmInetPollFd *pollFdArr, /* poll FD Array */
326 U32 numFds, /* Number of Fds to be monitored */
327 S16 *numRdyFds, /* number of ready descriptors */
328 U32 timeout /* timeout value for Poll */
331 PUBLIC S16 cmInetPoll(pollFdArr,numFds,numRdyFds,timeout)
332 CmInetPollFd *pollFdArr; /* poll FD Array */
333 U32 numFds; /* Number of Fds to be monitored */
334 S16 *numRdyFds; /* number of ready descriptors */
335 U32 timeout; /* timeout value for Poll */
344 if(numFds > CM_INET_POLL_MAXFDSUPP)
347 /* cm_inet_c_001.main_62:Warning fix */
349 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPoll() : number of file descriptor (%lu) invalid \n",numFds);
351 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPoll() : number of file descriptor (%u) invalid \n",numFds);
353 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
354 #endif /* CMINETDBG */
358 #if (ERRCLASS & ERRCLS_INT_PAR)
359 /* error check on parameters */
360 if (pollFdArr == NULLP)
363 /* cm_inet_c_001.main_62:Warning fix */
364 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPoll() : Invalid Parameter (pollFdArr is NULL)");
365 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
366 #endif /* CMINETDBG */
369 #endif /* ERRCLASS & ERRCLS_INT_PAR */
371 ret = poll(pollFdArr,numFds,timeout);
378 switch(INET_ERR_CODE)
385 /* cm_inet_c_001.main_62:Warning fix */
386 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "File: %s, cmInetPoll() failed on line: %d \n\
387 error(%d)\n", __FILE__, __LINE__, INET_ERR_CODE);
389 #endif /* CMINETDBG */
392 } /* end of switch */
395 *numRdyFds = (S16)ret;
403 * Fun: cmInetPollSetFd
405 * Desc: Set the selected fd in pollFdArr with event eventMask
407 * Ret: RFAILED : if file descriptor is out of range
408 * ROK : if pollFdArr is set.
417 PUBLIC S16 cmInetPollSetFd
419 CmInetFd *sockFd, /* socket file descriptor */
420 CmInetPollFd *pollFdArr, /* poll FD Array */
421 S16 idx, /* poll Fd Array Index */
422 U16 eventMask /* Event Mask to be set */
425 PUBLIC S16 cmInetPollSetFd(sockFd,pollFdArr,idx,eventMask)
426 CmInetFd *sockFd; /* socket file descriptor */
427 CmInetPollFd *pollFdArr; /* poll FD Array */
428 S16 idx; /* poll Fd Array Index */
429 U16 eventMask; /* Event Mask to be set */
433 TRC2(cmInetPollSetFd);
435 if ((idx) >= CM_INET_POLL_MAXFDSUPP || (idx) < 0)
438 /* cm_inet_c_001.main_62:Warning fix */
439 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollSetFd() : Invalid idx(%d) \n",idx);
440 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
441 #endif /* CMINETDBG */
446 #if (ERRCLASS & ERRCLS_INT_PAR)
447 /* error check on parameters */
448 if (pollFdArr == NULLP)
451 /* cm_inet_c_001.main_62:Warning fix */
452 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollSetFd() : Invalid Parameter (pollFdArr is NULL)");
453 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
454 #endif /* CMINETDBG */
457 #endif /* ERRCLASS & ERRCLS_INT_PAR */
461 /* cm_inet_c_001.main_62:Warning fix */
462 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,
463 "cmInetPollSetFd() Before Setting fd : sockFd->fd(%d) Index(%d) Event(%d) \n Fd and event to be set fd(%ld) event(%d) \n",
464 pollFdArr[idx].fd,idx, pollFdArr[idx].events,sockFd->fd,eventMask);
465 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
467 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,
468 "cmInetPollSetFd() Before Setting fd: sockFd->fd(%d) Index(%d) Event(%d) \n Fd and event to be set fd(%d) event(%d) \n",
469 pollFdArr[idx].fd,idx, pollFdArr[idx].events,sockFd->fd,eventMask);
470 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
471 #endif /*ALIGN_64BIT */
472 #endif /* CMINETDBG */
474 /* Setting fd and events with eventMask */
475 pollFdArr[idx].fd = sockFd->fd;
476 pollFdArr[idx].events |= eventMask;
481 /* cm_inet_c_001.main_62:Warning fix */
482 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollSetFd() After Setting fd: sockFd->fd(%d) Index(%d) Event(%d) \n",
483 pollFdArr[idx].fd,idx, pollFdArr[idx].events);
484 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
486 /* cm_inet_c_001.main_62:Warning fix */
487 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollSetFd() After Setting fd: sockFd->fd(%d) Index(%d) Event(%d) \n",
488 pollFdArr[idx].fd,idx, pollFdArr[idx].events);
489 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
490 #endif /*ALIGN_64BIT */
491 #endif /* CMINETDBG */
500 * Fun: cmInetPollFdIsSet
502 * Desc: Checks whether fd is selected
504 * Ret: TRUE : If Fd is Selected
505 * FALSE: If Fd is not Selected
514 PUBLIC S16 cmInetPollFdIsSet
516 CmInetPollFd *pollFdArr, /* poll FD Array */
517 S16 idx, /* poll Fd Array Index */
518 U16 eventMask /* Event Mask to be set */
521 PUBLIC S16 cmInetPollFdIsSet(pollFdArr,idx,eventMask)
522 CmInetPollFd *pollFdArr; /* poll FD Array */
523 S16 idx; /* poll Fd Array Index */
524 U16 eventMask; /* Event Mask to be set */
529 TRC2(cmInetPollFdIsSet);
531 if((idx < 0) || (idx > CM_INET_POLL_MAXFDSUPP))
534 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollFdIsSet() : Invalid Index (%d) \n",idx);
535 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
536 #endif /* CMINETDBG */
540 #if (ERRCLASS & ERRCLS_INT_PAR)
541 /* error check on parameters */
542 if (pollFdArr == NULLP)
545 /* cm_inet_c_001.main_62:Warning fix */
546 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollFdIsSet() : Invalid Parameter (pollFdArr is NULL)");
547 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
548 #endif /* CMINETDBG */
551 #endif /* ERRCLASS & ERRCLS_INT_PAR */
553 ret = (pollFdArr[idx].revents & eventMask);
560 * Fun: cmInetPollClearFdREvent
562 * Desc: clears the reventMask in revent of the givent FD.
574 PUBLIC S16 cmInetPollClearFdREvent
576 CmInetPollFd *pollFdArr, /* poll FD Array */
577 S16 idx, /* poll Fd Array Index */
578 U16 eventMask /* Event Mask to be set */
581 PUBLIC S16 cmInetPollClearFdREvent(sockFd,pollFdArr,eventMask)
582 CmInetPollFd *pollFdArr; /* poll FD Array */
583 S16 idx; /* poll Fd Array Index */
584 U16 eventMask; /* Event Mask to be set */
588 TRC2(cmInetPollClearFdREvent);
591 if((idx < 0) || (idx > CM_INET_POLL_MAXFDSUPP))
594 /* cm_inet_c_001.main_62:Warning fix */
595 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollClearFdREvent() : Invalid Index (%d) \n",idx);
596 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
597 #endif /* CMINETDBG */
601 #if (ERRCLASS & ERRCLS_INT_PAR)
602 /* error check on parameters */
603 if (pollFdArr == NULLP)
606 /* cm_inet_c_001.main_62:Warning fix */
607 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollClearFdREvent() : Invalid Parameter (pollFdArr is NULL)");
608 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
609 #endif /* CMINETDBG */
612 #endif /* ERRCLASS & ERRCLS_INT_PAR */
616 /* cm_inet_c_001.main_62:Warning fix */
617 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollClearFdREvent() Before clearing fd revents with eventMask: \n sockFd->fd(%d) Index(%d) REvent(%d) EventMask(%d) \n",
618 pollFdArr[idx].fd,idx, pollFdArr[idx].revents,eventMask);
619 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
621 /* cm_inet_c_001.main_62:Warning fix */
622 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollClearFdREvent() Before clearing fd revents with eventMask: \n sockFd->fd(%d) Index(%d) REvent(%d) EventMask(%d) \n",
623 pollFdArr[idx].fd,idx, pollFdArr[idx].revents,eventMask);
624 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
625 #endif /*ALIGN_64BIT */
626 #endif /* CMINETDBG */
628 /* Clearing the events with eventMask */
629 pollFdArr[idx].revents = (pollFdArr[idx].revents & (~(eventMask)));
633 /* cm_inet_c_001.main_62:Warning fix */
634 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollClearFdREvent() After clearing fd revents with eventMask: \n sockFd->fd(%d) Index(%d) REvent(%d) EventMask(%d) \n",
635 pollFdArr[idx].fd,idx, pollFdArr[idx].revents,eventMask);
636 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
638 /* cm_inet_c_001.main_62:Warning fix */
639 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollClearFdREvent() After clearing fd revents with eventMask: \n sockFd->fd(%d) Index(%d) REvent(%d) EventMask(%d) \n",
640 pollFdArr[idx].fd,idx, pollFdArr[idx].revents,eventMask);
641 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
642 #endif /*ALIGN_64BIT */
643 #endif /* CMINETDBG */
652 * Fun: cmInetPollClearFdEvent
654 * Desc: clears the eventMask in event of the givent FD.
666 PUBLIC S16 cmInetPollClearFdEvent
668 CmInetPollFd *pollFdArr, /* poll FD Array */
669 S16 idx, /* poll Fd Array Index */
670 U16 eventMask /* Event Mask to be set */
673 PUBLIC S16 cmInetPollClearFdEvent(sockFd,pollFdArr,eventMask)
674 CmInetPollFd *pollFdArr; /* poll FD Array */
675 S16 idx; /* poll Fd Array Index */
676 U16 eventMask; /* Event Mask to be set */
680 TRC2(cmInetPollClearFdEvent);
683 if((idx < 0) || (idx > CM_INET_POLL_MAXFDSUPP))
686 /* cm_inet_c_001.main_62:Warning fix */
687 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollClearFdEvent() : Invalid Index (%d) \n",idx);
688 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
689 #endif /* CMINETDBG */
693 #if (ERRCLASS & ERRCLS_INT_PAR)
694 /* error check on parameters */
695 if (pollFdArr == NULLP)
698 /* cm_inet_c_001.main_62:Warning fix */
699 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollClearFdEvent() : Invalid Parameter (pollFdArr is NULL)");
700 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
701 #endif /* CMINETDBG */
704 #endif /* ERRCLASS & ERRCLS_INT_PAR */
708 /* cm_inet_c_001.main_62:Warning fix */
709 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollClearFdEvent() Before clearing fd events with eventMask: \n sockFd->fd(%d) Index(%d) Event(%d) EventMask(%d) \n",
710 pollFdArr[idx].fd,idx, pollFdArr[idx].events,eventMask);
711 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
713 /* cm_inet_c_001.main_62:Warning fix */
714 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollClearFdEvent() Before clearing fd events with eventMask:\n sockFd->fd(%d) Index(%d) Event(%d) EventMask(%d) \n",
715 pollFdArr[idx].fd,idx, pollFdArr[idx].events,eventMask);
716 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
717 #endif /*ALIGN_64BIT */
718 #endif /* CMINETDBG */
720 /* Clearing events with eventMask */
721 pollFdArr[idx].events = (pollFdArr[idx].events & (~(eventMask)));
725 /* cm_inet_c_001.main_62:Warning fix */
726 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollClearFdEvent() After clearing fd events with eventMask: sockFd->fd(%d) Index(%d) Event(%d) EventMask(%d) \n",
727 pollFdArr[idx].fd,idx, pollFdArr[idx].events,eventMask);
728 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
730 /* cm_inet_c_001.main_62:Warning fix */
731 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollClearFdEvent() After clearing fd events with eventMask: sockFd->fd(%d) Index(%d) Event(%d) EventMask(%d) \n",
732 pollFdArr[idx].fd,idx, pollFdArr[idx].events,eventMask);
733 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
734 #endif /*ALIGN_64BIT */
735 #endif /* CMINETDBG */
744 * Fun: cmInetPollDelFd
746 * Desc: Delete the given FD from the pollFdArray
747 * delIdx : Poll Fd Array Index at which fd has to be deleted.
748 * lastIdx: Last index of poll fd array.
750 * It deletes fd from array by swapping lastIdx pollFd
751 * values to index to be deleted and deinitializes the
757 * Notes: It does not decrement the lastIdx and it has to be
758 * decremented by the caller of this function.
765 PUBLIC S16 cmInetPollDelFd
767 CmInetPollFd *pollFdArr, /* poll FD Array */
768 S16 delIdx, /* poll Fd Array Index for which fd has to be deleted*/
769 S16 lastIdx /* Last index of poll Fd Array */
772 PUBLIC S16 cmInetPollDelFd(pollFdArr, delIdx, lastIdx)
773 CmInetPollFd *pollFdArr; /* poll FD Array */
774 S16 delIdx; /* poll Fd Array Index for which fd has to be deleted*/
775 S16 lastIdx; /* Last index of poll Fd Array */
779 TRC2(cmInetPollDelFd);
781 if(lastIdx < delIdx || lastIdx < 0 || delIdx < 0)
784 /* cm_inet_c_001.main_62:Warning fix */
785 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollDelFd() : Invalid Index \n Current Index (%d) Delete Index (%d) \n",lastIdx,delIdx);
786 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
787 #endif /* CMINETDBG */
792 #if (ERRCLASS & ERRCLS_INT_PAR)
793 /* error check on parameters */
794 if (pollFdArr == NULLP)
797 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollDelFd() : Invalid Parameter (pollFdArr is NULL)");
798 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
799 #endif /* CMINETDBG */
802 #endif /* ERRCLASS & ERRCLS_INT_PAR */
806 /* cm_inet_c_001.main_62:Warning fix */
807 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollDelFd() Deleting the sockFd->fd(%d) Index(%d) Event(%d) revent(%d) \n",
808 pollFdArr[delIdx].fd,delIdx, pollFdArr[delIdx].events,pollFdArr[delIdx].revents);
809 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
811 /* cm_inet_c_001.main_62:Warning fix */
812 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollDelFd() After clearing fd events with eventMask: sockFd->fd(%d) Index(%d) Event(%d) EventMask(%d) \n",
813 pollFdArr[delIdx].fd,delIdx, pollFdArr[delIdx].events,pollFdArr[delIdx].revents);
814 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
815 #endif /*ALIGN_64BIT */
816 #endif /* CMINETDBG */
818 pollFdArr[delIdx].fd = pollFdArr[lastIdx].fd;
819 pollFdArr[delIdx].events = pollFdArr[lastIdx].events;
820 pollFdArr[delIdx].revents = pollFdArr[lastIdx].revents;
822 pollFdArr[lastIdx].fd = -1;
823 pollFdArr[lastIdx].events = 0;
824 pollFdArr[lastIdx].revents = 0;
832 * Fun: cmInetPollInitFdArr
834 * Desc: Cleans all elements of fd array.
839 * Notes: It does not allocates/deallocates memory for Poll Fd Array.
840 * Caller of function has to allocate/deallocate memory for
848 PUBLIC S16 cmInetPollInitFdArr
850 CmInetPollFd *pollFdArr /* poll FD Array */
853 PUBLIC S16 cmInetPollInitFdArr(pollFdArr)
854 CmInetPollFd *pollFdArr; /* poll FD Array */
859 TRC2(cmInetPollInitFdArr);
860 /* Sets each element of pollFdArr to initial value
865 #if (ERRCLASS & ERRCLS_INT_PAR)
866 /* error check on parameters */
867 if (pollFdArr == NULLP)
870 /* cm_inet_c_001.main_62:Warning fix */
871 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetPollInitFdArr() : Invalid Parameter (pollFdArr is NULL)");
872 CMINETLOGERROR(ERRCLS_DEBUG, ECMINETXXX, 0, prntBuf);
873 #endif /* CMINETDBG */
876 #endif /* ERRCLASS & ERRCLS_INT_PAR */
878 for(idx=0; idx < CM_INET_POLL_MAXFDSUPP; idx++)
880 pollFdArr[idx].fd = -1;
881 pollFdArr[idx].events = 0;
882 pollFdArr[idx].revents = 0;
887 #if (!(defined(WIN32)) && !(defined(CMINETFLATBUF)))
892 * Desc: Allocates dBufs to receive an entire message.
894 * Ret: ROK - successful
896 * ROUTRES - failed, out of resources
905 PRIVATE S16 buildRecvBuf
907 CmInetMemInfo *info, /* buffer allocation info */
908 MsgLen len, /* message length */
909 CmInetIovec rxArr[], /* gather array */
910 Buffer *dBuf[], /* allocated dBufs */
911 U16 maxSize, /* size of rxArr/dBuf array */
912 struct msghdr *msg, /* message header for recvmsg() */
913 Bool isStrmMsg /* Is a TCP message */
916 PRIVATE S16 buildRecvBuf(info, len, rxArr, dBuf, maxSize, msg, isStrmMsg)
917 CmInetMemInfo *info; /* buffer allocation info */
918 MsgLen len; /* message length */
919 CmInetIovec rxArr[]; /* gather array */
920 Buffer *dBuf[]; /* allocated dBufs */
921 U16 maxSize; /* size of rxArr/dBuf array */
922 struct msghdr *msg; /* message header for recvmsg() */
923 Bool isStrmMsg; /* Is a TCP message */
926 S16 ret; /* temporary return value */
927 U16 numBuf; /* number of dBufs */
928 U16 i; /* dBuf index counter */
929 Data *dPtr; /* data pointer */
930 /* cm_inet_c_001.main_47: 102069 Changed from S32 to MsgLen for bufLen*/
931 MsgLen bufLen; /* entire receive buffer length, if S16
932 could wrap to negative number */
933 MsgLen dLen; /* buffer length */
938 /* Initialise ret and part of msg here */
941 /* added defined(_XPG4_2) */
942 /* Moved initialisation of msg here. */
944 #if (defined(SS_LINUX) || defined(_XPG4_2))
945 msg->msg_control = NULLP;
946 msg->msg_controllen = 0;
948 msg->msg_accrights = NULLP;
949 msg->msg_accrightslen = 0;
950 #endif /* SS_LINUX */
952 /* Check if maxSize if enough to hold the entire message length before
953 * going into the loop. If the boolean isStrmMsg is TRUE then the recv
954 * buf is built even if the whole message cannot be accomodated. */
956 #ifdef T2K_MEM_LEAK_DBG
957 char * file = __FILE__;
959 ret = SGetDBuf(info->region, info->pool, &dBuf[numBuf]);
961 ret = SGetDBuf(info->region, info->pool, &dBuf[numBuf]);
966 /* Get the data part */
967 ret = SGetDataRx(dBuf[numBuf], 0, &dPtr, &dLen);
970 numBuf++; /* because of cleanup */
976 /* The assumption here is that all dBuf's from a given region and
977 * pool have a constance size */
978 if (len > (maxSize * dLen))
981 numBuf++; /* because of cleanup */
987 rxArr[numBuf].iov_base = (Void*)dPtr;
988 rxArr[numBuf].iov_len = (U32)dLen;
990 rxArr[numBuf].iov_base = (S8*)dPtr;
991 rxArr[numBuf].iov_len = dLen;
992 #endif /* SS_LINUX */
997 /* allocate buffer space for entire message length */
1000 if (numBuf >= maxSize)
1002 /* to big to fit in gather vector array */
1006 ret = SGetDBuf(info->region, info->pool, &dBuf[numBuf]);
1011 ret = SGetDataRx(dBuf[numBuf], 0, &dPtr, &dLen);
1014 numBuf++; /* because of cleanup */
1018 rxArr[numBuf].iov_base = (Void*)dPtr;
1019 rxArr[numBuf].iov_len = (U32)dLen;
1021 rxArr[numBuf].iov_base = (S8*)dPtr;
1022 rxArr[numBuf].iov_len = dLen;
1023 #endif /* SS_LINUX */
1028 /* adjust last buffer length */
1029 /* check if we broke out because numBuf >= maxSize */
1031 rxArr[numBuf - 1].iov_len = dLen;
1033 rxArr[numBuf - 1].iov_len = dLen - (bufLen - len);
1035 /* setup recvmsg() message header */
1036 msg->msg_iov = rxArr;
1037 msg->msg_iovlen = numBuf;
1043 for (i = 0; i < numBuf; i++)
1044 SPutDBuf(info->region, info->pool, dBuf[i]);
1046 msg->msg_iovlen = 0;
1049 } /* end of buildRecvBuf */
1055 * Desc: Builds a message out of the received dBufs.
1057 * Ret: ROK - successful
1059 * ROUTRES - failed, out of resources
1068 PRIVATE S16 buildRecvMsg
1070 CmInetMemInfo *info, /* buffer allocation info */
1071 CmInetIovec rxArr[], /* scatter array */
1072 S16 numBuf, /* number of allocated dBufs */
1073 MsgLen msgLen, /* message length */
1074 Buffer *dBufs[], /* dBufs */
1075 Buffer **mPtr /* message built from dBufs */
1078 PRIVATE S16 buildRecvMsg(info, rxArr, numBuf, msgLen, dBufs, mPtr)
1079 CmInetMemInfo *info; /* buffer allocation info */
1080 CmInetIovec rxArr[]; /* scatter array */
1081 S16 numBuf; /* number of allocated dBufs */
1082 MsgLen msgLen; /* length of one particular dBuf */
1083 Buffer *dBufs[]; /* dBufs */
1084 Buffer **mPtr; /* message built from dBufs */
1087 S16 ret; /* return value */
1088 S16 i; /* dBuf index counter */
1089 MsgLen bufLen; /* length of one particular dBuf */
1090 /* cm_inet_c_001.main_54: Fix for Klockworks issue */
1091 Buffer *mBuf = NULLP; /* allocated message */
1097 ret = SGetMsg(info->region, info->pool, &mBuf);
1103 /* link buffers to message */
1106 /* cm_inet_c_001.main_58: fix for klockwork issue */
1107 bufLen = (MsgLen)rxArr[i].iov_len;
1108 if (msgLen < bufLen)
1112 ret = SUpdMsg(mBuf, dBufs[i], bufLen);
1130 /* cleanup unused buffers */
1133 #ifdef T2K_MEM_LEAK_DBG
1134 char * file = __FILE__;
1135 U32 line = __LINE__;
1136 SPutDBuf(info->region, info->pool, dBufs[i]);
1138 SPutDBuf(info->region, info->pool, dBufs[i]);
1144 } /* end of buildRecvMsg */
1150 * Fun: buildSendIovec
1152 * Desc: Builds a io vector to send a message.
1154 * Ret: ROK - successful
1156 * ROUTRES - failed, out of resources
1157 * RNA - failed, not available, indicates that the
1158 * maximum number of dBufs are not sufficient
1159 * to hold the entire message.
1167 PRIVATE S16 buildSendIovec
1169 Buffer *mBuf, /* Message buffer */
1170 MsgLen msgLen, /* Length of mBuf */
1171 CmInetIovec txArr[], /* transmit scatter vector array */
1172 S16 numDBufs, /* Maximum number of dBufs to use */
1173 S16 *numIovElems, /* Number of iov elements in array */
1174 U32 *strtEndDBufNum, /* dBuf number to start and end */
1175 MsgLen *ioLen /* cm_inet_c_001.main_50 - Len of dbuf packed into IO-vector */
1178 PRIVATE S16 buildSendIovec(mBuf, msgLen, txArr, numDBufs, numIovElems,
1179 strtEndDBufNum,ioLen)
1180 Buffer *mBuf; /* Message buffer */
1181 MsgLen msgLen; /* Length of mBuf */
1182 CmInetIovec txArr[]; /* transmit scatter vector array */
1183 S16 numDBufs; /* Maximum number of dBufs to use */
1184 S16 *numIovElems; /* Number of iov elements in array */
1185 U32 *strtEndDBufNum; /* dBuf number to start and end */
1186 MsgLen *ioLen; /* cm_inet_c_001.main_50 - Len of dbuf packed into IO-vector */
1197 /* Initialisations */
1202 /* cm_inet_c_001.main_50 - Intialize the newly added parameter */
1205 /* Set up vector for gathering send */
1206 ret = SInitNxtDBuf(mBuf);
1213 txArr[iovIdx].iov_len = 0;
1215 if ((*strtEndDBufNum != 0))
1217 /* Skip through the required number of dBufs */
1218 dBufsToSkip = *strtEndDBufNum;
1222 ret = SGetNxtDBuf(mBuf, &dBuf);
1231 ret = SGetNxtDBuf(mBuf, &dBuf);
1234 ret = SGetDataTx(dBuf, &dPtr, &dLen);
1241 txArr[iovIdx].iov_base = (S8 *)dPtr;
1242 txArr[iovIdx].iov_len = dLen;
1246 else if (ret == ROKDNA)
1259 if (iovIdx >= numDBufs)
1261 if (allocLen >= msgLen)
1269 (*numIovElems) = iovIdx;
1270 (*strtEndDBufNum) += iovIdx;
1272 /* cm_inet_c_001.main_50 - Assign the value of dbufs packed in IO-vector */
1277 } /* end of buildSendIovec */
1278 #endif /* (defined(WIN32)) && !(defined(CMINETFLATBUF)) */
1285 * Desc: Creates an Internet socket descriptor.
1286 * On default the socket is non-blocking ( can be changed
1287 * with the function cmInetSetOpt()).
1290 * CM_INET_STREAM (TCP)
1291 * CM_INET_DGRAM (UDP)
1293 * Ret: ROK - successful
1303 #ifdef IPV6_SUPPORTED
1304 PUBLIC S16 cmInetSocket
1306 U8 type, /* socket type */
1307 CmInetFd *sockFd, /* socket file descriptor */
1308 U8 protocol, /* protocol value */
1309 U8 domain /* domain */
1312 PUBLIC S16 cmInetSocket
1314 U8 type, /* socket type */
1315 CmInetFd *sockFd, /* socket file descriptor */
1316 U8 protocol /* protocol value */
1318 #endif /* IPV6_SUPPORTED */
1319 #else /* CM_INET2 */
1320 PUBLIC S16 cmInetSocket
1322 U8 type, /* socket type */
1323 CmInetFd *sockFd /* socket file descriptor */
1325 #endif /* CM_INET2 */
1328 #ifdef IPV6_SUPPORTED
1329 PUBLIC S16 cmInetSocket(type, sockFd, protocol, domain)
1330 U8 type; /* socket type */
1331 CmInetFd *sockFd; /* socket file descriptor */
1332 U8 protocol; /* protocol value */
1333 U8 domain; /* domain */
1335 PUBLIC S16 cmInetSocket(type, sockFd, protocol)
1336 U8 type; /* socket type */
1337 CmInetFd *sockFd; /* socket file descriptor */
1338 U8 protocol; /* protocol value */
1339 #endif /* IPV6_SUPPORTED */
1340 #else /* CM_INET2 */
1341 PUBLIC S16 cmInetSocket(type, sockFd)
1342 U8 type; /* socket type */
1343 CmInetFd *sockFd; /* socket file descriptor */
1344 #endif /* CM_INET2 */
1347 S32 ret; /* temporary return value */
1351 #if (defined(WIN32) && defined(WIN2K))
1354 #endif /* WIN2K && WIN32 */
1358 #if (defined(WIN32) && defined(WIN2K))
1360 bNewBehavior = FALSE;
1361 #endif /* WIN32 && WIN2K */
1365 #ifdef IPV6_SUPPORTED
1366 sockFd->fd = socket(domain, type, protocol);
1368 sockFd->fd = socket(AF_INET, type, protocol);
1369 #endif /* IPV6_SUPPORTED */
1370 #else /* CM_INET2 */
1371 sockFd->fd = socket(AF_INET, type, 0);
1372 #endif /* CM_INET2 */
1373 if (CM_INET_INV_SOCK_FD(sockFd))
1377 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
1378 /* cm_inet_c_001.main_62:Warning fix */
1379 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSocket() Failed : errno(%d), sockFd->fd(%ld)\n",
1380 INET_ERR_CODE, sockFd->fd);
1381 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET001, 0, prntBuf);
1383 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSocket() Failed : errno(%d), sockFd->fd(%d)\n",
1384 INET_ERR_CODE, sockFd->fd);
1385 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET001, 0, prntBuf);
1386 #endif /*ALIGN_64BIT */
1387 #endif /* CMINETDBG */
1388 /* Set sockFd->fd to invalid socket */
1389 sockFd->fd = CM_INET_INV_SOCKFD;
1393 /* set socket type */
1394 sockFd->type = type;
1396 /* set socket protocol type (IPv4/IPv6) */
1397 #ifdef IPV6_SUPPORTED
1398 sockFd->protType = domain;
1399 #endif /* IPV6_SUPPORTED */
1401 /*cm_inet_c_001.main_38 Updated for TUCL 2.1 Release (Kernel SCTP Support) */
1403 if (protocol != IPPROTO_SCTP)
1406 /* set default options */
1407 optVal = CM_INET_OPT_DISABLE;
1408 ret = cmInetSetOpt(sockFd, SOL_SOCKET, CM_INET_OPT_BLOCK, (Ptr)&optVal);
1411 ret = cmInetClose(sockFd);
1416 #ifndef CMINET_BSDCOMPAT
1417 optVal = CM_INET_OPT_ENABLE;
1418 ret = cmInetSetOpt(sockFd, SOL_SOCKET, CM_INET_OPT_BSD_COMPAT, (Ptr)&optVal);
1421 ret = cmInetClose(sockFd);
1424 #endif /* CMINET_BSDCOMPAT */
1425 #endif /* SS_LINUX */
1427 #if (defined(WIN32) && defined(WIN2K))
1428 if(type == CM_INET_DGRAM)
1430 ret = WSAIoctl(sockFd->fd, SIO_UDP_CONNRESET, &bNewBehavior,
1431 sizeof(bNewBehavior), NULLP, 0, &bytesReturned,
1437 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
1438 /* cm_inet_c_001.main_62:Warning fix */
1439 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "WSAIoctl() Failed : error(%d), sockFd->fd(%ld)\n",
1440 INET_ERR_CODE, sockFd->fd);
1441 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET002, 0, prntBuf);
1443 /* cm_inet_c_001.main_62:Warning fix */
1444 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "WSAIoctl() Failed : error(%d), sockFd->fd(%d)\n",
1445 INET_ERR_CODE, sockFd->fd);
1446 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET002, 0, prntBuf);
1447 #endif /*ALIGN_64BIT*/
1448 #endif /* CMINETDBG */
1449 ret = cmInetClose(sockFd);
1453 #endif /* WIN2K && WIN32 */
1454 /*cm_inet_c_001.main_38 Updated for TUCL 2.1 Release (Kernel SCTP Support) */
1457 #ifdef CM_LKSCTP_NONBLOCK
1460 /* cm_inet_c_001.main_47:if non-blocking SCTP socket compile time
1461 * * flag is set then even for kernel SCTP make the socket
1464 optVal = CM_INET_OPT_DISABLE;
1465 ret = cmInetSetOpt(sockFd, SOL_SOCKET, CM_INET_OPT_BLOCK, (Ptr)&optVal);
1468 ret = cmInetClose(sockFd);
1472 #endif /* CM_LKSCTP_NONBLOCK ends */
1475 } /* end of cmInetSocket */
1482 * Desc: Binds a socket file descriptor to a local Internet
1485 * Ret: ROK - successful
1495 PUBLIC S16 cmInetBind
1497 CmInetFd *sockFd, /* socket file descriptor */
1498 CmInetAddr *myAddr /* locale Internet address/port */
1501 PUBLIC S16 cmInetBind(sockFd, myAddr)
1502 CmInetFd *sockFd; /* socket file descriptor */
1503 CmInetAddr *myAddr; /* locale Internet address/port */
1506 S32 ret; /* temporary return value */
1507 struct sockaddr_in srcAddr; /* local Internet address/port */
1508 #ifdef IPV6_SUPPORTED
1509 struct sockaddr_in6 srcAddr6; /* local IPV6 address/port */
1512 #endif /* CMINETDBG */
1513 #endif /* IPV6_SUPPORTED */
1514 U32 sizeOfAddr; /* sizeof address passed to the bind call */
1515 CmInetSockAddr *sockAddrPtr;
1519 #if (ERRCLASS & ERRCLS_INT_PAR)
1520 /* error check on parameters */
1521 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) ||
1526 #endif /* ERRCLASS & ERRCLS_INT_PAR */
1528 #ifdef IPV6_SUPPORTED
1529 if (myAddr->type == CM_INET_IPV6ADDR_TYPE)
1531 cmMemset((U8*)&srcAddr6, 0, sizeof(srcAddr6));
1532 srcAddr6.sin6_family = AF_INET6;
1533 srcAddr6.sin6_port = CM_INET_HTON_U16(myAddr->u.ipv6Addr.port);
1534 CM_INET_COPY_IPV6ADDR(&srcAddr6.sin6_addr,
1535 &myAddr->u.ipv6Addr.ipv6NetAddr);
1536 sizeOfAddr = sizeof(struct sockaddr_in6);
1537 sockAddrPtr = (CmInetSockAddr *)&srcAddr6;
1541 cmMemset((U8*)&srcAddr, 0, sizeof(srcAddr));
1542 srcAddr.sin_family = AF_INET;
1543 srcAddr.sin_port = CM_INET_HTON_U16(myAddr->u.ipv4Addr.port);
1544 srcAddr.sin_addr.s_addr = CM_INET_HTON_U32(myAddr->u.ipv4Addr.address);
1545 sizeOfAddr = sizeof(struct sockaddr_in);
1546 sockAddrPtr = (CmInetSockAddr *)&srcAddr;
1549 cmMemset((U8*)&srcAddr, 0, sizeof(srcAddr));
1550 srcAddr.sin_family = AF_INET;
1551 srcAddr.sin_port = CM_INET_HTON_U16(myAddr->port);
1552 srcAddr.sin_addr.s_addr = CM_INET_HTON_U32(myAddr->address);
1553 sizeOfAddr = sizeof(struct sockaddr_in);
1554 sockAddrPtr = (CmInetSockAddr *)&srcAddr;
1555 #endif /* IPV6_SUPPORTED */
1557 ret = bind(sockFd->fd, sockAddrPtr, sizeOfAddr);
1558 if (ret == INET_ERR)
1561 #ifdef IPV6_SUPPORTED
1562 if (myAddr->type == CM_INET_IPV6ADDR_TYPE)
1563 port = myAddr->u.ipv6Addr.port;
1565 port = myAddr->u.ipv4Addr.port;
1567 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
1568 /* cm_inet_c_001.main_62:Warning fix */
1569 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetBind() Failed : error(%d), addrType(%d),"
1570 " port(%d), sockFd->fd(%ld)\n",
1571 INET_ERR_CODE , myAddr->type, port, sockFd->fd);
1572 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET003, 0, prntBuf);
1574 /* cm_inet_c_001.main_62:Warning fix */
1575 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetBind() Failed : error(%d), addrType(%d),"
1576 " port(%d), sockFd->fd(%d)\n ",
1577 INET_ERR_CODE , myAddr->type, port, sockFd->fd);
1578 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET003, 0, prntBuf);
1579 #endif /*ALIGN_64BIT*/
1582 /* cm_inet_c_001.main_62:Warning fix */
1583 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetBind() Failed : error(%d), addr(0x%lx), port(%d),"
1584 "sockFd->fd(%ld)\n",
1585 INET_ERR_CODE , myAddr->address, myAddr->port, sockFd->fd);
1586 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET004, 0, prntBuf);
1588 /* cm_inet_c_001.main_62:Warning fix */
1589 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetBind() Failed : error(%d), addr(0x%x), port(%d),"
1590 " sockFd->fd(%d)\n",
1591 INET_ERR_CODE , myAddr->address, myAddr->port, sockFd->fd);
1592 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET004, 0, prntBuf);
1593 #endif /*ALIGN_64BIT*/
1594 #endif /* IPV6_SUPPORTED */
1595 #endif /* CMINETDBG */
1600 } /* end of cmInetBind */
1602 /*cm_inet_c_001.main_38 Updated for TUCL 2.1 Release (Kernel SCTP Support) */
1603 /* cm_inet_c_001.main_51 Added Ipv6 support to KSCtP implementation */
1607 * Fun: cmInetSctpBindx
1609 * Desc: Binds a SCTP socket file descriptor to local Internet
1612 * Ret: ROK - successful
1621 PUBLIC S16 cmInetSctpBindx
1623 CmInetFd *sockFd, /* socket file descriptor */
1624 CmInetNetAddrLst *addrLst, /* local Internet address list */
1625 U16 port /* port number */
1628 PUBLIC S16 cmInetSctpBindx(sockFd, addrLst, port)
1629 CmInetFd *sockFd; /* socket file descriptor */
1630 CmInetNetAddrLst *addrLst; /* locale Internet address list */
1631 U16 port; /* port number */
1634 S32 ret; /* temporary return value */
1637 U32 ipv4_array_size = 0;
1638 struct sockaddr_in addrs[CM_INET_NUM_NET_ADDR];
1639 #ifndef IPV6_SUPPORTED
1640 Data address_array[(CM_INET_NUM_NET_ADDR * sizeof(struct sockaddr_in))];
1642 Data address_array[(CM_INET_NUM_NET_ADDR * sizeof(struct sockaddr_in6))];
1643 #endif /* IPV6_SUPPORTED */
1646 Data *tempAddrPtr = NULLP;
1648 U32 addresses_array_size = 0;
1649 #ifdef IPV6_SUPPORTED
1651 S8 *addrString = NULLP;
1653 S8 ipv4Format[23] = "::ffff:";
1654 #endif /* SUN_KSCTP */
1656 U32 ipv6_array_size = 0;
1657 struct sockaddr_in6 addrs6[CM_INET_NUM_NET_ADDR];
1658 #endif /* IPV6_SUPPORTED */
1659 struct sockaddr *sockAddrPtr = NULLP;
1660 U32 sockAddrLen = 0;
1662 #if (ERRCLASS & ERRCLS_INT_PAR)
1663 /* error check on parameters */
1664 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) ||
1670 if(addrLst->count > CM_INET_NUM_NET_ADDR)
1674 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
1675 /* cm_inet_c_001.main_62:Warning fix */
1676 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "No of address(%d) is greater than Max(%d),"
1677 " sockFd->fd(%ld)\n",
1678 addrLst->count, CM_INET_NUM_NET_ADDR, sockFd->fd);
1679 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET005, 0, prntBuf);
1681 /* cm_inet_c_001.main_62:Warning fix */
1682 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "No of address(%d) is greater than Max(%d),"
1683 " sockFd->fd(%d)\n",
1684 addrLst->count, CM_INET_NUM_NET_ADDR, sockFd->fd);
1685 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET005, 0, prntBuf);
1686 #endif /*ALIGN_64BIT*/
1687 #endif /* CMINETDBG */
1690 #endif /* ERRCLASS & ERRCLS_INT_PAR */
1692 cmMemset((U8*)&addrs, 0, (sizeof(struct sockaddr_in) * CM_INET_NUM_NET_ADDR));
1693 #ifdef IPV6_SUPPORTED
1694 cmMemset((U8*)&addrs6, 0, (sizeof(struct sockaddr_in6) * CM_INET_NUM_NET_ADDR));
1695 #endif /* IPV6_SUPPORTED */
1697 for (idx = 0; idx < addrLst->count; idx++)
1699 #ifdef IPV6_SUPPORTED
1700 if (addrLst->addrs[idx].type == CM_INET_IPV6ADDR_TYPE)
1702 ipv6_array_size += sizeof(struct sockaddr_in6);
1703 addresses_array_size += sizeof(struct sockaddr_in6);
1704 if (sockFd->protType == AF_INET)
1708 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
1709 /* cm_inet_c_001.main_62:Warning fix */
1710 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "can't bind IPV6 address on IPV4 socket,"
1711 " sockFd->fd(%ld)\n", sockFd->fd);
1712 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET057, 0, prntBuf);
1714 /* cm_inet_c_001.main_62:Warning fix */
1715 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "can't bind IPV6 address on IPV4 socket,"
1716 " sockFd->fd(%d)\n", sockFd->fd);
1717 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET057, 0, prntBuf);
1718 #endif /*ALIGN_64BIT*/
1719 #endif /* CMINETDBG */
1723 addrs6[idx6].sin6_family = AF_INET6;
1724 addrs6[idx6].sin6_port = CM_INET_HTON_U16(port);
1725 CM_INET_COPY_IPV6ADDR((addrs6[idx6].sin6_addr.s6_addr), &(addrLst->addrs[idx].u.ipv6NetAddr));
1732 ipv6_array_size += sizeof(struct sockaddr_in6);
1733 addresses_array_size += sizeof(struct sockaddr_in6);
1734 if (sockFd->protType == AF_INET)
1738 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
1739 /* cm_inet_c_001.main_62:Warning fix */
1740 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "can't bind IPV6 address on IPV4 socket,"
1741 " sockFd->fd(%ld)\n", sockFd->fd);
1742 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET058, 0, prntBuf);
1744 /* cm_inet_c_001.main_62:Warning fix */
1745 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "can't bind IPV6 address on IPV4 socket,"
1746 " sockFd->fd(%d)\n", sockFd->fd);
1747 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET058, 0, prntBuf);
1748 #endif /*ALIGN_64BIT*/
1749 #endif /* CMINETDBG */
1753 addrs6[idx6].sin6_family = AF_INET6;
1754 addrs6[idx6].sin6_port = CM_INET_HTON_U16(port);
1755 addrLst->addrs[idx].u.ipv4NetAddr = CM_INET_HTON_U32(addrLst->addrs[idx].u.ipv4NetAddr);
1756 cmInetNtoa(addrLst->addrs[idx].u.ipv4NetAddr, &addrString);
1757 addrLen = cmStrlen((U8*)addrString);
1758 cmMemcpy((U8*)(ipv4Format+7), (U8*)addrString, addrLen);
1759 ipv4Format[7+addrLen] = '\0';
1760 cmInetPton6((CmInetIpAddr6*)(addrs6[idx6].sin6_addr.s6_addr), ipv4Format);
1763 ipv4_array_size += sizeof(struct sockaddr_in);
1764 addresses_array_size += sizeof(struct sockaddr_in);
1765 addrs[idx4].sin_family = AF_INET;
1766 addrs[idx4].sin_port = CM_INET_HTON_U16(port);
1767 addrs[idx4].sin_addr.s_addr = CM_INET_HTON_U32(addrLst->addrs[idx].u.ipv4NetAddr);
1769 #endif /* SUN_KSCTP */
1772 ipv4_array_size += sizeof(struct sockaddr_in);
1773 addresses_array_size += sizeof(struct sockaddr_in);
1774 addrs[idx4].sin_family = AF_INET;
1775 addrs[idx4].sin_port = CM_INET_HTON_U16(port);
1776 addrs[idx4].sin_addr.s_addr = CM_INET_HTON_U32(addrLst->addrs[idx].u.ipv4NetAddr);
1778 #endif /* IPV6_SUPPORTED */
1782 if(ipv4_array_size > 0)
1784 sockAddrPtr = (struct sockaddr*)address_array;
1785 sockAddrLen = sizeof(struct sockaddr_in);
1786 cmMemcpy((U8*)address_array, (U8*)addrs, ipv4_array_size);
1788 #ifdef IPV6_SUPPORTED
1791 sockAddrPtr = (struct sockaddr*)address_array;
1792 sockAddrLen = sizeof(struct sockaddr_in6);
1795 if(ipv6_array_size > 0)
1797 cmMemcpy((U8*)(address_array + ipv4_array_size), (U8*)addrs6, ipv6_array_size);
1799 #endif /* IPV6_SUPPORTED */
1803 ret = bind(sockFd->fd, sockAddrPtr, sockAddrLen);
1804 if (ret == INET_ERR)
1809 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
1810 /* cm_inet_c_001.main_62:Warning fix */
1811 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpBindx() Failed : error(%d), port(%d),"
1812 " sockFd->fd(%ld)\n",INET_ERR_CODE, port, sockFd->fd);
1813 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET006, 0, prntBuf);
1815 /* cm_inet_c_001.main_62:Warning fix */
1816 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpBindx() Failed : error(%d), port(%d),"
1817 " sockFd->fd(%d)\n",INET_ERR_CODE, port, sockFd->fd);
1818 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET006, 0, prntBuf);
1819 #endif /*ALIGN_64BIT*/
1820 #endif /* CMINETDBG */
1824 if (addrLst->count > 1)
1826 if(((struct sockaddr*)address_array)->sa_family == AF_INET)
1828 tempAddrPtr = address_array + (sizeof(struct sockaddr_in));
1830 else if(((struct sockaddr*)address_array)->sa_family == AF_INET6)
1832 tempAddrPtr = address_array + (sizeof(struct sockaddr_in6));
1838 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
1839 /* cm_inet_c_001.main_62:Warning fix */
1840 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpBindx(Invalid address Type) failed:"
1841 " sockFd->fd(%ld), error(%d), port(%d)\n ",
1842 INET_ERR_CODE, port, sockFd->fd);
1843 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET059, 0, prntBuf);
1845 /* cm_inet_c_001.main_62:Warning fix */
1846 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpBindx(Invalid address Type) failed:"
1847 " sockFd->fd(%d), error(%d), port(%d)\n ",
1848 INET_ERR_CODE, port, sockFd->fd);
1849 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET059, 0, prntBuf);
1850 #endif /*ALIGN_64BIT*/
1851 #endif /* CMINETDBG */
1855 ret = sctp_bindx(sockFd->fd, (Void*)tempAddrPtr, addrLst->count - 1, SCTP_BINDX_ADD_ADDR);
1859 ret = sctp_bindx(sockFd->fd, (struct sockaddr*)address_array, addrLst->count, SCTP_BINDX_ADD_ADDR);
1860 UNUSED(sockAddrPtr);
1861 UNUSED(sockAddrLen);
1863 if (ret == INET_ERR)
1867 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
1868 /* cm_inet_c_001.main_62:Warning fix */
1869 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpBindx() Failed : error(%d), port(%d),"
1870 " sockFd->fd(%ld)\n",INET_ERR_CODE, port, sockFd->fd);
1871 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET007, 0, prntBuf);
1873 /* cm_inet_c_001.main_62:Warning fix */
1874 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpBindx() Failed : error(%d), port(%d),"
1875 " sockFd->fd(%d)\n",INET_ERR_CODE, port, sockFd->fd);
1876 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET007, 0, prntBuf);
1877 #endif /*ALIGN_64BIT*/
1878 #endif /* CMINETDBG */
1887 * Fun: cmInetSctpConnectx
1889 * Desc: Establishes a sctp connection with remote addresses
1891 * Ret: ROK - successful
1900 PUBLIC S16 cmInetSctpConnectx
1902 CmInetFd *sockFd, /* socket file descriptor */
1903 CmInetNetAddr *primAddr, /* primary destination Internet address */
1904 CmInetNetAddrLst *addrLst, /* destination Internet address list */
1905 U16 port /* port number */
1908 PUBLIC S16 cmInetSctpConnectx(sockFd, primAddr, addrLst, port)
1909 CmInetFd *sockFd; /* socket file descriptor */
1910 CmInetNetAddr *primAddr; /* primary destination Internet address */
1911 CmInetNetAddrLst *addrLst; /* destination Internet address list */
1912 U16 port; /* port number */
1917 /* cm_inet_c_001.main_46: Removed SS_LINUX flag */
1920 /* cm_inet_c_001.main_64: New variable used as an argument for sctp_connectx */
1921 #ifdef SCTP_CONNECTX_NEW
1924 U32 addresses_array_size = 0;
1926 struct sockaddr_in addrs[CM_INET_NUM_NET_ADDR];
1927 U32 ipv4_array_size = 0;
1929 #ifndef IPV6_SUPPORTED
1930 Data address_array[(CM_INET_NUM_NET_ADDR * sizeof(struct sockaddr_in))];
1932 Data address_array[(CM_INET_NUM_NET_ADDR * sizeof(struct sockaddr_in6))];
1933 #endif /* IPV6_SUPPORTED */
1935 #ifdef IPV6_SUPPORTED
1937 S8 *addrString = NULLP;
1939 S8 ipv4Format[23] = "::ffff:";
1940 CmInetIpAddr ipv4NetAddr;
1941 #endif /* SUN_KSCTP */
1943 struct sockaddr_in6 addrs6[CM_INET_NUM_NET_ADDR];
1944 U32 ipv6_array_size = 0;
1945 #endif /* IPV6_SUPPORTED */
1947 U32 sockAddrLen = 0;
1948 #endif /* sockAddrLen */
1951 CmInetSockAddr *sockAddrPtr = NULLP;
1952 #endif /* SS_LINUX */
1953 #if (ERRCLASS & ERRCLS_INT_PAR)
1954 /* error check on parameters */
1955 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) ||
1956 (primAddr == NULLP))
1960 /* cm_inet_c_001.main_58 : Added check for addrLst to fix klockwork issue */
1961 if (addrLst == NULLP)
1965 /* cm_inet_c_001.main_46: Included check for no of address aginst max */
1966 if( addrLst->count > CM_INET_NUM_NET_ADDR )
1970 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
1971 /* cm_inet_c_001.main_62:Warning fix */
1972 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "No of address(%d) is greater than Max(%d),"
1973 " sockFd->fd(%ld)\n",
1974 addrLst->count, CM_INET_NUM_NET_ADDR, sockFd->fd);
1975 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET060, 0, prntBuf);
1977 /* cm_inet_c_001.main_62:Warning fix */
1978 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "No of address(%d) is greater than Max(%d),"
1979 " sockFd->fd(%d)\n",
1980 addrLst->count, CM_INET_NUM_NET_ADDR, sockFd->fd);
1981 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET060, 0, prntBuf);
1982 #endif /*ALIGN_64BIT*/
1983 #endif /* CMINETDBG */
1986 #endif /* ERRCLASS & ERRCLS_INT_PAR */
1989 cmMemset((U8*)&addrs, 0, (sizeof(struct sockaddr_in) * CM_INET_NUM_NET_ADDR));
1990 #ifdef IPV6_SUPPORTED
1991 cmMemset((U8*)&addrs6, 0, (sizeof(struct sockaddr_in6) * CM_INET_NUM_NET_ADDR));
1992 #endif /* IPV6_SUPPORTED */
1996 #ifdef IPV6_SUPPORTED
1997 if (primAddr->type == CM_INET_IPV6ADDR_TYPE)
1999 if (sockFd->protType == AF_INET)
2003 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
2004 /* cm_inet_c_001.main_62:Warning fix */
2005 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "Can't connect to IPV6 address through IPV4 socket,"
2006 " sockFd->fd(%ld)\n", sockFd->fd);
2007 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET008, 0, prntBuf);
2009 /* cm_inet_c_001.main_62:Warning fix */
2010 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "Can't connect to IPV6 address through IPV4 socket,"
2011 " sockFd->fd(%d)\n", sockFd->fd);
2012 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET008, 0, prntBuf);
2013 #endif /*ALIGN_64BIT*/
2014 #endif /* CMINETDBG */
2018 addrs6[idx6].sin6_family = AF_INET6;
2019 addrs6[idx6].sin6_port = CM_INET_HTON_U16(port);
2020 CM_INET_COPY_IPV6ADDR(&(addrs6[idx6].sin6_addr.s6_addr), &(primAddr->u.ipv6NetAddr));
2021 addresses_array_size += sizeof(struct sockaddr_in6);
2022 ipv6_array_size += sizeof(struct sockaddr_in6);
2028 if (sockFd->protType == AF_INET)
2032 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
2033 /* cm_inet_c_001.main_62:Warning fix */
2034 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "can't connect to IPV6 address through IPV4 socket,"
2035 " sockFd->fd(%ld)\n", sockFd->fd);
2036 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET061, 0, prntBuf);
2038 /* cm_inet_c_001.main_62:Warning fix */
2039 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "can't connect to IPV6 address through IPV4 socket,"
2040 " sockFd->fd(%d)\n", sockFd->fd);
2041 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET061, 0, prntBuf);
2042 #endif /*ALIGN_64BIT*/
2043 #endif /* CMINETDBG */
2046 addrs6[idx6].sin6_family = AF_INET6;
2047 addrs6[idx6].sin6_port = CM_INET_HTON_U16(port);
2048 ipv4NetAddr = CM_INET_HTON_U32(primAddr->u.ipv4NetAddr);
2049 cmInetNtoa(ipv4NetAddr, &addrString);
2050 addrLen = cmStrlen((U8*)addrString);
2051 cmMemcpy((U8*)(ipv4Format+7), (U8*)addrString, addrLen);
2052 ipv4Format[7+addrLen] = '\0';
2053 cmInetPton6((CmInetIpAddr6*)&(addrs6[idx6].sin6_addr), ipv4Format);
2054 addresses_array_size += sizeof(struct sockaddr_in6);
2055 ipv6_array_size += sizeof(struct sockaddr_in6);
2058 addrs[idx4].sin_family = AF_INET;
2059 addrs[idx4].sin_port = CM_INET_HTON_U16(port);
2060 addrs[idx4].sin_addr.s_addr = CM_INET_HTON_U32(primAddr->u.ipv4NetAddr);
2061 addresses_array_size += sizeof(struct sockaddr_in);
2062 ipv4_array_size += sizeof(struct sockaddr_in);
2067 addrs[idx4].sin_family = AF_INET;
2068 addrs[idx4].sin_port = CM_INET_HTON_U16(port);
2069 addrs[idx4].sin_addr.s_addr = CM_INET_HTON_U32(primAddr->u.ipv4NetAddr);
2070 addresses_array_size += sizeof(struct sockaddr_in);
2071 ipv4_array_size += sizeof(struct sockaddr_in);
2073 #endif /* IPV6_SUPPORTED */
2077 /* cm_inet_c_001.main_46: Moved the SS_LINUX flag down,
2078 * copy addresses in Solaris also */
2079 if (addrLst != NULLP)
2081 for (idx = 0; idx < addrLst->count; idx++)
2084 /* cm_inet_c_001.main_46: Don't include the primary address
2085 * if its prersent in list */
2086 if ( addrLst->addrs[idx].type == CM_INET_IPV4ADDR_TYPE )
2088 if ( addrLst->addrs[idx].u.ipv4NetAddr == primAddr->u.ipv4NetAddr )
2093 #ifdef IPV6_SUPPORTED
2094 else if ( addrLst->addrs[idx].type == CM_INET_IPV6ADDR_TYPE )
2096 if (( cmMemcmp(addrLst->addrs[idx].u.ipv6NetAddr,
2097 primAddr->u.ipv6NetAddr, sizeof(CmInetIpAddr6) )) == 0 )
2103 if (addrLst->addrs[idx].type == CM_INET_IPV6ADDR_TYPE)
2105 if (sockFd->protType == AF_INET)
2109 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
2110 /* cm_inet_c_001.main_62:Warning fix */
2111 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "Can't connect to IPV6 address through IPV4 socket,"
2112 " sockFd->fd(%ld)\n", sockFd->fd);
2113 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET009, 0, prntBuf);
2115 /* cm_inet_c_001.main_62:Warning fix */
2116 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "Can't connect to IPV6 address through IPV4 socket,"
2117 " sockFd->fd(%d)\n", sockFd->fd);
2118 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET009, 0, prntBuf);
2119 #endif /*ALIGN_64BIT*/
2120 #endif /* CMINETDBG */
2124 addrs6[idx6].sin6_family = AF_INET6;
2125 addrs6[idx6].sin6_port = CM_INET_HTON_U16(port);
2126 CM_INET_COPY_IPV6ADDR(&(addrs6[idx6].sin6_addr.s6_addr),
2127 &(addrLst->addrs[idx].u.ipv6NetAddr));
2128 addresses_array_size += sizeof(struct sockaddr_in6);
2129 ipv6_array_size += sizeof(struct sockaddr_in6);
2135 if (sockFd->protType == AF_INET)
2139 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
2140 /* cm_inet_c_001.main_62:Warning fix */
2141 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "can't connect to IPV6 address through IPV4 socket,"
2142 " sockFd->fd(%ld)\n", sockFd->fd);
2143 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET062, 0, prntBuf);
2145 /* cm_inet_c_001.main_62:Warning fix */
2146 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "can't connect to IPV6 address through IPV4 socket,"
2147 " sockFd->fd(%d)\n", sockFd->fd);
2148 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET062, 0, prntBuf);
2149 #endif /*ALIGN_64BIT*/
2150 #endif /* CMINETDBG */
2153 addrs6[idx6].sin6_family = AF_INET6;
2154 addrs6[idx6].sin6_port = CM_INET_HTON_U16(port);
2155 ipv4NetAddr = CM_INET_HTON_U32(addrLst->addrs[idx].u.ipv4NetAddr);
2156 cmInetNtoa(ipv4NetAddr, &addrString);
2157 addrLen = cmStrlen((U8*)addrString);
2158 cmMemcpy((U8*)(ipv4Format+7), (U8*)addrString, addrLen);
2159 ipv4Format[7+addrLen] = '\0';
2160 cmInetPton6((CmInetIpAddr6*)(addrs6[idx6].sin6_addr.s6_addr), ipv4Format);
2161 addresses_array_size += sizeof(struct sockaddr_in6);
2162 ipv6_array_size += sizeof(struct sockaddr_in6);
2165 addrs[idx4].sin_family = AF_INET;
2166 addrs[idx4].sin_port = CM_INET_HTON_U16(port);
2167 addrs[idx4].sin_addr.s_addr = CM_INET_HTON_U32(addrLst->addrs[idx].u.ipv4NetAddr);
2168 addresses_array_size += sizeof(struct sockaddr_in);
2169 ipv4_array_size += sizeof(struct sockaddr_in);
2171 #endif /* SUN_KSCTP */
2174 addrs[idx4].sin_family = AF_INET;
2175 addrs[idx4].sin_port = CM_INET_HTON_U16(port);
2176 addrs[idx4].sin_addr.s_addr = CM_INET_HTON_U32(addrLst->addrs[idx].u.ipv4NetAddr);
2177 addresses_array_size += sizeof(struct sockaddr_in);
2178 ipv4_array_size += sizeof(struct sockaddr_in);
2180 #endif /* IPV6_SUPPORTED */
2181 /*cm_inet_c_001.main_39 */
2186 /* cm_inet_c_001.main_46: Moved SS_LINUX flag to here */
2188 /*cm_inet_c_001.main_58 : Added check array_size to fix klockwork issue */
2189 if((ipv4_array_size > 0) && (ipv4_array_size <= (CM_INET_NUM_NET_ADDR * \
2190 sizeof(struct sockaddr_in))))
2192 cmMemcpy((U8*)address_array, (U8*)&addrs[0], ipv4_array_size);
2199 #ifdef IPV6_SUPPORTED
2200 if((ipv6_array_size > 0) && (ipv6_array_size <= (CM_INET_NUM_NET_ADDR * \
2201 sizeof(struct sockaddr_in))))
2203 cmMemcpy((U8*)(address_array + ipv4_array_size), (U8*)addrs6, ipv6_array_size);
2209 #endif /* IPV6_SUPPORTED */
2211 /* cm_inet_c_001.main_64: Support for new definition of sctp_connectx */
2212 #ifndef SCTP_CONNECTX_NEW
2213 ret = sctp_connectx(sockFd->fd, (struct sockaddr*)address_array, cnt);
2215 ret = sctp_connectx(sockFd->fd, (struct sockaddr*)address_array, cnt, (sctp_assoc_t *)&assocId);
2220 /* cm_inet_c_001.main_46: Use next provided address to connect if
2221 * first one fails */
2223 #ifdef CMINET_SUN_CONNECTX
2225 #ifdef IPV6_SUPPORTED
2227 #endif /* IPV6_SUPPORTED */
2228 for (idx = 0; idx < cnt; idx++)
2230 if( addrs[idx4].sin_family == AF_INET)
2232 sockAddrPtr = (CmInetSockAddr *)&addrs[idx4];
2233 sockAddrLen = sizeof(struct sockaddr_in);
2236 #ifdef IPV6_SUPPORTED
2239 sockAddrPtr = (CmInetSockAddr *)&addrs6[idx6];
2240 sockAddrLen = sizeof(struct sockaddr_in6);
2243 #endif/* IPV6_SUPPORTED */
2245 ret = connect(sockFd->fd, sockAddrPtr, sockAddrLen);
2247 if ( ret != INET_ERR )
2253 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
2254 /* cm_inet_c_001.main_62:Warning fix */
2255 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpConnectx() failed:error(%d), port(0x%1x),"
2256 " sockFd->fd(%ld)\n", INET_ERR_CODE, port, sockFd->fd);
2257 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET063, 0, prntBuf);
2259 /* cm_inet_c_001.main_62:Warning fix */
2260 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpConnectx() failed:error(%d), port(0x%1x),"
2261 " sockFd->fd(%d)\n", INET_ERR_CODE, port, sockFd->fd);
2262 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET063, 0, prntBuf);
2263 #endif /*ALIGN_64BIT*/
2264 #endif /* CMINETDBG */
2269 if( addrs[0].sin_family == AF_INET)
2271 sockAddrPtr = (CmInetSockAddr*)&addrs[0];
2272 sockAddrLen = sizeof(struct sockaddr_in);
2275 #ifdef IPV6_SUPPORTED
2278 sockAddrPtr = (CmInetSockAddr*)&addrs6[0];
2279 sockAddrLen = sizeof(struct sockaddr_in6);
2282 #endif/* IPV6_SUPPORTED */
2284 ret = connect(sockFd->fd, sockAddrPtr, sockAddrLen);
2286 #endif /* CMINET_SUN_CONNECTX */
2287 #endif /* SS_LINUX */
2289 if (ret == INET_ERR)
2293 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
2294 /* cm_inet_c_001.main_62:Warning fix */
2295 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "CmInetSctpConnectx() Failed : error(%d), port(0x%1x),"
2296 " sockFd->fd(%ld)\n", INET_ERR_CODE, port, sockFd->fd);
2297 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET010, 0, prntBuf);
2299 /* cm_inet_c_001.main_62:Warning fix */
2300 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "CmInetSctpConnectx() Failed : error(%d), port(0x%1x),"
2301 " sockFd->fd(%d)\n", INET_ERR_CODE, port, sockFd->fd);
2302 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET010, 0, prntBuf);
2303 #endif /*ALIGN_64BIT*/
2304 #endif /* CMINETDBG */
2306 switch (INET_ERR_CODE)
2308 /* non-blocking: connection is in progress */
2309 case ERR_INPROGRESS:
2310 RETVALUE(RINPROGRESS);
2314 * non-blocking: connection is established
2315 * blocking : connection is already established
2321 /* resource temporarily unavailable */
2322 case ERR_WOULDBLOCK:
2326 /* non-blocking: connection is in progress */
2328 RETVALUE(RINPROGRESS);
2332 RETVALUE(RINPROGRESS);
2335 /* Check for connection refused and timeout errors */
2336 case ERR_CONNREFUSED:
2341 /* it is a real error */
2353 * Fun: cmInetSctpPeelOff
2355 * Desc: Branches an existing sctp association off to a seperate socket
2357 * Ret: ROK - successful
2366 PUBLIC S16 cmInetSctpPeelOff
2368 CmInetFd *sockFd, /* socket file descriptor */
2369 U32 assocId, /* association id */
2370 CmInetFdType *assocFd /* association fd */
2373 PUBLIC S16 cmInetSctpPeelOff(sockFd, assocId, assocFd)
2374 CmInetFd *sockFd; /* socket file descriptor */
2375 U32 assocId; /* association id */
2376 CmInetFdType *assocFd; /* association fd */
2381 #if (ERRCLASS & ERRCLS_INT_PAR)
2382 /* error check on parameters */
2383 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) || (assocFd == NULLP))
2387 #endif /* ERRCLASS & ERRCLS_INT_PAR */
2390 ret = sctp_peeloff(sockFd->fd, assocId);
2391 if (ret == INET_ERR)
2395 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
2396 /* cm_inet_c_001.main_62:Warning fix */
2397 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpPeelOff() Failed : error(%d) assocId(%ld),"
2398 " sockFd->fd(%ld)\n", INET_ERR_CODE, assocId, sockFd->fd);
2399 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET011, 0, prntBuf);
2401 /* cm_inet_c_001.main_55: Fix for compilation warning */
2402 /* cm_inet_c_001.main_62:Warning fix */
2403 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpPeelOff() Failed : error(%d) assocId(%d),"
2404 " sockFd->fd(%d)\n", INET_ERR_CODE, assocId, sockFd->fd);
2405 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET011, 0, prntBuf);
2406 #endif /*ALIGN_64BIT*/
2407 #endif /* CMINETDBG */
2419 * Fun: cmInetSctpSendMsg
2421 * Desc: invokes sctp socket API to send message to the remote addresses
2423 * Ret: ROK - successful
2432 PUBLIC S16 cmInetSctpSendMsg
2434 CmInetFd *sockFd, /* socket file descriptor */
2435 CmInetNetAddr *dstAddr, /* destination Internet address/port */
2436 U16 port, /* destination port no. */
2437 CmInetMemInfo *info, /* buffer allocation info */
2438 Buffer *mBuf, /* buffer structure to send */
2439 MsgLen *len, /* number of actually sent octets */
2440 U16 strmId, /* sctp stream identifier */
2441 Bool unorderFlg, /* flag to enable the unordered delivery */
2442 U16 ttl, /* time to live */
2443 U32 ppId, /* opaque value passed along with the message */
2444 U32 context /* value to be passed back, if error occurs */
2447 PUBLIC S16 cmInetSctpSendMsg(sockFd, dstAddr, port, info, mBuf, len, strmId,
2448 unorderFlg, ttl, ppId, context)
2449 CmInetFd *sockFd; /* socket file descriptor */
2450 CmInetNetAddr *dstAddr; /* destination Internet address/port */
2451 U16 port; /* destination port no. */
2452 CmInetMemInfo *info; /* buffer allocation info */
2453 Buffer *mBuf; /* buffer structure to send */
2454 MsgLen *len; /* number of actually sent octets */
2455 U16 strmId; /* sctp stream identifier */
2456 Bool unorderFlg; /* flag to enable the unordered delivery */
2457 U16 ttl; /* time to live */
2458 U32 ppId; /* opaque value passed along with the message */
2459 U32 context; /* value to be passed back, if error occurs */
2463 /* cm_inet_c_001.main_58 : Fix for klockwork issue */
2464 MsgLen msgLen = 0; /* message length */
2465 MsgLen bufLen = 0; /* send buffer length */
2466 Data *sendBuf = NULLP; /* plain send buffer */
2468 CmInetSockAddr *sockAddrPtr = NULLP;
2469 /* cm_inet_c_001.main_58 : Fix for klockwork issue */
2470 MsgLen sockAddrLen = 0;
2471 struct sockaddr_in addr;
2472 #ifdef IPV6_SUPPORTED
2474 S8 *addrString = NULLP;
2476 S8 ipv4Format[23] = "::ffff:";
2477 CmInetIpAddr ipv4NetAddr;
2478 #endif /* SUN_KSCTP */
2479 struct sockaddr_in6 addr6;
2480 #endif /* IPV6_SUPPORTED */
2482 #if (ERRCLASS & ERRCLS_INT_PAR)
2483 /* error check on parameters */
2484 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd)
2485 || (info == NULLP) || (mBuf == NULLP) || (len == NULLP))
2489 #endif /* ERRCLASS & ERRCLS_INT_PAR */
2492 cmMemset((U8*)&addr, 0, sizeof(struct sockaddr_in));
2493 #ifdef IPV6_SUPPORTED
2494 cmMemset((U8*)&addr6, 0, sizeof(struct sockaddr_in6));
2495 #endif /* IPV6_SUPPORTED */
2497 /* copy message to a flat buffer */
2498 ret = SFndLenMsg(mBuf, &bufLen);
2503 /* max message length is limited to control the memory usage */
2504 /* casting bufLen to avoid warnings */
2505 if ((bufLen > 0) && ((U32)bufLen > CM_INET_MAX_MSG_LEN))
2509 ret = SGetSBuf(info->region, info->pool, &sendBuf, bufLen);
2514 ret = SCpyMsgFix(mBuf, 0, bufLen, sendBuf, &msgLen);
2515 if ((ret != ROK) || (msgLen != bufLen))
2517 SPutSBuf(info->region, info->pool, sendBuf, bufLen);
2521 if ( dstAddr != NULLP)
2523 #ifdef IPV6_SUPPORTED
2524 if (dstAddr->type == CM_INET_IPV6ADDR_TYPE)
2526 if (sockFd->protType == AF_INET)
2528 SPutSBuf(info->region, info->pool, sendBuf, bufLen);
2531 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
2532 /* cm_inet_c_001.main_62:Warning fix */
2533 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "Can't send message to IPV6 address through"
2534 " IPV4 socket, sockFd->fd(%ld)\n", sockFd->fd);
2535 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET012, 0, prntBuf);
2537 /* cm_inet_c_001.main_62:Warning fix */
2538 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "Can't send message to IPV6 address through"
2539 " IPV4 socket, sockFd->fd(%d)\n", sockFd->fd);
2540 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET012, 0, prntBuf);
2541 #endif /*ALIGN_64BIT*/
2542 #endif /* CMINETDBG */
2546 addr6.sin6_family = AF_INET6;
2547 addr6.sin6_port = CM_INET_HTON_U16(port);
2548 CM_INET_COPY_IPV6ADDR(&addr6.sin6_addr.s6_addr, &dstAddr->u.ipv6NetAddr);
2549 sockAddrLen = sizeof(struct sockaddr_in6);
2550 sockAddrPtr = (CmInetSockAddr*)&addr6;
2556 if (sockFd->protType == AF_INET)
2560 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
2561 /* cm_inet_c_001.main_62:Warning fix */
2562 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "can't connect to IPV6 address through IPV4"
2563 " socket, sockFd->fd(%ld)\n", sockFd->fd);
2564 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET064, 0, prntBuf);
2566 /* cm_inet_c_001.main_62:Warning fix */
2567 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "can't connect to IPV6 address through IPV4"
2568 " socket, sockFd->fd(%d)\n", sockFd->fd);
2569 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET064, 0, prntBuf);
2570 #endif /*ALIGN_64BIT*/
2571 #endif /* CMINETDBG */
2574 addr6.sin6_family = AF_INET6;
2575 addr6.sin6_port = CM_INET_HTON_U16(port);
2576 ipv4NetAddr = CM_INET_HTON_U32(dstAddr->u.ipv4NetAddr);
2577 cmInetNtoa(ipv4NetAddr, &addrString);
2578 addrLen = cmStrlen((U8*)addrString);
2579 cmMemcpy((U8*)(ipv4Format+7), (U8*)addrString, addrLen);
2580 ipv4Format[7+addrLen] = '\0';
2581 cmInetPton6((CmInetIpAddr6*)(addr6.sin6_addr.s6_addr), ipv4Format);
2582 sockAddrLen = sizeof(struct sockaddr_in6);
2583 sockAddrPtr = (CmInetSockAddr*)&addr6;
2585 addr.sin_family = AF_INET;
2586 addr.sin_port = CM_INET_HTON_U16(port);
2587 addr.sin_addr.s_addr = CM_INET_HTON_U32(dstAddr->u.ipv4NetAddr);
2588 sockAddrLen = sizeof(struct sockaddr_in);
2589 sockAddrPtr = (CmInetSockAddr*)&addr;
2590 #endif /* SUN_KSCTP */
2593 addr.sin_family = AF_INET;
2594 addr.sin_port = CM_INET_HTON_U16(port);
2595 addr.sin_addr.s_addr = CM_INET_HTON_U32(dstAddr->u.ipv4NetAddr);
2596 /* cm_inet_c_001.main_58 : Fix for Klockwork issue */
2597 sockAddrLen = (MsgLen)sizeof(struct sockaddr_in);
2598 sockAddrPtr = (CmInetSockAddr*)&addr;
2599 #endif /* IPV6_SUPPORTED */
2606 sockAddrPtr = (CmInetSockAddr*)&addr;
2608 /* cm_inet_c_001.main_58 : initialized sockAddrLen properly */
2609 #ifdef IPV6_SUPPORTED
2610 sockAddrLen = sizeof(struct sockaddr_in6);
2612 sockAddrLen = sizeof(struct sockaddr_in);
2616 /* Not validating the address, whether addr is a valid address or not */
2621 if (unorderFlg == TRUE)
2624 flags |= MSG_UNORDERED;
2627 flags |= SCTP_UNORDERED;
2630 /*cm_inet_c_001.main_54: converting ppid to network*/
2631 ppId = CM_INET_HTON_U32(ppId);
2632 ret = sctp_sendmsg(sockFd->fd, (Void*)sendBuf, bufLen,
2633 (struct sockaddr*)sockAddrPtr, (size_t)sockAddrLen,
2634 ppId, flags, strmId, ttl, context);
2635 if (ret == INET_ERR)
2637 SPutSBuf(info->region, info->pool, sendBuf, bufLen);
2640 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
2641 /* cm_inet_c_001.main_62:Warning fix */
2642 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpSendMsg() Failed : error(%d) ppId(%ld),"
2643 " strmId(%u),sockFd->fd(%ld)\n",
2644 INET_ERR_CODE, ppId, strmId, sockFd->fd);
2645 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET013, 0, prntBuf);
2647 /* cm_inet_c_001.main_55: Fix for compilation warning */
2648 /* cm_inet_c_001.main_62:Warning fix */
2649 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpSendMsg() Failed : error(%d) ppId(%d),"
2650 " strmId(%u),sockFd->fd(%d)\n",
2651 INET_ERR_CODE, ppId, strmId, sockFd->fd);
2652 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET013, 0, prntBuf);
2653 #endif /*ALIGN_64BIT*/
2654 #endif /* CMINETDBG */
2656 if ((INET_ERR_CODE == ERR_AGAIN) || (INET_ERR_CODE == ERR_WOULDBLOCK))
2657 RETVALUE(RWOULDBLOCK);
2658 else if (INET_ERR_CODE == ERR_PIPE)
2664 /* cm_inet_c_001.main_58 : Fix for klockwork issue */
2668 SPutSBuf(info->region, info->pool, sendBuf, bufLen);
2675 * Fun: cmInetSctpRecvMsg
2677 * Desc: invokes sctp API to get the message received at sctp socket
2679 * Ret: ROK - successful
2688 PUBLIC S16 cmInetSctpRecvMsg
2690 CmInetFd *sockFd, /* socket file descriptor */
2691 CmInetNetAddr *srcAddr, /* source Internet address/port */
2692 U16 *port, /* source port no. */
2693 CmInetMemInfo *meminfo, /* buffer allocation info */
2694 Buffer **mBuf, /* buffer structure received */
2695 MsgLen *len, /* number of octets received */
2696 CmInetSctpSndRcvInfo *sinfo, /* sctp send-receive info */
2697 U32 *flag, /* flags */
2698 CmInetSctpNotification *ntfy /* notification parameters */
2701 PUBLIC S16 cmInetSctpRecvMsg(sockFd, srcAddr, port, meminfo, mBuf, len,
2703 CmInetFd *sockFd; /* socket file descriptor */
2704 CmInetNetAddr *srcAddr; /* source Internet address/port */
2705 U16 *port; /* source port no. */
2706 CmInetMemInfo *meminfo; /* buffer allocation info */
2707 Buffer **mBuf; /* buffer structure received */
2708 MsgLen *len; /* number of octets received */
2709 CmInetSctpSndRcvInfo *sinfo; /* sctp send-receive info */
2710 U32 *flag; /* flags */
2711 CmInetSctpNotification *ntfy; /* notification parameters */
2716 struct sctp_sndrcvinfo info;
2717 struct sockaddr_storage addr;
2718 struct sockaddr_in *pAddr = NULLP;
2719 #ifdef IPV6_SUPPORTED
2720 struct sockaddr_in6 *pAddr6 = NULLP;
2723 Data *recvbuf = NULLP;
2725 union sctp_notification *sctpNtfy = NULLP;
2726 /* cm_inet_c_001.main_46: Defined new variable to store length of data */
2729 #endif /* SS_LINUX */
2731 #if (ERRCLASS & ERRCLS_INT_PAR)
2732 /* error check on parameters */
2733 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) ||
2734 (srcAddr == NULLP) || (port == NULLP) || (meminfo == NULLP) ||
2735 (mBuf == NULLP) || (len == NULLP) || (sinfo == NULLP) || (flag == NULLP))
2739 #endif /* ERRCLASS & ERRCLS_INT_PAR */
2744 cmMemset((U8*)ntfy, 0, sizeof(CmInetSctpNotification));
2746 buflen = CM_INET_MAX_MSG_LEN;
2748 /* allocate flat receive buffer */
2749 ret = SGetSBuf(meminfo->region, meminfo->pool, &recvbuf, buflen);
2753 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
2754 /* cm_inet_c_001.main_62:Warning fix */
2755 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "SGetSBuf failed to allocate memory\n");
2756 CMINETLOGERROR(ERRCLS_ADD_RES, ECMINET065, 0, prntBuf);
2757 #endif /* CMINETDBG */
2761 addrlen = sizeof(struct sockaddr_storage);
2763 cmMemset((U8*)&addr, 0, sizeof(struct sockaddr_storage));
2764 cmMemset((U8*)&info, 0, sizeof(struct sctp_sndrcvinfo));
2766 ret = sctp_recvmsg(sockFd->fd, (Void *)recvbuf, (size_t)buflen,
2767 (struct sockaddr*)&addr, &addrlen, &info,
2769 if (ret == INET_ERR)
2772 SPutSBuf(meminfo->region, meminfo->pool, recvbuf, buflen);
2775 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
2776 /* cm_inet_c_001.main_62:Warning fix */
2777 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpRecvMsg() Failed : error(%d),"
2778 " sockFd->fd(%ld)\n", INET_ERR_CODE, sockFd->fd);
2779 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET014, 0, prntBuf);
2781 /* cm_inet_c_001.main_62:Warning fix */
2782 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpRecvMsg() Failed : error(%d),"
2783 " sockFd->fd(%d)\n", INET_ERR_CODE, sockFd->fd);
2784 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET014, 0, prntBuf);
2785 #endif /*ALIGN_64BIT*/
2786 #endif /* CMINETDBG */
2791 /* save the length of the received message */
2792 /* cm_inet_c_001.main_58 : Fix for klockwork issue */
2795 #ifdef IPV6_SUPPORTED
2796 if (addr.ss_family == AF_INET6)
2798 U8 ipv4Format[12] = {0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0xff,0xff};
2799 pAddr6 = (struct sockaddr_in6*)&addr;
2800 *port = CM_INET_NTOH_U16(pAddr6->sin6_port);
2802 if((cmMemcmp(ipv4Format, pAddr6->sin6_addr.s6_addr, 12)) == 0)
2804 srcAddr->type = CM_INET_IPV4ADDR_TYPE;
2805 cmMemcpy((U8*)&srcAddr->u.ipv4NetAddr, (U8*)((pAddr6->sin6_addr.s6_addr) + 12), sizeof(U32));
2806 srcAddr->u.ipv4NetAddr = CM_INET_HTON_U32(srcAddr->u.ipv4NetAddr);
2811 srcAddr->type = CM_INET_IPV6ADDR_TYPE;
2812 CM_INET_COPY_IPV6ADDR(&srcAddr->u.ipv6NetAddr, &pAddr6->sin6_addr.s6_addr);
2817 pAddr = (struct sockaddr_in*)&addr;
2818 *port = CM_INET_NTOH_U16(pAddr->sin_port);
2819 srcAddr->type = CM_INET_IPV4ADDR_TYPE;
2820 srcAddr->u.ipv4NetAddr = CM_INET_NTOH_U32(pAddr->sin_addr.s_addr);
2823 pAddr = (struct sockaddr_in*)&addr;
2824 *port = CM_INET_NTOH_U16(pAddr->sin_port);
2825 srcAddr->type = CM_INET_IPV4ADDR_TYPE;
2826 srcAddr->u.ipv4NetAddr = CM_INET_NTOH_U32(pAddr->sin_addr.s_addr);
2827 #endif /* IPV6_SUPPORTED */
2829 /* fill sndrcv info */
2830 sinfo->stream = info.sinfo_stream;
2831 sinfo->ssn = info.sinfo_ssn;
2832 sinfo->flags = info.sinfo_flags;
2833 /*cm_inet_c_001.main_54: converting ppid to host*/
2834 sinfo->ppid = CM_INET_NTOH_U32(info.sinfo_ppid);
2835 sinfo->context = info.sinfo_context;
2836 sinfo->timetolive = info.sinfo_timetolive;
2837 sinfo->tsn = info.sinfo_tsn;
2838 sinfo->cumtsn = info.sinfo_cumtsn;
2839 sinfo->assocId = info.sinfo_assoc_id;
2841 /* fill message flags */
2843 if ((msgFlags & MSG_EOR) != 0)
2844 *flag |= CM_INET_SCTP_MSG_EOR;
2846 if ((msgFlags & MSG_NOTIFICATION) != 0)
2848 *flag |= CM_INET_SCTP_MSG_NOTIFICATION;
2851 sctpNtfy = (union sctp_notification*)recvbuf;
2853 ntfy->header.nFlags = sctpNtfy->sn_header.sn_flags;
2854 ntfy->header.nLen = sctpNtfy->sn_header.sn_length;
2856 switch(sctpNtfy->sn_header.sn_type)
2858 case SCTP_ASSOC_CHANGE:
2859 ntfy->header.nType = CM_INET_SCTP_ASSOC_CHANGE;
2860 switch(sctpNtfy->sn_assoc_change.sac_state)
2863 ntfy->u.assocChange.state = CM_INET_SCTP_COMM_UP;
2865 case SCTP_COMM_LOST:
2866 ntfy->u.assocChange.state = CM_INET_SCTP_COMM_LOST;
2869 ntfy->u.assocChange.state = CM_INET_SCTP_RESTART;
2871 case SCTP_SHUTDOWN_COMP:
2872 ntfy->u.assocChange.state = CM_INET_SCTP_SHUTDOWN_COMP;
2874 case SCTP_CANT_STR_ASSOC:
2875 ntfy->u.assocChange.state = CM_INET_SCTP_CANT_STR_ASSOC;
2880 ntfy->u.assocChange.error = sctpNtfy->sn_assoc_change.sac_error;
2881 ntfy->u.assocChange.outStreams = sctpNtfy->sn_assoc_change.sac_outbound_streams;
2882 ntfy->u.assocChange.inStreams = sctpNtfy->sn_assoc_change.sac_inbound_streams;
2883 ntfy->u.assocChange.assocId = sctpNtfy->sn_assoc_change.sac_assoc_id;
2885 ntfy->u.assocChange.info = sctpNtfy->sn_assoc_change.sac_info;
2888 case SCTP_PEER_ADDR_CHANGE:
2889 ntfy->header.nType = CM_INET_SCTP_PEER_ADDR_CHANGE;
2890 switch(sctpNtfy->sn_paddr_change.spc_state)
2892 case SCTP_ADDR_AVAILABLE:
2893 ntfy->u.paddrChange.state = CM_INET_SCTP_ADDR_AVAILABLE;
2895 case SCTP_ADDR_UNREACHABLE:
2896 ntfy->u.paddrChange.state = CM_INET_SCTP_ADDR_UNREACHABLE;
2898 case SCTP_ADDR_REMOVED:
2899 ntfy->u.paddrChange.state = CM_INET_SCTP_ADDR_REMOVED;
2901 case SCTP_ADDR_ADDED:
2902 ntfy->u.paddrChange.state = CM_INET_SCTP_ADDR_ADDED;
2904 case SCTP_ADDR_MADE_PRIM:
2905 ntfy->u.paddrChange.state = CM_INET_SCTP_ADDR_MADE_PRIM;
2908 case SCTP_ADDR_CONFIRMED:
2909 ntfy->u.paddrChange.state = CM_INET_SCTP_ADDR_CONFIRMED;
2916 #ifdef IPV6_SUPPORTED
2917 if (sctpNtfy->sn_paddr_change.spc_aaddr.ss_family == AF_INET6)
2919 pAddr6 = (struct sockaddr_in6*)&(sctpNtfy->sn_paddr_change.spc_aaddr);
2920 ntfy->u.paddrChange.addr.type = CM_INET_IPV6ADDR_TYPE;
2921 CM_INET_COPY_IPV6ADDR(&ntfy->u.paddrChange.addr.u.ipv6NetAddr,
2922 &pAddr6->sin6_addr.s6_addr);
2926 pAddr = (struct sockaddr_in*)&(sctpNtfy->sn_paddr_change.spc_aaddr);
2927 ntfy->u.paddrChange.addr.type = CM_INET_IPV4ADDR_TYPE;
2928 ntfy->u.paddrChange.addr.u.ipv4NetAddr = CM_INET_NTOH_U32(pAddr->sin_addr.s_addr);
2931 pAddr = (struct sockaddr_in*)&(sctpNtfy->sn_paddr_change.spc_aaddr);
2932 ntfy->u.paddrChange.addr.type = CM_INET_IPV4ADDR_TYPE;
2933 ntfy->u.paddrChange.addr.u.ipv4NetAddr = CM_INET_NTOH_U32(pAddr->sin_addr.s_addr);
2934 #endif /* IPV6_SUPPORTED */
2936 ntfy->u.paddrChange.error = sctpNtfy->sn_paddr_change.spc_error;
2937 ntfy->u.paddrChange.assocId = sctpNtfy->sn_paddr_change.spc_assoc_id;
2939 case SCTP_REMOTE_ERROR:
2940 ntfy->header.nType = CM_INET_SCTP_REMOTE_ERROR;
2942 ntfy->u.remoteErr.error = sctpNtfy->sn_remote_error.sre_error;
2943 ntfy->u.remoteErr.assocId = sctpNtfy->sn_remote_error.sre_assoc_id;
2945 /* cm_inet_c_001.main_46: Allocate memory for data before copying */
2946 datlen = cmStrlen(sctpNtfy->sn_remote_error.sre_data) + 1;
2948 ret = SGetSBuf( meminfo->region, meminfo->pool, \
2949 &ntfy->u.remoteErr.data, datlen );
2952 ntfy->u.remoteErr.data = NULLP;
2955 cmMemcpy(ntfy->u.remoteErr.data,\
2956 sctpNtfy->sn_remote_error.sre_data, datlen);
2959 case SCTP_SEND_FAILED:
2960 ntfy->header.nType = CM_INET_SCTP_SEND_FAILED;
2962 ntfy->u.sndFailed.error = sctpNtfy->sn_send_failed.ssf_error;
2963 ntfy->u.sndFailed.assocId = sctpNtfy->sn_send_failed.ssf_assoc_id;
2965 /* cm_inet_c_001.main_46: Allocate memory for data before copying */
2966 datlen = cmStrlen(sctpNtfy->sn_send_failed.ssf_data) + 1;
2968 ret = SGetSBuf( meminfo->region, meminfo->pool, \
2969 &ntfy->u.sndFailed.data, datlen );
2972 ntfy->u.sndFailed.data = NULLP;
2975 cmMemcpy(ntfy->u.sndFailed.data,\
2976 sctpNtfy->sn_send_failed.ssf_data, datlen );
2978 ntfy->u.sndFailed.info.stream = sctpNtfy->sn_send_failed.ssf_info.sinfo_stream;
2979 ntfy->u.sndFailed.info.ssn = sctpNtfy->sn_send_failed.ssf_info.sinfo_ssn;
2980 ntfy->u.sndFailed.info.flags = sctpNtfy->sn_send_failed.ssf_info.sinfo_flags;
2981 ntfy->u.sndFailed.info.ppid = sctpNtfy->sn_send_failed.ssf_info.sinfo_ppid;
2982 ntfy->u.sndFailed.info.context = sctpNtfy->sn_send_failed.ssf_info.sinfo_context;
2983 ntfy->u.sndFailed.info.timetolive = sctpNtfy->sn_send_failed.ssf_info.sinfo_timetolive;
2984 ntfy->u.sndFailed.info.tsn = sctpNtfy->sn_send_failed.ssf_info.sinfo_tsn;
2985 ntfy->u.sndFailed.info.cumtsn = sctpNtfy->sn_send_failed.ssf_info.sinfo_cumtsn;
2986 ntfy->u.sndFailed.info.assocId = sctpNtfy->sn_send_failed.ssf_info.sinfo_assoc_id;
2988 case SCTP_SHUTDOWN_EVENT:
2989 ntfy->header.nType = CM_INET_SCTP_SHUTDOWN_EVENT;
2991 ntfy->u.shutdownEvt.assocId = sctpNtfy->sn_shutdown_event.sse_assoc_id;
2994 case SCTP_ADAPTION_INDICATION :
2997 case SCTP_ADAPTATION_INDICATION :
2999 ntfy->header.nType = CM_INET_SCTP_ADAPTATION_INDICATION;
3002 ntfy->u.adaptationEvt.adaptationInd = sctpNtfy->sn_adaption_event.sai_adaption_ind;
3003 ntfy->u.adaptationEvt.assocId = sctpNtfy->sn_adaption_event.sai_assoc_id;
3006 ntfy->u.adaptationEvt.adaptationInd = sctpNtfy->sn_adaptation_event.sai_adaptation_ind;
3007 ntfy->u.adaptationEvt.assocId = sctpNtfy->sn_adaptation_event.sai_assoc_id;
3010 case SCTP_PARTIAL_DELIVERY_EVENT:
3011 ntfy->header.nType = CM_INET_SCTP_PARTIAL_DELIVERY_EVENT;
3013 ntfy->u.pdapiEvt.indication = sctpNtfy->sn_pdapi_event.pdapi_indication;
3014 ntfy->u.pdapiEvt.assocId = sctpNtfy->sn_pdapi_event.pdapi_assoc_id;
3022 /* get a message buffer */
3023 ret = SGetMsg(meminfo->region, meminfo->pool, mBuf);
3026 SPutSBuf(meminfo->region, meminfo->pool, recvbuf, buflen);
3030 ret = SAddPstMsgMult(recvbuf, *len, *mBuf);
3034 SPutSBuf(meminfo->region, meminfo->pool, recvbuf, buflen);
3040 SPutSBuf(meminfo->region, meminfo->pool, recvbuf, buflen);
3047 * Fun: cmInetSctpGetPAddrs
3049 * Desc: returns the list of peer addresses
3051 * Ret: ROK - successful
3060 PUBLIC S16 cmInetSctpGetPAddrs
3062 CmInetFd *sockFd, /* socket file descriptor */
3063 U32 assocId, /* association id */
3064 CmInetNetAddrLst *addrlst /* peer address list */
3067 PUBLIC S16 cmInetSctpGetPAddrs(sockFd, assocId, addrlst)
3068 CmInetFd *sockFd; /* socket file descriptor */
3069 U32 assocId; /* association id */
3070 CmInetNetAddrLst *addrlst; /* peer address list */
3073 /* cm_inet_c_001.main_58 : Fix for Klockwork issue */
3077 struct sockaddr *peerAddrList;
3078 struct sockaddr_in *pAddr;
3079 #ifdef IPV6_SUPPORTED
3080 struct sockaddr_in6 *pAddr6;
3081 #endif /* IPV6_SUPPORTED */
3084 if((cnt = sctp_getpaddrs(sockFd->fd, assocId, (Void**)&peerAddrList)) == -1)
3086 if((cnt = sctp_getpaddrs(sockFd->fd, assocId, &peerAddrList)) == -1)
3091 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
3092 /* cm_inet_c_001.main_62:Warning fix */
3093 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpGetPAddrs() Failed : error(%d),"
3094 " sockFd->fd(%ld), assocId(%ld)\n",
3095 INET_ERR_CODE, sockFd->fd, assocId);
3096 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET015, 0, prntBuf);
3098 /* cm_inet_c_001.main_55: Fix for compilation warning */
3099 /* cm_inet_c_001.main_62:Warning fix */
3100 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSctpGetPAddrs() Failed : error(%d),"
3101 " sockFd->fd(%d),assocId(%d)\n",
3102 INET_ERR_CODE, sockFd->fd, assocId);
3103 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET015, 0, prntBuf);
3104 #endif /*ALIGN_64BIT*/
3105 #endif /* CMINETDBG */
3110 byteAddress = (U8*)peerAddrList;
3111 for (idx = 0; idx < cnt; idx++)
3113 #ifdef IPV6_SUPPORTED
3115 if (((struct sockaddr*)byteAddress)->sa_family == AF_INET6)
3117 if (sockFd->protType == AF_INET)
3121 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
3122 sprintf(prntBuf, "cmInetSctpGetPAddrs() Failed : Invalid address"
3123 " sockFd->fd(%ld)", sockFd->fd);
3124 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET016, 0, prntBuf);
3126 sprintf(prntBuf, "cmInetSctpGetPAddrs() Failed : Invalid address"
3127 " sockFd->fd(%d)", sockFd->fd);
3128 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET016, 0, prntBuf);
3129 #endif /*ALIGN_64BIT*/
3130 #endif /* CMINETDBG */
3132 sctp_freepaddrs(peerAddrList);
3136 pAddr6 = (struct sockaddr_in6*)byteAddress;
3138 addrlst->addrs[idx].type = CM_INET_IPV6ADDR_TYPE;
3139 CM_INET_COPY_IPV6ADDR(&(addrlst->addrs[idx].u.ipv6NetAddr), &(pAddr6->sin6_addr.s6_addr));
3140 byteAddress += sizeof(struct sockaddr_in6);
3144 pAddr = (struct sockaddr_in*)byteAddress;
3145 addrlst->addrs[idx].type = CM_INET_IPV4ADDR_TYPE;
3146 addrlst->addrs[idx].u.ipv4NetAddr = CM_INET_NTOH_U32(pAddr->sin_addr.s_addr);
3147 byteAddress += sizeof(struct sockaddr_in);
3150 pAddr = (struct sockaddr_in*)byteAddress;
3151 addrlst->addrs[idx].type = CM_INET_IPV4ADDR_TYPE;
3152 addrlst->addrs[idx].u.ipv4NetAddr = CM_INET_NTOH_U32(pAddr->sin_addr.s_addr);
3153 byteAddress += sizeof(struct sockaddr_in);
3154 #endif /* IPV6_SUPPORTED */
3157 /* cm_inet_c_001.main_58 : Fix for klockwork issue */
3158 addrlst->count = (U8)cnt;
3160 sctp_freepaddrs(peerAddrList);
3169 * Desc: invokes socket API to retrive specified socket options
3171 * Ret: ROK - successful
3180 PUBLIC S16 cmInetGetOpt
3182 CmInetFd *sockFd, /* socket file descriptor */
3183 U32 level, /* option level */
3184 U32 type, /* option type */
3185 Ptr value /* option value */
3188 PUBLIC S16 cmInetGetOpt(sockFd, level, type, value)
3189 CmInetFd *sockFd; /* socket file descriptor */
3190 U32 level; /* option level */
3191 U32 type; /* option type */
3192 Ptr value; /* option value */
3196 struct sctp_status status;
3197 struct sctp_paddrinfo addrInfo;
3198 struct sockaddr_in *pAddr;
3199 #ifdef IPV6_SUPPORTED
3200 struct sockaddr_in6 *pAddr6;
3201 #endif /* IPV6_SUPPORTED */
3202 struct sctp_assocparams assocParams;
3203 /*cm_inet_c_001.main_40 Updated for the support of configurable RTO parameters,
3204 HBeat value Max retransmissions (Init, Path, Association)*/
3205 struct sctp_initmsg initMsg;
3206 struct sctp_rtoinfo rtoInfo;
3207 struct sctp_paddrparams addrParams;
3208 CmInetSctpStatus *pSctpStatus;
3209 CmInetSctpPeerAddrInfo *pPeerAddrInfo;
3210 CmInetSctpInitMsg *pInitMsg;
3211 CmInetSctpAssocParams *pAssocParams;
3212 CmInetSctpRtoInfo *pRtoInfo;
3213 CmInetSctpPeerAddrParams *pPeerAddrParams;
3214 /*cm_inet_c_001.main_58 : fix for klockwork issue */
3219 #if (ERRCLASS & ERRCLS_INT_PAR)
3220 /* error check on parameters */
3221 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd))
3225 #endif /* ERRCLASS & ERRCLS_INT_PAR */
3229 case CM_INET_OPT_SCTP_GET_ASSOC_STA:
3230 pSctpStatus = (CmInetSctpStatus*)value;
3231 cmMemset((U8*)&status, 0, sizeof(struct sctp_status));
3232 len = sizeof(status);
3233 status.sstat_assoc_id = pSctpStatus->assocId;
3235 ret = getsockopt(sockFd->fd, level, SCTP_STATUS, &status, &len);
3237 pSctpStatus->rwnd = status.sstat_rwnd;
3238 pSctpStatus->unackdata = status.sstat_unackdata;
3239 pSctpStatus->penddata = status.sstat_penddata;
3240 pSctpStatus->instrms = status.sstat_instrms;
3241 pSctpStatus->outstrms = status.sstat_outstrms;
3242 pSctpStatus->fragPoint = status.sstat_fragmentation_point;
3244 switch (status.sstat_state)
3254 pSctpStatus->state = CM_INET_SCTP_STA_EMPTY;
3261 pSctpStatus->state = CM_INET_SCTP_STA_CLOSED;
3267 case SCTPS_COOKIE_WAIT:
3269 case SCTP_COOKIE_WAIT:
3272 pSctpStatus->state = CM_INET_SCTP_STA_COOKIE_WAIT;
3277 case SCTPS_COOKIE_ECHOED:
3279 case SCTP_COOKIE_ECHOED:
3282 pSctpStatus->state = CM_INET_SCTP_STA_COOKIE_ECHOED;
3287 case SCTPS_ESTABLISHED:
3289 case SCTP_ESTABLISHED:
3292 pSctpStatus->state = CM_INET_SCTP_STA_ESTABLISHED;
3297 case SCTPS_SHUTDOWN_PENDING:
3299 case SCTP_SHUTDOWN_PENDING:
3302 pSctpStatus->state = CM_INET_SCTP_STA_SHUTDOWN_PENDING;
3307 case SCTPS_SHUTDOWN_SENT:
3309 case SCTP_SHUTDOWN_SENT:
3312 pSctpStatus->state = CM_INET_SCTP_STA_SHUTDOWN_SENT;
3317 case SCTPS_SHUTDOWN_RECEIVED:
3319 case SCTP_SHUTDOWN_RECEIVED:
3322 pSctpStatus->state = CM_INET_SCTP_STA_SHUTDOWN_RECEIVED;
3327 case SCTPS_SHUTDOWN_ACK_SENT:
3329 case SCTP_SHUTDOWN_ACK_SENT:
3332 pSctpStatus->state = CM_INET_SCTP_STA_SHUTDOWN_ACK_SENT;
3343 #ifdef IPV6_SUPPORTED
3344 if (status.sstat_primary.spinfo_address.ss_family == AF_INET6)
3346 pAddr6 = (struct sockaddr_in6*)&(status.sstat_primary.spinfo_address);
3347 pSctpStatus->primary.port = CM_INET_NTOH_U16(pAddr6->sin6_port);
3349 pSctpStatus->primary.addr.type = CM_INET_IPV6ADDR_TYPE;
3350 CM_INET_COPY_IPV6ADDR(&pSctpStatus->primary.addr.u.ipv6NetAddr,
3351 &pAddr6->sin6_addr.s6_addr);
3355 pAddr = (struct sockaddr_in*)&(status.sstat_primary.spinfo_address);
3356 pSctpStatus->primary.port = CM_INET_NTOH_U16(pAddr->sin_port);
3357 pSctpStatus->primary.addr.type = CM_INET_IPV4ADDR_TYPE;
3358 pSctpStatus->primary.addr.u.ipv4NetAddr = CM_INET_NTOH_U32(pAddr->sin_addr.s_addr);
3361 pAddr = (struct sockaddr_in*)&(status.sstat_primary.spinfo_address);
3362 pSctpStatus->primary.port = CM_INET_NTOH_U16(pAddr->sin_port);
3363 pSctpStatus->primary.addr.type = CM_INET_IPV4ADDR_TYPE;
3364 pSctpStatus->primary.addr.u.ipv4NetAddr = CM_INET_NTOH_U32(pAddr->sin_addr.s_addr);
3365 #endif /* IPV6_SUPPORTED */
3367 pSctpStatus->primary.assocId = status.sstat_primary.spinfo_assoc_id;
3368 if (status.sstat_primary.spinfo_state == SCTP_ACTIVE)
3369 pSctpStatus->primary.isActive = TRUE;
3371 pSctpStatus->primary.isActive = FALSE;
3372 pSctpStatus->primary.cwnd = status.sstat_primary.spinfo_cwnd;
3373 pSctpStatus->primary.srtt = status.sstat_primary.spinfo_srtt;
3374 pSctpStatus->primary.rto = status.sstat_primary.spinfo_rto;
3375 pSctpStatus->primary.mtu = status.sstat_primary.spinfo_mtu;
3378 case CM_INET_OPT_SCTP_GET_PADDR_INFO:
3379 pPeerAddrInfo = (CmInetSctpPeerAddrInfo*)value;
3380 cmMemset((U8*)&addrInfo, 0, sizeof(struct sctp_paddrinfo));
3381 len = sizeof(addrInfo);
3382 addrInfo.spinfo_assoc_id = pPeerAddrInfo->assocId;
3384 #ifdef IPV6_SUPPORTED
3385 if (pPeerAddrInfo->addr.type == CM_INET_IPV6ADDR_TYPE)
3387 if (sockFd->protType == AF_INET)
3391 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
3392 /* cm_inet_c_001.main_62:Warning fix */
3393 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetGetOpt() Failed : Invalid address,"
3394 " sockFd->fd(%ld)\n", sockFd->fd);
3395 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET017, 0, prntBuf);
3397 /* cm_inet_c_001.main_62:Warning fix */
3398 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetGetOpt() Failed : Invalid address,"
3399 " sockFd->fd(%d)\n", sockFd->fd);
3400 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET017, 0, prntBuf);
3401 #endif /*ALIGN_64BIT*/
3402 #endif /* CMINETDBG */
3406 pAddr6 = (struct sockaddr_in6*)&(addrInfo.spinfo_address);
3407 pAddr6->sin6_family = AF_INET6;
3408 pAddr6->sin6_port = CM_INET_HTON_U16(pPeerAddrInfo->port);
3409 CM_INET_COPY_IPV6ADDR(&pAddr6->sin6_addr.s6_addr, &pPeerAddrInfo->addr.u.ipv6NetAddr);
3413 pAddr = (struct sockaddr_in*)&(addrInfo.spinfo_address);
3414 pAddr->sin_family = AF_INET;
3415 pAddr->sin_port = CM_INET_HTON_U16(pPeerAddrInfo->port);
3416 pAddr->sin_addr.s_addr = CM_INET_HTON_U32(pPeerAddrInfo->addr.u.ipv4NetAddr);
3419 pAddr = (struct sockaddr_in*)&(addrInfo.spinfo_address);
3420 pAddr->sin_family = AF_INET;
3421 pAddr->sin_port = CM_INET_HTON_U16(pPeerAddrInfo->port);
3422 pAddr->sin_addr.s_addr = CM_INET_HTON_U32(pPeerAddrInfo->addr.u.ipv4NetAddr);
3423 #endif /* IPV6_SUPPORTED */
3425 /* Not validating the address, whether Addr is a valid address or not */
3427 ret = getsockopt(sockFd->fd, level, SCTP_GET_PEER_ADDR_INFO, &addrInfo, &len);
3429 if (addrInfo.spinfo_state == SCTP_ACTIVE)
3430 pPeerAddrInfo->isActive = TRUE;
3432 pPeerAddrInfo->isActive = FALSE;
3433 pPeerAddrInfo->cwnd = addrInfo.spinfo_cwnd;
3434 pPeerAddrInfo->srtt = addrInfo.spinfo_srtt;
3435 pPeerAddrInfo->rto = addrInfo.spinfo_rto;
3436 pPeerAddrInfo->mtu = addrInfo.spinfo_mtu;
3439 case CM_INET_OPT_SCTP_PEERADDR_PARAMS:
3441 pPeerAddrParams = (CmInetSctpPeerAddrParams *)value;
3443 cmMemset((U8*)&addrParams, 0, sizeof(struct sctp_paddrparams));
3445 addrParams.spp_assoc_id = pPeerAddrParams->assocId;
3447 if (pPeerAddrParams->s.addrPres == TRUE)
3449 #ifdef IPV6_SUPPORTED
3450 if (pPeerAddrParams->s.addr.type == CM_INET_IPV6ADDR_TYPE)
3452 if (sockFd->protType == AF_INET)
3456 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
3457 /* cm_inet_c_001.main_62:Warning fix */
3458 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "invalid address line:sockFd->fd(%ld)\n",
3460 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET066, 0, prntBuf);
3462 /* cm_inet_c_001.main_62:Warning fix */
3463 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "invalid address line:sockFd->fd(%d)\n",
3465 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET066, 0, prntBuf);
3466 #endif /*ALIGN_64BIT*/
3467 #endif /* CMINETDBG */
3471 pAddr6 = (struct sockaddr_in6*)&(addrParams.spp_address);
3472 pAddr6->sin6_family = AF_INET6;
3473 pAddr6->sin6_port = CM_INET_HTON_U16(pPeerAddrParams->s.port);
3474 CM_INET_COPY_IPV6ADDR(&pAddr6->sin6_addr.s6_addr, &pPeerAddrParams->s.addr.u.ipv6NetAddr);
3478 pAddr = (struct sockaddr_in*)&(addrParams.spp_address);
3479 pAddr->sin_family = AF_INET;
3480 pAddr->sin_port = CM_INET_HTON_U16(pPeerAddrParams->s.port);
3481 pAddr->sin_addr.s_addr = CM_INET_HTON_U32(pPeerAddrParams->s.addr.u.ipv4NetAddr);
3484 pAddr = (struct sockaddr_in*)&(addrParams.spp_address);
3485 pAddr->sin_family = AF_INET;
3486 pAddr->sin_port = CM_INET_HTON_U16(pPeerAddrParams->s.port);
3487 pAddr->sin_addr.s_addr = CM_INET_HTON_U32(pPeerAddrParams->s.addr.u.ipv4NetAddr);
3488 #endif /* IPV6_SUPPORTED */
3492 #ifdef IPV6_SUPPORTED
3493 if (sockFd->protType == AF_INET6)
3494 addrParams.spp_address.ss_family = AF_INET6;
3496 addrParams.spp_address.ss_family = AF_INET;
3498 addrParams.spp_address.ss_family = AF_INET;
3502 len = sizeof(addrParams);
3504 ret = getsockopt(sockFd->fd, level, SCTP_PEER_ADDR_PARAMS, &addrParams, &len);
3505 /* cm_inet_c_001.main_41 : Fixed the Solaris compilation problem */
3508 pPeerAddrParams->hbInterval = addrParams.spp_hbinterval;
3509 pPeerAddrParams->pathMaxRxt = addrParams.spp_pathmaxrxt;
3510 pPeerAddrParams->assocId = addrParams.spp_assoc_id;
3511 pPeerAddrParams->pathMtu = addrParams.spp_pathmtu;
3512 pPeerAddrParams->sackDelay = addrParams.spp_sackdelay;
3514 if (addrParams.spp_flags & SPP_HB_ENABLE)
3515 pPeerAddrParams->hbEnblFlag = CM_INET_OPT_ENABLE;
3517 pPeerAddrParams->hbEnblFlag = CM_INET_OPT_DISABLE;
3519 if (addrParams.spp_flags & SPP_PMTUD_ENABLE)
3520 pPeerAddrParams->pmtudFlag = CM_INET_OPT_ENABLE;
3522 pPeerAddrParams->pmtudFlag = CM_INET_OPT_DISABLE;
3524 if (addrParams.spp_flags & SPP_SACKDELAY_ENABLE)
3525 pPeerAddrParams->sackDelayFlag = CM_INET_OPT_ENABLE;
3527 pPeerAddrParams->sackDelayFlag = CM_INET_OPT_DISABLE;
3532 case CM_INET_OPT_SCTP_ASSOC_PARAMS:
3534 pAssocParams = (CmInetSctpAssocParams *)value;
3536 cmMemset((U8*)&assocParams, 0, sizeof(struct sctp_assocparams));
3538 assocParams.sasoc_assoc_id = pAssocParams->assocId;
3540 len = sizeof(assocParams);
3542 ret = getsockopt(sockFd->fd, level, SCTP_ASSOCINFO, &assocParams, &len);
3544 pAssocParams->assocMaxReTx = assocParams.sasoc_asocmaxrxt;
3545 pAssocParams->cookieLife = assocParams.sasoc_cookie_life;
3546 pAssocParams->assocId = assocParams.sasoc_assoc_id;
3547 pAssocParams->numberOfPeerDest = assocParams.sasoc_number_peer_destinations;
3548 pAssocParams->peerRwnd = assocParams.sasoc_peer_rwnd;
3549 pAssocParams->localRwnd = assocParams.sasoc_local_rwnd;
3553 case CM_INET_OPT_SCTP_RTO_INFO:
3555 pRtoInfo = (CmInetSctpRtoInfo *)value;
3557 cmMemset((U8*)&rtoInfo, 0, sizeof(struct sctp_rtoinfo));
3559 len = sizeof(rtoInfo);
3561 ret = getsockopt(sockFd->fd, level, SCTP_RTOINFO, &rtoInfo, &len);
3563 pRtoInfo->assocId = rtoInfo.srto_assoc_id;
3564 pRtoInfo->rtoInitial = rtoInfo.srto_initial;
3565 pRtoInfo->rtoMax = rtoInfo.srto_max;
3566 pRtoInfo->rtoMin = rtoInfo.srto_min;
3570 case CM_INET_OPT_SCTP_INIT_MSG:
3572 pInitMsg = (CmInetSctpInitMsg *)value;
3574 cmMemset((U8*)&initMsg, 0, sizeof(struct sctp_initmsg));
3576 len = sizeof(initMsg);
3578 ret = getsockopt(sockFd->fd, level, SCTP_INITMSG, &initMsg, &len);
3580 pInitMsg->maxInitReTx = initMsg.sinit_max_attempts;
3581 pInitMsg->maxInitTimeout = initMsg.sinit_max_init_timeo;
3582 pInitMsg->numOstreams = initMsg.sinit_num_ostreams;
3583 pInitMsg->maxInstreams = initMsg.sinit_max_instreams;
3591 if (ret == INET_ERR)
3595 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
3596 /* cm_inet_c_001.main_62:Warning fix */
3597 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetGetOpt() failed on line:"
3598 " error(%d), sockFd->fd(%ld)\n", INET_ERR_CODE, sockFd->fd);
3599 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET067, 0, prntBuf);
3601 /* cm_inet_c_001.main_62:Warning fix */
3602 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetGetOpt() failed on line:"
3603 " error(%d), sockFd->fd(%d)\n", INET_ERR_CODE, sockFd->fd);
3604 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET067, 0, prntBuf);
3605 #endif /*ALIGN_64BIT*/
3606 #endif /* CMINETDBG */
3613 /* cm_inet_c_001.main_54: Added new function cmInetShutDownSctp()*/
3616 * Fun: cmInetShutDownSctp
3618 * Desc: Shutdown the SCTP association gracefully.
3620 * Ret: ROK - successful
3629 PUBLIC S16 cmInetShutDownSctp
3631 CmInetFd *sockFd /* socket file descriptor */
3634 PUBLIC S16 cmInetShutDownSctp(sockFd)
3635 CmInetFd *sockFd; /* socket file descriptor */
3638 /*cm_inet_c_001.main_58 : fix for klockwork issue */
3640 struct sctp_sndrcvinfo sndRcvInfo;
3642 TRC2(cmInetShutDownSctp);
3644 cmMemset((U8*)&sndRcvInfo, 0, sizeof(sndRcvInfo));
3647 sndRcvInfo.sinfo_flags = MSG_EOF;
3649 sndRcvInfo.sinfo_flags = SCTP_EOF;
3652 /* Call the sctp_send with flag set to termiante the association */
3654 ret = sctp_send(sockFd->fd, NULLP, 0, &sndRcvInfo, sndRcvInfo.sinfo_flags);
3660 /* cm_inet_c_001.main_62:Warning fix */
3661 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetShutDownSctp() Failed : error(%d), sockFd->fd(%ld)\n",
3662 INET_ERR_CODE, sockFd->fd);
3663 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET018, 0, prntBuf);
3665 /* cm_inet_c_001.main_62:Warning fix */
3666 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetShutDownSctp() Failed : error(%d), sockFd->fd(%d)\n",
3667 INET_ERR_CODE, sockFd->fd);
3668 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET018, 0, prntBuf);
3669 #endif /*ALIGN_64BIT*/
3670 #endif /* CMINETDBG */
3678 /* cm_inet_c_001.main_61: Added new function cmInetAbortSctpAssoc()*/
3681 * Fun: cmInetAbortSctpAssoc
3683 * Desc: ABORT the association.
3685 * Ret: ROK - successful
3694 PUBLIC S16 cmInetAbortSctpAssoc
3696 CmInetFd *sockFd, /* socket file descriptor */
3697 UConnId assocId /* Association ID */
3700 PUBLIC S16 cmInetAbortSctpAssoc(sockFd, assocId)
3701 CmInetFd *sockFd; /* socket file descriptor */
3702 UConnId assocId; /* Association ID */
3706 struct sctp_sndrcvinfo sndRcvInfo;
3708 TRC2(cmInetAbortSctpAssoc);
3710 cmMemset((U8*)&sndRcvInfo, 0, sizeof(sndRcvInfo));
3713 sndRcvInfo.sinfo_flags = MSG_ABORT;
3715 sndRcvInfo.sinfo_flags = SCTP_ABORT;
3718 sndRcvInfo.sinfo_assoc_id = assocId;
3720 /* Call the sctp_send with flag set to termiante the association */
3722 ret = sctp_send(sockFd->fd, NULLP, 0, &sndRcvInfo, sndRcvInfo.sinfo_flags);
3728 /* cm_inet_c_001.main_62:Warning fix */
3729 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetAbortSctpAssoc() Failed : error(%d), sockFd->fd(%ld)\n",
3730 INET_ERR_CODE, sockFd->fd);
3731 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET018, 0, prntBuf);
3733 /* cm_inet_c_001.main_62:Warning fix */
3734 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetAbortSctpAssoc() Failed : error(%d), sockFd->fd(%d)\n",
3735 INET_ERR_CODE, sockFd->fd);
3736 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET018, 0, prntBuf);
3737 #endif /*ALIGN_64BIT*/
3738 #endif /* CMINETDBG */
3751 * Fun: cmInetConnect
3753 * Desc: Establishs a connection to a foreign address (TCP) or associates
3754 * a UDP socket to a foreign address.
3756 * Ret: ROK - successful
3757 * ROKDNA - resource temporarily unavaiable
3758 * RINPROGRESS - connection is in progress (only non-blocking)
3759 * RISCONN - connection is established (only non-blocking)
3769 PUBLIC S16 cmInetConnect
3771 CmInetFd *sockFd, /* socket file descriptor */
3772 CmInetAddr *servAddr /* foreign Internet address/port */
3775 PUBLIC S16 cmInetConnect(sockFd, servAddr)
3776 CmInetFd *sockFd; /* socket file descriptor */
3777 CmInetAddr *servAddr; /* foreign Internet address/port */
3780 S32 ret; /* temporary return value */
3781 struct sockaddr_in dstAddr; /* foreign Internet address/port */
3782 #ifdef IPV6_SUPPORTED
3783 struct sockaddr_in6 dstAddr6; /* foreign Internet IPV6 address/port */
3786 #endif /* CMINETDBG */
3787 #endif /* IPV6_SUPPORTED */
3789 CmInetSockAddr *sockAddrPtr;
3791 TRC2(cmInetConnect);
3793 #if (ERRCLASS & ERRCLS_INT_PAR)
3794 /* error check on parameters */
3795 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) ||
3796 (servAddr == NULLP))
3800 #endif /* ERRCLASS & ERRCLS_INT_PAR */
3802 #ifdef IPV6_SUPPORTED
3803 if (servAddr->type == CM_INET_IPV6ADDR_TYPE)
3805 cmMemset((U8*)&dstAddr6, 0, sizeof(dstAddr6));
3806 dstAddr6.sin6_family = AF_INET6;
3807 dstAddr6.sin6_port = CM_INET_HTON_U16(servAddr->u.ipv6Addr.port);
3808 CM_INET_COPY_IPV6ADDR(&dstAddr6.sin6_addr,
3809 &servAddr->u.ipv6Addr.ipv6NetAddr);
3810 sizeOfAddr = sizeof(struct sockaddr_in6);
3811 sockAddrPtr = (CmInetSockAddr *)&dstAddr6;
3815 cmMemset((U8*)&dstAddr, 0, sizeof(dstAddr));
3816 dstAddr.sin_family = AF_INET;
3817 dstAddr.sin_port = CM_INET_HTON_U16(servAddr->u.ipv4Addr.port);
3818 dstAddr.sin_addr.s_addr = CM_INET_HTON_U32(servAddr->u.ipv4Addr.address);
3819 sizeOfAddr = sizeof(struct sockaddr_in);
3820 sockAddrPtr = (CmInetSockAddr *)&dstAddr;
3823 cmMemset((U8*)&dstAddr, 0, sizeof(dstAddr));
3824 dstAddr.sin_family = AF_INET;
3825 dstAddr.sin_port = CM_INET_HTON_U16(servAddr->port);
3826 dstAddr.sin_addr.s_addr = CM_INET_HTON_U32(servAddr->address);
3827 sizeOfAddr = sizeof(struct sockaddr_in);
3828 sockAddrPtr = (CmInetSockAddr *)&dstAddr;
3829 #endif /* IPV6_SUPPORTED */
3831 ret = connect(sockFd->fd, sockAddrPtr, sizeOfAddr);
3832 if (ret == INET_ERR)
3834 switch (INET_ERR_CODE)
3836 /* non-blocking: connection is in progress */
3837 case ERR_INPROGRESS:
3838 RETVALUE(RINPROGRESS);
3842 * non-blocking: connection is established
3843 * blocking : connection is already established
3849 /* resource temporarily unavailable */
3850 case ERR_WOULDBLOCK:
3854 /* non-blocking: connection is in progress */
3856 RETVALUE(RINPROGRESS);
3860 RETVALUE(RINPROGRESS);
3863 /* Check for connection refused and timeout errors */
3864 case ERR_CONNREFUSED:
3869 /* it is a real error */
3872 #ifdef IPV6_SUPPORTED
3873 if (servAddr->type == CM_INET_IPV6ADDR_TYPE)
3874 port = servAddr->u.ipv6Addr.port;
3876 port = servAddr->u.ipv4Addr.port;
3878 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
3880 /* cm_inet_c_001.main_62:Warning fix */
3881 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetConnect() Failed : error(%d),"
3882 " addrtype(0x%x), port(0x%1x), sockFd->fd(%ld)\n",
3883 INET_ERR_CODE, servAddr->type, port, sockFd->fd);
3884 CMINETLOGERROR(ERRCLS_ADD_RES, ECMINET019, 0, prntBuf);
3886 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetConnect() Failed : error(%d),"
3887 " addrtype(0x%x), port(0x%1x), sockFd->fd(%d)\n",
3888 INET_ERR_CODE, servAddr->type, port, sockFd->fd);
3889 CMINETLOGERROR(ERRCLS_ADD_RES, ECMINET019, 0, prntBuf);
3890 #endif /*ALIGN_64BIT*/
3893 /* cm_inet_c_001.main_62:Warning fix */
3894 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetConnect() Failed : error(%d), addr(0x%lx),"
3895 "port(0x%1x), sockFd->fd(%ld)\n", INET_ERR_CODE ,
3896 servAddr->address, servAddr->port, sockFd->fd);
3897 CMINETLOGERROR(ERRCLS_ADD_RES, ECMINET020, 0, prntBuf);
3899 /* cm_inet_c_001.main_62:Warning fix */
3900 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetConnect() Failed : error(%d), addr(0x%x),"
3901 "port(0x%x), sockFd->fd(%d)\n", INET_ERR_CODE ,
3902 servAddr->address, servAddr->port, sockFd->fd);
3903 CMINETLOGERROR(ERRCLS_ADD_RES, ECMINET020, 0, prntBuf);
3904 #endif /*ALIGN_64BIT*/
3905 #endif /* IPV6_SUPPORTED */
3906 #endif /* CMINETDBG */
3913 } /* end of cmInetConnect */
3920 * Desc: Indicates the willingness of a socket to listen for incomming
3921 * connection requests.
3923 * Ret: ROK - successful
3926 * Notes: The backLog value has to be within 0..5
3933 PUBLIC S16 cmInetListen
3935 CmInetFd *sockFd, /* socket file descriptor */
3936 S16 backLog /* max. number of outstandig connections 0..5 */
3939 PUBLIC S16 cmInetListen(sockFd, backLog)
3940 CmInetFd *sockFd; /* socket file descriptor */
3941 S16 backLog; /* max. number of outstandig connections 0..5 */
3944 S32 ret; /* temporary return value */
3948 #if (ERRCLASS & ERRCLS_INT_PAR)
3949 /* error check on parameters */
3950 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) ||
3951 (backLog < MIN_BACK_LOG) || (backLog > MAX_BACK_LOG))
3955 #endif /* ERRCLASS & ERRCLS_INT_PAR */
3957 ret = listen(sockFd->fd, backLog);
3958 if (ret == INET_ERR)
3962 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
3963 /* cm_inet_c_001.main_62:Warning fix */
3964 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetListen() Failed : error(%d), backLog(%d),"
3965 " sockFd->fd(%ld)\n", INET_ERR_CODE, backLog, sockFd->fd);
3966 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET021, 0, prntBuf);
3968 /* cm_inet_c_001.main_62:Warning fix */
3969 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetListen() Failed : error(%d), backLog(%d),"
3970 " sockFd->fd(%d)\n", INET_ERR_CODE, backLog, sockFd->fd);
3971 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET021, 0, prntBuf);
3972 #endif /*ALIGN_64BIT*/
3973 #endif /* CMINETDBG */
3978 } /* end of cmInetListen */
3985 * Desc: Accepts an incoming connection.
3986 * On default the new socket is non-blocking. The options can be
3987 * changed with the function cmInetSetOpt().
3989 * Ret: ROK - successful
3990 * ROKDNA - there is no connection present to accept (only
4001 PUBLIC S16 cmInetAccept
4003 CmInetFd *sockFd, /* socket file descriptor */
4004 CmInetAddr *fromAddr, /* calling Internet address/port */
4005 CmInetFd *newSockFd /* socket file descriptor for new connection*/
4008 PUBLIC S16 cmInetAccept(sockFd, fromAddr, newSockFd)
4009 CmInetFd *sockFd; /* socket file descriptor */
4010 CmInetAddr *fromAddr; /* calling Internet address/port */
4011 CmInetFd *newSockFd; /* socket file descriptor for new connection*/
4014 S32 ret; /* temporary return value */
4015 S32 addrLen; /* address structure length */
4016 struct sockaddr_in *peerAddr; /* calling Internet address/port */
4017 #ifdef IPV6_SUPPORTED
4018 struct sockaddr_in6 *peerAddr6; /* calling Internet address/port */
4019 struct sockaddr_in6 sockAddr;
4021 CmInetSockAddr sockAddr;
4022 #endif /* IPV6_SUPPORTED */
4029 #if (ERRCLASS & ERRCLS_INT_PAR)
4030 /* error check on parameters */
4031 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd))
4035 #endif /* ERRCLASS & ERRCLS_INT_PAR */
4037 /* change CmInetSockAddr to sockAddr */
4038 addrLen = sizeof(sockAddr);
4041 #if ( defined(SUNOS) || defined(SS_LINUX))
4042 newSockFd->fd = accept(sockFd->fd, (CmInetSockAddr*)&sockAddr,
4043 (socklen_t *)&addrLen);
4045 newSockFd->fd = accept(sockFd->fd, (CmInetSockAddr*)&sockAddr,
4047 #endif /* SUNOS || SS_LINUX */
4049 /* cm_inet_c_001.main_58: Moved setting of protType below */
4051 if (CM_INET_INV_SOCK_FD(newSockFd))
4053 if (INET_ERR_CODE == ERR_WOULDBLOCK)
4055 /* no connection present to accept */
4062 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
4063 /* cm_inet_c_001.main_62:Warning fix */
4064 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetAccept() Failed : error(%d),"
4065 " sockFd->fd(%ld)\n", INET_ERR_CODE, sockFd->fd);
4066 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET022, 0, prntBuf);
4068 /* cm_inet_c_001.main_62:Warning fix */
4069 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetAccept() Failed : error(%d),"
4070 " sockFd->fd(%d)\n", INET_ERR_CODE, sockFd->fd);
4071 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET022, 0, prntBuf);
4072 #endif /*ALIGN_64BIT*/
4073 #endif /* CMINETDBG */
4079 /* cm_inet_c_001.main_58: Fix for g++ compilation warning */
4080 /* added for IPv6/IPv4 socket distinguishing */
4081 #ifdef IPV6_SUPPORTED
4082 if (addrLen == sizeof(struct sockaddr_in))
4083 newSockFd->protType = AF_INET;
4084 else if(addrLen == sizeof(struct sockaddr_in6))
4085 newSockFd->protType = AF_INET6;
4090 /* cm_inet_c_001.main_62:Warning fix */
4091 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetAccept() Failed : sockFd->fd(%ld)\n", sockFd->fd);
4092 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET071, 0, prntBuf);
4094 /* cm_inet_c_001.main_62:Warning fix */
4095 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetAccept() Failed : sockFd->fd(%d)\n", sockFd->fd);
4096 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET071, 0, prntBuf);
4097 #endif /*ALIGN_64BIT*/
4098 #endif /* CMINETDBG */
4101 #endif /* IPV6_SUPPORTED */
4103 /* set the new socket file descriptor type */
4104 newSockFd->type = CM_INET_STREAM;
4106 /* set default options for new socket file descriptor */
4107 optVal = CM_INET_OPT_DISABLE;
4108 ret = cmInetSetOpt(newSockFd, SOL_SOCKET, CM_INET_OPT_BLOCK, &optVal);
4111 ret = cmInetClose(newSockFd);
4115 #ifdef IPV6_SUPPORTED
4116 cmMemset((U8*)fromAddr, 0, sizeof(fromAddr));
4117 if (addrLen == sizeof(struct sockaddr_in))
4119 peerAddr = (struct sockaddr_in *)&sockAddr;
4120 fromAddr->type = CM_INET_IPV4ADDR_TYPE;
4121 fromAddr->u.ipv4Addr.port = CM_INET_NTOH_U16(peerAddr->sin_port);
4122 fromAddr->u.ipv4Addr.address =
4123 CM_INET_NTOH_U32(peerAddr->sin_addr.s_addr);
4125 else if (addrLen == sizeof(struct sockaddr_in6))
4127 peerAddr6 = (struct sockaddr_in6 *)&sockAddr;
4128 fromAddr->type = CM_INET_IPV6ADDR_TYPE;
4129 fromAddr->u.ipv6Addr.port = CM_INET_NTOH_U16(peerAddr6->sin6_port);
4130 CM_INET_COPY_IPV6ADDR(&fromAddr->u.ipv6Addr.ipv6NetAddr,
4131 &peerAddr6->sin6_addr);
4134 peerAddr = (struct sockaddr_in *)&sockAddr;
4135 fromAddr->port = CM_INET_NTOH_U16(peerAddr->sin_port);
4136 fromAddr->address = CM_INET_NTOH_U32(peerAddr->sin_addr.s_addr);
4137 #endif /* IPV6_SUPPORTED */
4139 } /* end of cmInetAccept */
4144 * Fun: cmInet4FillTos
4146 * Desc: This function inserts tos (into ancillary data) which
4147 * will be used to fill tos value in ip header in outgoing IP packet
4148 * when sending that packet using sendmsg()function.
4159 PRIVATE S16 cmInet4FillTos
4161 U8 tos, /* tos value to be filled in ipheader */
4162 U8 *cmsgBuf, /* flat buffer where to build ext hdrs */
4163 U32 *curMsgIdx /* idx in cmsgBuf where HBH/Dest ext hdr ends */
4166 PRIVATE S16 cmInet4FillTos(tos, cmsgBuf, curMsgIdx, protType)
4167 U8 tos; /* tos value to be filled in ipheader */
4168 U8 *cmsgBuf; /* flat buffer where to build ext hdrs */
4169 U32 *curMsgIdx; /* idx in cmsgBuf where HBH/Dest ext hdr ends */
4172 struct cmsghdr *tempHdr;
4175 TRC2(cmInet4FillTos)
4180 /* cmsghdr struc will appear before data in the ancillary data object.
4181 * So put cmsghdr struc in flat buffer first. */
4183 /* cmsghdr struc points to flat buffer's starting address */
4184 tempHdr = (struct cmsghdr *)cmsgBuf;
4186 /* fill up level & type of cmsghdr structure */
4187 tempHdr->cmsg_level = IPPROTO_IPV6;
4188 tempHdr->cmsg_type = IP_TOS;
4189 (*(U8*)CMSG_DATA(tempHdr)) = tos;
4190 len = CMSG_SPACE(sizeof tos);
4193 /* fill up the length of cmsghdr structure */
4194 tempHdr->cmsg_len = len;
4199 }/* end of cmInet4FillTos */
4202 * Fun: cmInetSendDscpMsg
4204 * Desc: Sends the message data hold by mBuf.
4205 * The len paramter gives the actual written octets. If the socket
4206 * is non-blocking this value can be differ from the mBuf length
4207 * because there was not enough transmit buffer space available. If
4208 * this occurs, RWOULDBLOCK is returned and only a part of the mBuf
4210 * Values for flag parameter:
4212 * CM_INET_NO_FLAG - no additional control flag
4214 * Ret: ROK - successful
4215 * RWOULDBLOCK - no or not entire mBuf sent because would block
4216 * ROUTRES - failed, out of resources
4217 * RCLOSED - connection was closed by the peer
4220 * Notes: The successful completion of a send call does not indicate that
4221 * the data has been successfully delivered!
4223 * This function does not free any sent buffers.
4231 PUBLIC S16 cmInetSendDscpMsg
4233 CmInetFd *sockFd, /* socket file descriptor */
4234 CmInetAddr *dstAddr, /* destination Internet address/port */
4235 CmInetMemInfo *info, /* buffer allocation info */
4236 Buffer *mBuf, /* buffer structure to send */
4237 MsgLen *len, /* number of actually sent octets */
4238 /* added for IPv6 ext hdr */
4239 CmInetIpHdrParm *ipHdrParams, /* IPv6 extensions headers */
4240 S16 flags /* additional control flags, unused */
4243 /* added for IPv6 ext hdr */
4244 PUBLIC S16 cmInetSendDscpMsg(sockFd, dstAddr, info, mBuf, len, ipHdrParams, flags)
4245 CmInetFd *sockFd; /* socket file descriptor */
4246 CmInetAddr *dstAddr; /* destination Internet address/port */
4247 CmInetMemInfo *info; /* buffer allocation info */
4248 Buffer *mBuf; /* buffer structure to send */
4249 MsgLen *len; /* number of actually sent octets */
4250 CmInetIpHdrParm *ipHdrParams; /* IPv6 extensions headers */
4251 S16 flags; /* additional control flags, unused */
4254 #if (defined(WIN32) || defined(CMINETFLATBUF))
4255 S32 ret; /* temporary return value */
4256 MsgLen msgLen; /* message length */
4257 MsgLen bufLen; /* send buffer length */
4258 Data *sendBuf; /* plain send buffer */
4260 S32 ret; /* temporary return value */
4261 S32 retVal; /* temporary return value */
4262 S16 i; /* loop index */
4263 CmInetIovec txArr[CM_INET_MAX_DBUF]; /* scatter vector */
4264 S16 numDBufs; /* number of dBufs in message */
4265 struct msghdr msg; /* sendmsg() message header */
4266 MsgLen msgLen; /* message length */
4267 U32 strtEndDBufNum; /* starting/ending DBuf number */
4268 MsgLen unSentLen; /* sent len */
4269 #ifdef IPV6_SUPPORTED
4270 U32 curMsgIdx; /* indx in cmsgData where to write an ext hdr */
4271 /* added for IPv6 ext hdr */
4272 #if (defined(SS_LINUX) || defined(_XPG4_2))
4273 /* alloc from stack for IPv6 ancill data */
4274 U8 cmsgData[CM_INET_IPV6_ANCIL_DATA];
4275 #endif /* SS_LINUX || _XPG4_2 */
4277 U32 curMsgIdx; /* indx in cmsgData where to write an ext hdr */
4278 #if (defined(SS_LINUX) || defined(_XPG4_2))
4279 /* alloc from stack for IPv4 ancill data */
4280 U8 cmsgData[CM_INET_IPV4_ANCIL_DATA];
4281 #endif /* SS_LINUX || _XPG4_2 */
4282 #endif /* IPV6_SUPPORTED */
4283 #endif /* WIN32 | CMINETFLATBUF */
4285 struct sockaddr_in remAddr; /* remote Internet address */
4286 #ifdef IPV6_SUPPORTED
4287 struct sockaddr_in6 remAddr6; /* remote Internet address */
4288 #endif /* IPV8_SUPPORTED */
4289 CmInetSockAddr *sockAddrPtr;
4290 /* cm_inet_c_001.main_58 : Fix for klockwork issue */
4293 /* cm_inet_c_001.main_50 - Added for partial send handling */
4294 /* cm_inet_c_001.main_59: Protected under if not defined WIN32*/
4295 #if (!defined(WIN32))
4299 TRC2(cmInetSendDscpMsg)
4303 #if (ERRCLASS & ERRCLS_INT_PAR)
4304 /* error check on parameters */
4305 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) ||
4306 (info == NULLP) || (len == NULLP))
4310 #endif /* ERRCLASS & ERRCLS_INT_PAR */
4312 /* added for IPv6 ext hdr */
4313 #if !(defined(WIN32) || defined(CMINETFLATBUF))
4314 #if (defined(SS_LINUX) || defined(_XPG4_2))
4315 /* cmMemset((U8*)cmsgData, 0, sizeof(cmsgData)); */
4316 #endif /* SS_LINUX || _XPG4_2 */
4318 #endif /* WIN32 | CMINETFLATBUF */
4320 msgLen = 0; /* need by CC to pass without warning */
4321 sockAddrPtr = NULLP;
4324 /* setup remote address */
4325 if (dstAddr != NULLP)
4327 #ifdef IPV6_SUPPORTED
4328 if (dstAddr->type == CM_INET_IPV6ADDR_TYPE)
4330 cmMemset((U8*)&remAddr6, 0, sizeof(remAddr6));
4331 remAddr6.sin6_family = AF_INET6;
4332 remAddr6.sin6_port = CM_INET_HTON_U16(dstAddr->u.ipv6Addr.port);
4333 CM_INET_COPY_IPV6ADDR(&remAddr6.sin6_addr,
4334 &dstAddr->u.ipv6Addr.ipv6NetAddr);
4335 sizeOfAddr = sizeof(remAddr6);
4336 sockAddrPtr = (CmInetSockAddr *)&remAddr6;
4340 cmMemset((U8*)&remAddr, 0, sizeof(remAddr));
4341 remAddr.sin_family = AF_INET;
4342 remAddr.sin_port = CM_INET_HTON_U16(dstAddr->u.ipv4Addr.port);
4343 remAddr.sin_addr.s_addr =
4344 CM_INET_HTON_U32(dstAddr->u.ipv4Addr.address);
4345 sizeOfAddr = sizeof(remAddr);
4346 sockAddrPtr = (CmInetSockAddr *)&remAddr;
4349 /* cmMemset((U8*)&remAddr, 0, sizeof(remAddr)); */
4350 remAddr.sin_family = AF_INET;
4351 remAddr.sin_port = CM_INET_HTON_U16(dstAddr->port);
4352 remAddr.sin_addr.s_addr = CM_INET_HTON_U32(dstAddr->address);
4353 sizeOfAddr = sizeof(remAddr);
4354 sockAddrPtr = (CmInetSockAddr *)&remAddr;
4355 #endif /* IPV6_SUPPORTED */
4358 #if (defined(WIN32) || defined(CMINETFLATBUF))
4359 /* copy message to a flat buffer */
4360 ret = SFndLenMsg(mBuf, &bufLen);
4365 /* max message length is limited to control the memory usage */
4366 /* casting bufLen to avoid warnings */
4367 if ((bufLen > 0) && ((U32)bufLen > CM_INET_MAX_MSG_LEN))
4371 ret = SGetSBuf(info->region, info->pool, &sendBuf, bufLen);
4376 ret = SCpyMsgFix(mBuf, 0, bufLen, sendBuf, &msgLen);
4377 if ((ret != ROK) || (msgLen != bufLen))
4380 SPutSBuf(info->region, info->pool, sendBuf, bufLen);
4384 if (dstAddr == NULLP)
4386 /* VxWorks sendto has some problem
4387 * with connected UDP socket, use send */
4389 ret = sendto(sockFd->fd, (S8 *)sendBuf, bufLen, 0,
4392 ret = send(sockFd->fd, (S8 *)sendBuf, bufLen, 0);
4393 #endif /* end of SS_VW */
4396 /* cm_inet_c_001.main_54: Fix for vxworks 6.7 sending data on TCP sockets */
4398 #if (defined(SS_VW) && defined(SS_VW6_7))
4399 if ((sockFd->type == CM_INET_STREAM) || (sockFd->type == SOCK_RDM) )
4401 ret = send(sockFd->fd, (S8 *)sendBuf, bufLen, 0);
4404 #endif /* end of SS_VW6_7 and SS_VW */
4406 ret = sendto(sockFd->fd, (S8 *)sendBuf, bufLen, 0,
4407 sockAddrPtr, sizeOfAddr);
4410 if (ret == INET_ERR)
4413 SPutSBuf(info->region, info->pool, sendBuf, bufLen);
4415 if(INET_ERR_CODE == ERR_AGAIN)
4418 RETVALUE(RWOULDBLOCK);
4421 /* Check for ERR_WOULDBLOCK */
4422 if(INET_ERR_CODE == ERR_WOULDBLOCK)
4425 RETVALUE(RWOULDBLOCK);
4430 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
4431 /* cm_inet_c_001.main_62:Warning fix */
4432 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSendDscpMsg() Failed : error(%d), msgLen(%d),"
4433 " sockFd->fd(%ld)\n", INET_ERR_CODE, bufLen, sockFd->fd);
4434 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET023, 0, prntBuf);
4436 /* cm_inet_c_001.main_62:Warning fix */
4437 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSendDscpMsg() Failed : error(%d), msgLen(%d),"
4438 " sockFd->fd(%d)\n", INET_ERR_CODE, bufLen, sockFd->fd);
4439 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET023, 0, prntBuf);
4440 #endif /*ALIGN_64BIT*/
4441 #endif /* CMINETDBG */
4443 /* cm_inet_c_001.main_37 network unreacheble error is added */
4444 /* check if network is reacheble*/
4445 if ((INET_ERR_CODE == ERR_NETUNREACH))
4447 RETVALUE(RNETFAILED);
4451 /* Check if connection was closed */
4452 if ((INET_ERR_CODE == ERR_PIPE) ||
4453 (INET_ERR_CODE == ERR_CONNABORTED) ||
4454 (INET_ERR_CODE == ERR_CONNRESET))
4465 /* check if entire message could be sent */
4470 SPutSBuf(info->region, info->pool, sendBuf, bufLen);
4471 RETVALUE(RWOULDBLOCK);
4475 SPutSBuf(info->region, info->pool, sendBuf, bufLen);
4477 #else /* end of Win NT/flat buffer specific part */
4478 ret = SFndLenMsg(mBuf, &msgLen);
4485 /* cmMemset((U8*)&msg, 0, sizeof(msg)); */
4488 if (dstAddr != NULLP)
4491 msg.msg_name = (Void*)sockAddrPtr;
4494 msg.msg_name = (char *)sockAddrPtr;
4496 msg.msg_name = (caddr_t)sockAddrPtr;
4498 #endif /* SS_LINUX */
4499 msg.msg_namelen = sizeOfAddr;
4503 msg.msg_name = NULLP;
4504 msg.msg_namelen = 0;
4506 /* added defined(_XPG4_2) */
4507 #if (defined(SS_LINUX) || defined(_XPG4_2))
4508 msg.msg_control = NULLP;
4509 msg.msg_controllen = 0;
4511 msg.msg_accrights = 0;
4512 msg.msg_accrightslen = NULLP;
4513 #endif /* SS_LINUX */
4515 /* allocate scatter vector */
4516 numDBufs = CM_INET_MAX_DBUF;
4522 if (ipHdrParams != NULLP && (ipHdrParams->type == CM_INET_IPV4ADDR_TYPE))
4523 if((ipHdrParams->u.hdrParmIpv4.tos.pres == TRUE)&& \
4524 (ipHdrParams->u.hdrParmIpv4.tos.val != 0))
4526 cmInet4FillTos(ipHdrParams->u.hdrParmIpv4.tos.val,
4527 (U8 *)(cmsgData + curMsgIdx), &curMsgIdx);
4528 msg.msg_control = cmsgData; /* pointer to Ancillary Data */
4529 msg.msg_controllen = curMsgIdx; /* total length of ancillary Data */
4531 /* if the sender wants to send Ipv6 exten. headers */
4532 #ifdef IPV6_OPTS_SUPPORTED
4533 if (ipHdrParams != NULLP && (ipHdrParams->type == CM_INET_IPV6ADDR_TYPE))
4536 if(ipHdrParams->u.ipv6HdrParm.ttl.pres == TRUE)
4538 cmInetBuildSendHoplimit((U32)ipHdrParams->u.ipv6HdrParm.ttl.val,
4539 (U8 *)(cmsgData + curMsgIdx), &curMsgIdx);
4541 #endif /* SS_LINUX */
4544 /* have to decide how to get the src addr to add in in6_pktinfo */
4545 if(ipHdrParams->u.ipv6HdrParm.srcAddr6.type == 6)
4547 cmInet6BuildSendPktinfo(
4548 &ipHdrParams->u.ipv6HdrParm.srcAddr6.u.ipv6NetAddr,
4549 (U8 *)(cmsgData + curMsgIdx), &curMsgIdx,
4552 #endif /* LOCAL_INTF */
4554 /* copy each ipv6 ext header from ipHdrParams to the flat buffer
4555 * cmsgData one by one. */
4557 if (ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.hbhHdrPrsnt == TRUE)
4558 /* build HBH ext header in cmsgData starting at indx 0 */
4559 cmInet6BuildSendHBHOpts(
4560 &ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.hbhOptsArr,
4561 (U8 *)(cmsgData + curMsgIdx), &curMsgIdx, 0);
4563 /* now copy the elements from the Destination Option array one by
4564 * one to the Flat Buffer cmsgData. Start filling at indx curMsgIdx
4565 * which is the end of HBH hdr. */
4566 if (ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.destOptsPrsnt == TRUE)
4567 /* build Dest opt hdr starting at (cmsgData + curMsgIdx) */
4568 cmInet6BuildSendDestOpts(
4569 &(ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.destOptsArr),
4570 (U8 *)(cmsgData + curMsgIdx), &curMsgIdx, 1);
4572 /* copy Route header to to the Flat Buffer cmsgData */
4573 if (ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.rtOptsPrsnt == TRUE)
4574 /* curMsgIdx will be the indx where Dest opt ends in cmsgData */
4575 cmInet6BuildSendRouteOpts(
4576 &ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.rtOptsArr,
4577 (U8 *)(cmsgData + curMsgIdx), &curMsgIdx);
4579 /* msghrd struc's msg_control will point cmsgData and msg_controllen
4580 * will be the curMsgIdx */
4581 msg.msg_control = cmsgData; /* pointer to Ancillary Data */
4582 msg.msg_controllen = curMsgIdx; /* total length of ancillary Data */
4585 #endif /* IPV6_OPTS_SUPPORTED */
4587 /* Loop till all the data is sent or till the sendmsg call cannot send
4591 /* build the send vector */
4592 /* cm_inet_c_001.main_50 - Partial send handling. Added variable to hold
4593 total length of the packed dbufs */
4594 retVal = buildSendIovec(mBuf, unSentLen, txArr, numDBufs, &i,
4595 &strtEndDBufNum, &ioLen);
4600 /* Incase of UDP/RAW messages call SCompressMsg. */
4601 if (sockFd->type != CM_INET_STREAM)
4603 /* Compress the message into a single dBuf */
4604 ret = SCompressMsg(mBuf);
4609 /* Rebuild the send vector */
4610 /* cm_inet_c_001.main_50 - Partial send handling. Added variable to hold
4611 total length of the packed dbuf */
4612 ret = buildSendIovec(mBuf, unSentLen, txArr, numDBufs, &i,
4613 &strtEndDBufNum, &ioLen);
4623 msg.msg_iov = txArr;
4629 extern int ntl_hLib;
4630 if ( sockFd->fd >= 0xD001)
4631 ret = ntl_sendmsg(ntl_hLib, sockFd->fd, &msg, 0);
4633 ret = sendmsg(sockFd->fd, &msg, 0);
4636 ret = sendmsg(sockFd->fd, &msg, 0);
4638 /* cm_inet_c_001.main_50 - Update the length only in successful cases */
4639 if (ret == INET_ERR)
4641 if((INET_ERR_CODE == ERR_AGAIN) ||
4642 (INET_ERR_CODE == ERR_WOULDBLOCK))
4644 /* cm_inet_c_001.main_50 - Return without making length 0, if in case the partial
4645 message was sent earlier */
4646 RETVALUE(RWOULDBLOCK);
4650 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
4651 /* cm_inet_c_001.main_62:Warning fix */
4652 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSendDscpMsg() Failed : error(%d),"
4653 " sockFd->fd(%ld)\n", INET_ERR_CODE, sockFd->fd);
4654 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET024, 0, prntBuf);
4656 /* cm_inet_c_001.main_62:Warning fix */
4657 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSendDscpMsg() Failed : error(%d),"
4658 " sockFd->fd(%d)\n", INET_ERR_CODE, sockFd->fd);
4659 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET024, 0, prntBuf);
4660 #endif /*ALIGN_64BIT*/
4661 #endif /* CMINETDBG */
4663 /* cm_inet_c_001.main_37 network unreacheble error is added */
4664 /* check if network is reacheble or not */
4665 if ((INET_ERR_CODE == ERR_NETUNREACH))
4667 RETVALUE(RNETFAILED);
4670 /* Check if connection was closed by the peer */
4671 if ((INET_ERR_CODE == ERR_PIPE) ||
4672 (INET_ERR_CODE == ERR_CONNREFUSED) ||
4673 (INET_ERR_CODE == ERR_CONNABORTED))
4681 /* cm_inet_c_001.main_50 - Update the length only in successful cases */
4684 /* cm_inet_c_001.main_50 - if what is actually sent is less than what is attemped
4685 * to be sent, then return WOULDBLOCK
4688 RETVALUE(RWOULDBLOCK);
4692 } while (*len < msgLen);
4693 #endif /* WIN32 | CMINETFLATBUF */
4697 } /* end of cmInetSendDscpMsg */
4701 * Fun: cmInetSendMsg
4703 * Desc: Sends the message data hold by mBuf.
4704 * The len paramter gives the actual written octets. If the socket
4705 * is non-blocking this value can be differ from the mBuf length
4706 * because there was not enough transmit buffer space available. If
4707 * this occurs, RWOULDBLOCK is returned and only a part of the mBuf
4709 * Values for flag parameter:
4711 * CM_INET_NO_FLAG - no additional control flag
4713 * Ret: ROK - successful
4714 * RWOULDBLOCK - no or not entire mBuf sent because would block
4715 * ROUTRES - failed, out of resources
4716 * RCLOSED - connection was closed by the peer
4719 * Notes: The successful completion of a send call does not indicate that
4720 * the data has been successfully delivered!
4722 * This function does not free any sent buffers.
4730 PUBLIC S16 cmInetSendMsg
4732 CmInetFd *sockFd, /* socket file descriptor */
4733 CmInetAddr *dstAddr, /* destination Internet address/port */
4734 CmInetMemInfo *info, /* buffer allocation info */
4735 Buffer *mBuf, /* buffer structure to send */
4736 MsgLen *len, /* number of actually sent octets */
4737 /* added for IPv6 ext hdr */
4738 #ifdef IPV6_OPTS_SUPPORTED
4739 CmInetIpHdrParm *ipHdrParams, /* IPv6 extensions headers */
4740 #endif /* IPV6_OPTS_SUPPORTED */
4741 S16 flags /* additional control flags, unused */
4744 /* added for IPv6 ext hdr */
4745 #ifdef IPV6_OPTS_SUPPORTED
4746 PUBLIC S16 cmInetSendMsg(sockFd, dstAddr, info, mBuf, len, ipHdrParams, flags)
4747 CmInetFd *sockFd; /* socket file descriptor */
4748 CmInetAddr *dstAddr; /* destination Internet address/port */
4749 CmInetMemInfo *info; /* buffer allocation info */
4750 Buffer *mBuf; /* buffer structure to send */
4751 MsgLen *len; /* number of actually sent octets */
4752 CmInetIpHdrParm *ipHdrParams; /* IPv6 extensions headers */
4753 S16 flags; /* additional control flags, unused */
4755 PUBLIC S16 cmInetSendMsg(sockFd, dstAddr, info, mBuf, len, flags)
4756 CmInetFd *sockFd; /* socket file descriptor */
4757 CmInetAddr *dstAddr; /* destination Internet address/port */
4758 CmInetMemInfo *info; /* buffer allocation info */
4759 Buffer *mBuf; /* buffer structure to send */
4760 MsgLen *len; /* number of actually sent octets */
4761 S16 flags; /* additional control flags, unused */
4762 #endif /* IPV6_OPTS_SUPPORTED */
4765 #if (defined(WIN32) || defined(CMINETFLATBUF))
4766 S32 ret; /* temporary return value */
4767 MsgLen msgLen; /* message length */
4768 MsgLen bufLen; /* send buffer length */
4769 Data *sendBuf; /* plain send buffer */
4771 S32 ret; /* temporary return value */
4772 S32 retVal; /* temporary return value */
4773 S16 i; /* loop index */
4774 CmInetIovec txArr[CM_INET_MAX_DBUF]; /* scatter vector */
4775 S16 numDBufs; /* number of dBufs in message */
4776 struct msghdr msg; /* sendmsg() message header */
4777 MsgLen msgLen; /* message length */
4778 U32 strtEndDBufNum; /* starting/ending DBuf number */
4779 MsgLen unSentLen; /* sent len */
4780 #ifdef IPV6_SUPPORTED
4781 /* added for IPv6 ext hdr */
4782 #ifdef IPV6_OPTS_SUPPORTED
4783 U32 curMsgIdx; /* indx in cmsgData where to write an ext hdr */
4784 #if (defined(SS_LINUX) || defined(_XPG4_2))
4785 /* alloc from stack for IPv6 ancill data */
4786 U8 cmsgData[CM_INET_IPV6_ANCIL_DATA];
4787 #endif /* SS_LINUX || _XPG4_2 */
4788 #endif /* IPV6_OPTS_SUPPORTED */
4790 #if (defined(SS_LINUX) || defined(_XPG4_2))
4791 /* alloc from stack for IPv4 ancill data */
4792 /* U8 cmsgData[CM_INET_IPV4_ANCIL_DATA];*/
4793 #endif /* SS_LINUX || _XPG4_2 */
4794 #endif /* IPV6_SUPPORTED */
4795 #endif /* WIN32 | CMINETFLATBUF */
4797 struct sockaddr_in remAddr; /* remote Internet address */
4798 #ifdef IPV6_SUPPORTED
4799 struct sockaddr_in6 remAddr6; /* remote Internet address */
4800 #endif /* IPV8_SUPPORTED */
4801 CmInetSockAddr *sockAddrPtr;
4802 /* cm_inet_c_001.main_58 : Fix for klockwork issue */
4805 /* cm_inet_c_001.main_50 - Added for partial send handling */
4806 /* cm_inet_c_001.main_59: Protected under if not defined WIN32*/
4807 #if (!defined(WIN32))
4815 #if (ERRCLASS & ERRCLS_INT_PAR)
4816 /* error check on parameters */
4817 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) ||
4818 (info == NULLP) || (len == NULLP))
4822 #endif /* ERRCLASS & ERRCLS_INT_PAR */
4824 /* added for IPv6 ext hdr */
4825 #if !(defined(WIN32) || defined(CMINETFLATBUF))
4826 #if (defined(SS_LINUX) || defined(_XPG4_2))
4827 /* cmMemset((U8*)cmsgData, 0, sizeof(cmsgData)); */
4828 #endif /* SS_LINUX || _XPG4_2 */
4829 #ifdef IPV6_OPTS_SUPPORTED
4831 #endif /* IPV6_SUPPORTED */
4832 #endif /* WIN32 | CMINETFLATBUF */
4834 msgLen = 0; /* need by CC to pass without warning */
4835 sockAddrPtr = NULLP;
4838 /* setup remote address */
4839 if (dstAddr != NULLP)
4841 #ifdef IPV6_SUPPORTED
4842 if (dstAddr->type == CM_INET_IPV6ADDR_TYPE)
4844 cmMemset((U8*)&remAddr6, 0, sizeof(remAddr6));
4845 remAddr6.sin6_family = AF_INET6;
4846 remAddr6.sin6_port = CM_INET_HTON_U16(dstAddr->u.ipv6Addr.port);
4847 CM_INET_COPY_IPV6ADDR(&remAddr6.sin6_addr,
4848 &dstAddr->u.ipv6Addr.ipv6NetAddr);
4849 sizeOfAddr = sizeof(remAddr6);
4850 sockAddrPtr = (CmInetSockAddr *)&remAddr6;
4854 cmMemset((U8*)&remAddr, 0, sizeof(remAddr));
4855 remAddr.sin_family = AF_INET;
4856 remAddr.sin_port = CM_INET_HTON_U16(dstAddr->u.ipv4Addr.port);
4857 remAddr.sin_addr.s_addr =
4858 CM_INET_HTON_U32(dstAddr->u.ipv4Addr.address);
4859 sizeOfAddr = sizeof(remAddr);
4860 sockAddrPtr = (CmInetSockAddr *)&remAddr;
4863 /* cmMemset((U8*)&remAddr, 0, sizeof(remAddr)); */
4864 remAddr.sin_family = AF_INET;
4865 remAddr.sin_port = CM_INET_HTON_U16(dstAddr->port);
4866 remAddr.sin_addr.s_addr = CM_INET_HTON_U32(dstAddr->address);
4867 sizeOfAddr = sizeof(remAddr);
4868 sockAddrPtr = (CmInetSockAddr *)&remAddr;
4869 #endif /* IPV6_SUPPORTED */
4872 #if (defined(WIN32) || defined(CMINETFLATBUF))
4873 /* copy message to a flat buffer */
4874 ret = SFndLenMsg(mBuf, &bufLen);
4879 /* max message length is limited to control the memory usage */
4880 /* casting bufLen to avoid warnings */
4881 if ((bufLen > 0) && ((U32)bufLen > CM_INET_MAX_MSG_LEN))
4885 ret = SGetSBuf(info->region, info->pool, &sendBuf, bufLen);
4890 ret = SCpyMsgFix(mBuf, 0, bufLen, sendBuf, &msgLen);
4891 if ((ret != ROK) || (msgLen != bufLen))
4894 SPutSBuf(info->region, info->pool, sendBuf, bufLen);
4898 if (dstAddr == NULLP)
4900 /* VxWorks sendto has some problem
4901 * with connected UDP socket, use send */
4903 ret = sendto(sockFd->fd, (S8 *)sendBuf, bufLen, 0,
4906 ret = send(sockFd->fd, (S8 *)sendBuf, bufLen, 0);
4907 #endif /* end of SS_VW */
4910 /* cm_inet_c_001.main_54: Fix for vxworks 6.7 sending data on TCP sockets */
4912 #if (defined(SS_VW) && defined(SS_VW6_7))
4913 if ((sockFd->type == CM_INET_STREAM) || (sockFd->type == SOCK_RDM) )
4915 ret = send(sockFd->fd, (S8 *)sendBuf, bufLen, 0);
4918 #endif /* end of SS_VW6_7 and SS_VW */
4920 ret = sendto(sockFd->fd, (S8 *)sendBuf, bufLen, 0,
4921 sockAddrPtr, sizeOfAddr);
4924 if (ret == INET_ERR)
4927 SPutSBuf(info->region, info->pool, sendBuf, bufLen);
4929 if(INET_ERR_CODE == ERR_AGAIN)
4932 RETVALUE(RWOULDBLOCK);
4935 /* Check for ERR_WOULDBLOCK */
4936 if(INET_ERR_CODE == ERR_WOULDBLOCK)
4939 RETVALUE(RWOULDBLOCK);
4944 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
4945 /* cm_inet_c_001.main_62:Warning fix */
4946 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSendMsg() Failed : error(%d), msgLen(%d),"
4947 " sockFd->fd(%ld)\n", INET_ERR_CODE, bufLen, sockFd->fd);
4948 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET023, 0, prntBuf);
4950 /* cm_inet_c_001.main_62:Warning fix */
4951 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSendMsg() Failed : error(%d), msgLen(%d),"
4952 " sockFd->fd(%d)\n", INET_ERR_CODE, bufLen, sockFd->fd);
4953 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET023, 0, prntBuf);
4954 #endif /*ALIGN_64BIT*/
4955 #endif /* CMINETDBG */
4957 /* cm_inet_c_001.main_37 network unreacheble error is added */
4958 /* check if network is reacheble*/
4959 if ((INET_ERR_CODE == ERR_NETUNREACH))
4961 RETVALUE(RNETFAILED);
4965 /* Check if connection was closed */
4966 if ((INET_ERR_CODE == ERR_PIPE) ||
4967 (INET_ERR_CODE == ERR_CONNABORTED) ||
4968 (INET_ERR_CODE == ERR_CONNRESET))
4979 /* check if entire message could be sent */
4984 SPutSBuf(info->region, info->pool, sendBuf, bufLen);
4985 RETVALUE(RWOULDBLOCK);
4989 SPutSBuf(info->region, info->pool, sendBuf, bufLen);
4991 #else /* end of Win NT/flat buffer specific part */
4992 ret = SFndLenMsg(mBuf, &msgLen);
4999 /* cmMemset((U8*)&msg, 0, sizeof(msg)); */
5002 if (dstAddr != NULLP)
5005 msg.msg_name = (Void*)sockAddrPtr;
5008 msg.msg_name = (char *)sockAddrPtr;
5010 msg.msg_name = (caddr_t)sockAddrPtr;
5012 #endif /* SS_LINUX */
5013 msg.msg_namelen = sizeOfAddr;
5017 msg.msg_name = NULLP;
5018 msg.msg_namelen = 0;
5020 /* added defined(_XPG4_2) */
5021 #if (defined(SS_LINUX) || defined(_XPG4_2))
5022 msg.msg_control = NULLP;
5023 msg.msg_controllen = 0;
5025 msg.msg_accrights = 0;
5026 msg.msg_accrightslen = NULLP;
5027 #endif /* SS_LINUX */
5029 /* allocate scatter vector */
5030 numDBufs = CM_INET_MAX_DBUF;
5037 /* if the sender wants to send Ipv6 exten. headers */
5038 #ifdef IPV6_OPTS_SUPPORTED
5039 if (ipHdrParams != NULLP && (ipHdrParams->type == CM_INET_IPV6ADDR_TYPE))
5042 if(ipHdrParams->u.ipv6HdrParm.ttl.pres == TRUE)
5044 cmInetBuildSendHoplimit((U32)ipHdrParams->u.ipv6HdrParm.ttl.val,
5045 (U8 *)(cmsgData + curMsgIdx), &curMsgIdx);
5047 #endif /* SS_LINUX */
5050 /* have to decide how to get the src addr to add in in6_pktinfo */
5051 if(ipHdrParams->u.ipv6HdrParm.srcAddr6.type == 6)
5053 cmInet6BuildSendPktinfo(
5054 &ipHdrParams->u.ipv6HdrParm.srcAddr6.u.ipv6NetAddr,
5055 (U8 *)(cmsgData + curMsgIdx), &curMsgIdx,
5058 #endif /* LOCAL_INTF */
5060 /* copy each ipv6 ext header from ipHdrParams to the flat buffer
5061 * cmsgData one by one. */
5063 if (ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.hbhHdrPrsnt == TRUE)
5064 /* build HBH ext header in cmsgData starting at indx 0 */
5065 cmInet6BuildSendHBHOpts(
5066 &ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.hbhOptsArr,
5067 (U8 *)(cmsgData + curMsgIdx), &curMsgIdx, 0);
5069 /* now copy the elements from the Destination Option array one by
5070 * one to the Flat Buffer cmsgData. Start filling at indx curMsgIdx
5071 * which is the end of HBH hdr. */
5072 if (ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.destOptsPrsnt == TRUE)
5073 /* build Dest opt hdr starting at (cmsgData + curMsgIdx) */
5074 cmInet6BuildSendDestOpts(
5075 &(ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.destOptsArr),
5076 (U8 *)(cmsgData + curMsgIdx), &curMsgIdx, 1);
5078 /* copy Route header to to the Flat Buffer cmsgData */
5079 if (ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.rtOptsPrsnt == TRUE)
5080 /* curMsgIdx will be the indx where Dest opt ends in cmsgData */
5081 cmInet6BuildSendRouteOpts(
5082 &ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.rtOptsArr,
5083 (U8 *)(cmsgData + curMsgIdx), &curMsgIdx);
5085 /* msghrd struc's msg_control will point cmsgData and msg_controllen
5086 * will be the curMsgIdx */
5087 msg.msg_control = cmsgData; /* pointer to Ancillary Data */
5088 msg.msg_controllen = curMsgIdx; /* total length of ancillary Data */
5091 #endif /* IPV6_OPTS_SUPPORTED */
5093 /* Loop till all the data is sent or till the sendmsg call cannot send
5097 /* build the send vector */
5098 /* cm_inet_c_001.main_50 - Partial send handling. Added variable to hold
5099 total length of the packed dbufs */
5100 retVal = buildSendIovec(mBuf, unSentLen, txArr, numDBufs, &i,
5101 &strtEndDBufNum, &ioLen);
5106 /* Incase of UDP/RAW messages call SCompressMsg. */
5107 if (sockFd->type != CM_INET_STREAM)
5109 /* Compress the message into a single dBuf */
5110 ret = SCompressMsg(mBuf);
5115 /* Rebuild the send vector */
5116 /* cm_inet_c_001.main_50 - Partial send handling. Added variable to hold
5117 total length of the packed dbuf */
5118 ret = buildSendIovec(mBuf, unSentLen, txArr, numDBufs, &i,
5119 &strtEndDBufNum, &ioLen);
5129 msg.msg_iov = txArr;
5135 extern int ntl_hLib;
5136 if ( sockFd->fd >= 0xD001)
5137 ret = ntl_sendmsg(ntl_hLib, sockFd->fd, &msg, 0);
5139 ret = sendmsg(sockFd->fd, &msg, 0);
5142 ret = sendmsg(sockFd->fd, &msg, 0);
5144 /* cm_inet_c_001.main_50 - Update the length only in successful cases */
5145 if (ret == INET_ERR)
5147 if((INET_ERR_CODE == ERR_AGAIN) ||
5148 (INET_ERR_CODE == ERR_WOULDBLOCK))
5150 /* cm_inet_c_001.main_50 - Return without making length 0, if in case the partial
5151 message was sent earlier */
5152 RETVALUE(RWOULDBLOCK);
5156 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
5157 /* cm_inet_c_001.main_62:Warning fix */
5158 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSendMsg() Failed : error(%d),"
5159 " sockFd->fd(%ld)\n", INET_ERR_CODE, sockFd->fd);
5160 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET024, 0, prntBuf);
5162 /* cm_inet_c_001.main_62:Warning fix */
5163 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSendMsg() Failed : error(%d),"
5164 " sockFd->fd(%d)\n", INET_ERR_CODE, sockFd->fd);
5165 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET024, 0, prntBuf);
5166 #endif /*ALIGN_64BIT*/
5167 #endif /* CMINETDBG */
5169 /* cm_inet_c_001.main_37 network unreacheble error is added */
5170 /* check if network is reacheble or not */
5171 if ((INET_ERR_CODE == ERR_NETUNREACH))
5173 RETVALUE(RNETFAILED);
5176 /* Check if connection was closed by the peer */
5177 if ((INET_ERR_CODE == ERR_PIPE) ||
5178 (INET_ERR_CODE == ERR_CONNREFUSED) ||
5179 (INET_ERR_CODE == ERR_CONNABORTED))
5187 /* cm_inet_c_001.main_50 - Update the length only in successful cases */
5190 /* cm_inet_c_001.main_50 - if what is actually sent is less than what is attemped
5191 * to be sent, then return WOULDBLOCK
5194 RETVALUE(RWOULDBLOCK);
5198 } while (*len < msgLen);
5199 #endif /* WIN32 | CMINETFLATBUF */
5203 } /* end of cmInetSendMsg */
5206 /* added new functions for IPv6 extension headers */
5207 #ifdef IPV6_OPTS_SUPPORTED
5211 * Fun: cmInet6BuildSendPktinfo
5213 * Desc: This function inserts src address (into ancillary data) which
5214 * will be used as the src addr in outgoing IP packet when sending
5215 * that packet using sendmsg()function.
5226 PRIVATE S16 cmInet6BuildSendPktinfo
5228 CmInetIpAddr6 *srcAddr, /* src ip addr to set on outgoing packet */
5229 U8 *cmsgBuf, /* flat buffer where to build ext hdrs */
5230 U32 *curMsgIdx, /* idx in cmsgBuf where HBH/Dest ext hdr ends */
5231 U8 protType /* whether IPv4/IPv6 socket */
5234 PRIVATE S16 cmInet6BuildSendPktinfo(srcAddr, cmsgBuf, curMsgIdx, protType)
5235 CmInetIpAddr6 *srcAddr; /* src ip addr to set on outgoing packet */
5236 U8 *cmsgBuf; /* flat buffer where to build ext hdrs */
5237 U32 *curMsgIdx; /* idx in cmsgBuf where HBH/Dest ext hdr ends */
5238 U8 protType; /* whether IPv4/IPv6 socket */
5241 struct cmsghdr *tempHdr;
5242 struct in6_pktinfo *ipv6Pktinfo;
5243 struct in6_addr lpBkAddr;
5246 TRC2(cmInet6BuildSendPktinfo)
5250 lpBkAddr = in6addr_loopback;
5252 /* cmsghdr struc will appear before data in the ancillary data object.
5253 * So put cmsghdr struc in flat buffer first. */
5255 /* cmsghdr struc points to flat buffer's starting address */
5256 tempHdr = (struct cmsghdr *)cmsgBuf;
5258 /* fill up level & type of cmsghdr structure */
5259 if (protType == AF_INET6)
5261 tempHdr->cmsg_level = IPPROTO_IPV6;
5262 tempHdr->cmsg_type = IPV6_PKTINFO;
5265 else if(protType == AF_INET)
5267 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
5268 /* cm_inet_c_001.main_62:Warning fix */
5269 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "Invalid socket type in cmInet6BuildPktinfo(),"
5270 "protType(%d)\n", protType);
5271 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET025, 0, prntBuf);
5275 /* skip length of cmsghdr structure - 12 bytes */
5276 len += sizeof(struct cmsghdr);
5278 if(protType == AF_INET6)
5279 ipv6Pktinfo = (struct in6_pktinfo *)(cmsgBuf + len);
5283 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
5284 /* cm_inet_c_001.main_62:Warning fix */
5285 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "Invalid socket type in cmInet6BuildPktinfo(),"
5286 "protType(%d)\n", protType);
5287 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET026, 0, prntBuf);
5291 /* insert the hoplimit. This will override the kernel's
5292 * default hoplimit value */
5293 if(protType == AF_INET6)
5295 /* store ipv6 src addr */
5296 cmMemcpy((U8 *)&(ipv6Pktinfo->ipi6_addr), (U8 *)srcAddr, 16);
5299 /* store interface index */
5300 /* 0 is invalid intf indx it tells kernel to chose any intf it likes to
5301 * send this pkt. if we use nozero intf indx then kernel will send this
5302 * pkt only through that intf */
5303 ipv6Pktinfo->ipi6_ifindex = 0;
5307 else if(protType == AF_INET)
5309 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
5310 /* cm_inet_c_001.main_62:Warning fix */
5311 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "Invalid socket type in cmInet6BuildPktinfo(),"
5312 "protType(%d)\n", protType);
5313 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET027, 0, prntBuf);
5317 /* fill up the length of cmsghdr structure */
5318 tempHdr->cmsg_len = len;
5323 }/* end of cmInet6BuildSendPktinfo */
5324 #endif /* LOCAL_INTF */
5330 * Fun: cmInetBuildSendHoplimit
5332 * Desc: This function inserts hoplimit value to be sent out by ancillary
5333 * data by calling sendmsg()function.
5344 PRIVATE S16 cmInetBuildSendHoplimit
5346 U32 hoplimit, /* the hoplimit value to be set on outgoing packet */
5347 U8 *cmsgBuf, /* flat buffer where to build ext hdrs */
5348 U32 *curMsgIdx /* idx in cmsgBuf where HBH/Dest ext hdr ends */
5351 PRIVATE S16 cmInetBuildSendHoplimit(hoplimit, cmsgBuf, curMsgIdx)
5352 U32 hoplimit; /* the hoplimit value to be sent on outgoing packet */
5353 U8 *cmsgBuf; /* flat buffer where to build ext hdrs */
5354 U32 *curMsgIdx; /* idx in cmsgBuf where HBH/Dest ext hdr ends */
5357 struct cmsghdr *tempHdr;
5360 TRC2(cmInetBuildSendHoplimit)
5364 /* cmsghdr struc will appear before data in the ancillary data object.
5365 * So put cmsghdr struc in flat buffer first. */
5367 /* cmsghdr struc points to flat buffer's starting address */
5368 tempHdr = (struct cmsghdr *)cmsgBuf;
5370 /* fill up level & type of cmsghdr structure */
5371 tempHdr->cmsg_level = IPPROTO_IPV6;
5372 tempHdr->cmsg_type = IPV6_HOPLIMIT;
5374 /* skip cmsghdr struc (length of cmsghdr structure) */
5375 len += sizeof(struct cmsghdr);
5377 /* insert the hoplimit. This will override the kernel's
5378 * default hoplimit value */
5379 *(cmsgBuf + len) = hoplimit;
5380 len += sizeof(hoplimit);
5382 /* fill up the length of cmsghdr structure */
5383 tempHdr->cmsg_len = len;
5387 } /* end of cmInetBuildSendHoplimit */
5388 #endif /* SS_LINUX */
5393 * Fun: cmInet6BuildSendHBHOpts
5395 * Desc: This function builds the HopByHop option which will be put
5396 * in the data portion of the ancillary data object. To build
5397 * the HopByHop option this function takes an array of
5398 * individual HopByHop option and fill them in a flat buffer.
5399 * cmsghdr struc always appear before HopBYHop Options, Dest
5400 * Options and Route header option.
5402 * The address of the flat Buffer *cmsgBuf is passed to this
5403 * function from cmInetSendMsg. This buffer will have all extension
5404 * headers. This buffer is passed as ancillary data by sendmsg()
5408 * Notes: This function will also be used for Destination options
5415 PRIVATE S16 cmInet6BuildSendHBHOpts
5417 CmInetIpv6HBHHdrArr *hbhOptsArr,/* IPv6 extensions headers HBH/Dest opts */
5418 U8 *cmsgBuf, /* flat buffer where to build ext hdrs */
5419 U32 *curMsgIdx, /* idx in cmsgBuf where HBH/Dest ext hdr ends */
5420 U8 hdrId /* 0: HBH hdr, 1:Dest Hdr */
5423 PRIVATE S16 cmInet6BuildSendHBHOpts(hbhOptsArr, cmsgBuf, curMsgIdx, hdrId)
5424 CmInetIpv6HBHHdrArr *hbhOptsArr;/* IPv6 extensions headers HBH/Dest opts */
5425 U8 *cmsgBuf; /* flat buffer where to build ext hdrs */
5426 U32 *curMsgIdx; /* idx in cmsgBuf where HBH/Dest ext hdr ends */
5427 U8 hdrId; /* 0: HBH hdr, 1:Dest Hdr */
5430 struct cmsghdr *tempHdr;
5434 TRC2(cmInet6BuildSendHBHOpts)
5439 /* cmsghdr struc will appear before data in the ancillary data object.
5440 * So put cmsghdr struc in flat buffer first. */
5442 /* cmsghdr struc points to flat buffer's starting address */
5443 tempHdr = (struct cmsghdr *)cmsgBuf;
5445 /* fill up level & type of cmsghdr structure */
5448 tempHdr->cmsg_level = IPPROTO_IPV6;
5449 tempHdr->cmsg_type = IPV6_HOPOPTS;
5451 else if (hdrId == 1)
5453 tempHdr->cmsg_level = IPPROTO_IPV6;
5454 tempHdr->cmsg_type = IPV6_DSTOPTS;
5457 /* skip cmsghdr struc (length of cmsghdr structure) */
5458 len += (sizeof(tempHdr->cmsg_level) + sizeof(tempHdr->cmsg_len) +
5459 sizeof(tempHdr->cmsg_type));
5461 /* Next Hdr: will be fill up accordingly by Kernel */
5462 *(cmsgBuf + len) = 0x00;
5465 /* Header Ext Length: will be fill up by us. In units of 8-byte excluding
5466 * first 8 bytes starting from Next Header field. */
5467 *(cmsgBuf + len) = 0x00;
5470 /* fillup all HBH/dest options' TLV. Here, we assume that all the HBH/dest
5471 * options are packed inside 1 HBH option header. */
5472 for (optsIdx = 0; optsIdx < hbhOptsArr->numHBHOpts;
5475 /* Copy the TLV into cmsgBuf data portion */
5476 /* copy type field of every HBH/dest option */
5477 *(cmsgBuf + len) = hbhOptsArr->hbhOpts[optsIdx].type;
5478 len += sizeof(hbhOptsArr->hbhOpts[optsIdx].type);
5480 /* copy length field of every HBH/dest option */
5481 *(cmsgBuf + len) = hbhOptsArr->hbhOpts[optsIdx].length;
5482 len += sizeof(hbhOptsArr->hbhOpts[optsIdx].length);
5484 /* copy all value bytes of current HBH/dest option to the flat buffer */
5485 cmMemcpy((U8 *)(cmsgBuf + len),
5486 (U8 *)(hbhOptsArr->hbhOpts[optsIdx].value),
5487 hbhOptsArr->hbhOpts[optsIdx].length);
5488 len += hbhOptsArr->hbhOpts[optsIdx].length;
5491 /* cuMsgIdx will have the total length of HBH options array */
5492 /* add this length to the length of cmsgHdr struc */
5494 /* Padding: Different header has different padding requirement(xn+y). For
5495 * HBH Router Alert we need 2 bytes of padding. As this same function is
5496 * used for Destination option also and there is no option for it is yet
5497 * proposed, we are passing padN options - 6 bytes to make the Dest Option
5498 * hdr a multiple of 8 bytes. */
5500 /* HBH: padN of 2 bytes needed for Router Alert */
5501 /* This logic is present currently to support router alert which is the
5502 * only supported HBH option today. For other, generic method needed */
5505 *(cmsgBuf + len) = 0x01;
5507 *(cmsgBuf + len) = 0x00;
5511 /* fill up the length of cmsghdr structure */
5512 tempHdr->cmsg_len = len;
5516 } /* end of cmInet6BuildSendHBHOpts */
5521 * Fun: cmInet6BuildSendRouteOpts
5523 * Desc: This function transfers bytes from the Route hdr array to the
5524 * flat buffer. First the top cmsghdr structure will be filled in
5525 * the flat buffer, then route hdr type 0 will be added after
5526 * cmsghdr struc in the flat buffer. Then all IPV6 addresses will
5538 PRIVATE S16 cmInet6BuildSendRouteOpts
5540 CmInetIpv6RtHdr *rtOptsArr, /* IPv6 destination options array */
5541 U8 *cmsgBuf, /* flat buffer where to build ext hdrs */
5542 U32 *curMsgIdx /* idx in cmsgBuf where to start building RT hdr */
5545 PRIVATE S16 cmInet6BuildSendRouteOpts(rtOptsArr, cmsgBuf, curMsgIdx)
5546 CmInetIpv6RtHdr *rtOptsArr; /* IPv6 destination options array */
5547 U8 *cmsgBuf; /* flat buffer where to build ext hdrs */
5548 U32 *curMsgIdx; /* idx in cmsgBuf where to start building RT hd */
5551 struct cmsghdr *tempHdr;
5552 CmInetIpv6RtHdr0 *tempRtHdr;
5556 TRC2(cmInet6BuildSendRouteOpts);
5561 /* cmsghdr struc will appear before data in the ancillary data object.
5562 * So put cmsghdr struc in flat buffer first */
5564 /* cmsghdr struc points to flat buffer */
5565 tempHdr = (struct cmsghdr *)(cmsgBuf);
5567 tempHdr->cmsg_level = IPPROTO_IPV6;
5568 tempHdr->cmsg_type = IPV6_RTHDR;
5570 /* skip cmsghdr structure */
5571 len += sizeof(struct cmsghdr);
5573 /* we know the total size of Route hdr if we know the num of ipv6 addrs */
5574 tempHdr->cmsg_len = len + sizeof(CmInetIpv6RtHdr0)
5575 + rtOptsArr->numAddrs * sizeof(CmInetIpAddr6);
5577 /* attach route hdr type 0 after cmsghdr structure */
5578 tempRtHdr = (CmInetIpv6RtHdr0 *)(cmsgBuf + len);
5580 /* fill up fields of route hdr type 0 */
5582 /* will be filled up by Kernel */
5583 tempRtHdr->ip6r0_nextHdr = 0x00;
5585 tempRtHdr->ip6r0_hdrExtLen = (2 * rtOptsArr->numAddrs);
5587 /* only type supported today */
5588 tempRtHdr->ip6r0_type = 0x00;
5590 tempRtHdr->ip6r0_segLeft = rtOptsArr->numAddrs;
5592 /* Note: rfc 2292(1998) mentions 1 reserve byte & 3 strict/loose bytes
5593 * restricting total 23 ipv6 addresses can be added to the route header.
5594 * But rfc 2292(2002) mentions all 4 bytes are reserved which allows
5595 * as many ipv6 addresses as wishes to be added to the route header */
5597 tempRtHdr->ip6r0_resrvAndSLmap = rtOptsArr->slMap;
5599 /* move pointer in the flat buffer to the end of this structure */
5600 len += sizeof(CmInetIpv6RtHdr0);
5602 /* fill up all IPV6 addresses from rtOptsArr in the flat buffer */
5603 for (addrIdx = 0; addrIdx < rtOptsArr->numAddrs; addrIdx++)
5605 cmMemcpy((U8 *)(cmsgBuf + len),
5606 (U8 *)(rtOptsArr->ipv6Addrs[addrIdx]), 16);
5612 } /* end of cmInet6BuildSendRouteOpts */
5617 * Fun: cmInet6BuildRecvHopOptsArr
5619 * Desc: This function fills up the HopByHop Array of ipHdrParam from
5620 * the ancillary data received through recvmsg() call. The memory
5621 * to hold the extension headers is allocated here. All received
5622 * ext hdr info will be passed to upper user as ipHdrParam.
5624 * Ret: ROK - successful
5634 PRIVATE S16 cmInet6BuildRecvHopOptsArr
5636 U8 *cmsgData, /* flat buffer where to build ext hdrs */
5637 U32 hbhDataLen, /* byte len of cmsghdr + hbh ancil data */
5638 CmInetIpv6HBHHdrArr *hbhOptsArr, /* IPv6 extensions headers */
5639 U8 hdrId, /* 0: HBH, 1: DEST */
5640 CmInetMemInfo *info /* Memory information */
5643 PRIVATE S16 cmInet6BuildRecvHopOptsArr(cmsgData, hbhDataLen, hbhOptsArr, hdrId,
5645 U8 *cmsgData; /* flat buffer where to build ext hdrs */
5646 U32 hbhDataLen; /* byte len of cmsghdr + hbh ancil data */
5647 CmInetIpv6HBHHdrArr *hbhOptsArr; /* IPv6 extensions headers */
5648 U8 hdrId; /* 0: HBH, 1: DEST */
5649 CmInetMemInfo *info; /* Memory information */
5652 U32 curDataIdx; /* to keep track where we are in the hbh Data */
5653 U8 optsIdx; /* how many hbh opts present in data */
5654 U8 numOpts; /* number of hbh opts present in data */
5659 TRC2(cmInet6BuildRecvHopOptsArr)
5661 /* get length of actual hbh ancillary data */
5662 hbhDataLen -= sizeof(struct cmsghdr);
5668 /* skip Next Hdr byte & Hdr Ext Length byte */
5671 /* First find out how many hop-by-hop headers we need to allocate */
5674 /* break when all HBH data is copied to hbhOptsArr */
5675 if (curDataIdx >= hbhDataLen)
5681 tempType = *(U8 *)(cmsgData + curDataIdx);
5684 /* take care of pad1 option */
5687 /* not considering the pad1 as valid option */
5693 tempLen = *(U8 *)(cmsgData + curDataIdx);
5695 /* 1 is to skip length. tempLen to skip the value field */
5696 curDataIdx += (1 + tempLen);
5698 /* considering the padN as valid option for Dest Opt Hdr!!! As this is
5699 * the "only" valid option today. Ignore for HBH hdr */
5705 /* allocate mem needed to hold all HBH/Dest options */
5706 ret = SGetSBuf(info->region, info->pool,
5707 (Data **)&hbhOptsArr->hbhOpts,
5708 (Size)((sizeof(CmInetIpv6HBHHdr)) * numOpts));
5712 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
5713 /* cm_inet_c_001.main_62:Warning fix */
5714 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "SGetSBuf failure 1 in cmInet6BuildRecvHopOptsArr\n");
5715 CMINETLOGERROR(ERRCLS_ADD_RES, ECMINET028, 0, prntBuf);
5716 #endif /* CMINETDBG */
5723 /* skip Next Hdr byte & Hdr Ext Length byte */
5726 hbhOptsArr->numHBHOpts = numOpts;
5728 /* fill up HBH/dest opt array from recvd ancillary data */
5731 /* break when all HBH data is copied to hbhOptsArr */
5732 if (curDataIdx >= hbhDataLen)
5735 /* only copy Router Alert HBH option part which has type 5. Otherwise,
5736 * skip it when it is a PAD1, PADN or Jumbogram option for HBH. But
5737 * consider padN as valid option for dest opt hdr. */
5739 /* get the type of current HBH/dest option */
5740 tempType = *(cmsgData + curDataIdx);
5743 /* ignore PAD1 for both HBH/dest by skipping to next option */
5747 /* calculate how much to skip for padN in case of HBH */
5752 /* get the length field of padN option */
5753 tempLen = *(cmsgData + curDataIdx);
5756 /* move pointer forward to skip value field */
5757 curDataIdx += tempLen;
5761 hbhOptsArr->hbhOpts[optsIdx].type = tempType;
5763 /* copy the length */
5764 hbhOptsArr->hbhOpts[optsIdx].length = *(cmsgData + curDataIdx);
5767 /* take care of PADN = 2 when value field empty. We also don't need
5768 * to allocate memory for empty value field */
5769 if (hbhOptsArr->hbhOpts[optsIdx].length == 0)
5770 hbhOptsArr->hbhOpts[optsIdx].value = NULLP;
5773 /* take care of all other options having valid value field
5774 * such as Router Alert, PADN >= 3 bytes and Jumbo */
5775 ret = SGetSBuf(info->region, info->pool,
5776 (Data **)&hbhOptsArr->hbhOpts[optsIdx].value,
5777 (Size)hbhOptsArr->hbhOpts[optsIdx].length);
5781 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
5782 /* cm_inet_c_001.main_62:Warning fix */
5783 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "SGetSBuf failure 2 cmInet6BuildRecvHopOptsArr\n");
5784 CMINETLOGERROR(ERRCLS_ADD_RES, ECMINET029, 0, prntBuf);
5785 #endif /* CMINETDBG */
5786 /* now go inside every separate HBH option and free the memory
5787 * allocated for its value field */
5788 for (; optsIdx > 0; optsIdx --)
5790 if (hbhOptsArr->hbhOpts[optsIdx - 1].value != NULLP)
5793 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
5794 /* cm_inet_c_001.main_62:Warning fix */
5795 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "SPutSBuf call 1 in BuildRecvHopOptsArr\n");
5796 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET030, 0, prntBuf);
5797 #endif /* CMINETDBG */
5798 SPutSBuf(info->region, info->pool,
5799 (Data *)hbhOptsArr->hbhOpts[optsIdx - 1].value,
5800 (Size)hbhOptsArr->hbhOpts[optsIdx - 1].length);
5803 /* clean up all CmInetIpv6HBHHdr structures allocated for all
5804 * arrived HBH options OR numOpts CmInetIpv6HBHHdr structures
5805 * allocated after counting numOpts */
5807 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
5808 /* cm_inet_c_001.main_62:Warning fix */
5809 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "SPutSBuf call 2 in BuildRecvHopOptsArr\n");
5810 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET031, 0, prntBuf);
5811 #endif /* CMINETDBG */
5812 SPutSBuf(info->region, info->pool,
5813 (Data *)hbhOptsArr->hbhOpts, numOpts * sizeof(CmInetIpv6HBHHdr));
5814 hbhOptsArr->numHBHOpts = 0;
5815 hbhOptsArr->hbhOpts = NULLP;
5818 /* copy the value bytes */
5819 cmMemcpy((U8 *)hbhOptsArr->hbhOpts[optsIdx].value,
5820 (U8 *)(cmsgData + curDataIdx),
5821 hbhOptsArr->hbhOpts[optsIdx].length);
5822 curDataIdx += hbhOptsArr->hbhOpts[optsIdx].length;
5825 /* get next option */
5829 } /* end of cmInet6BuildRecvHopOptsArr() */
5834 * Fun: cmInet6BuildRecvRtHdr
5836 * Desc: This function fills up the Route Header in the cmInetIpv6HdrParm
5837 * from the recvd ancillary data from recvmsg system call.
5839 * Ret: ROK - successful
5849 PRIVATE S16 cmInet6BuildRecvRtHdr
5851 U8 *cmsgData, /* flat buffer where to build Route hdr */
5852 U32 rtDataLen, /* byte len of cmsghdr struc+rtHdr ancil data */
5853 CmInetIpv6RtHdr0 *rtHdr0, /* rtHeader0 struct that precedes IPV6 addrss */
5854 CmInetIpv6RtHdr *rtOptsArr,/* IPv6 extensions headers */
5855 CmInetMemInfo *info /* Memory information */
5858 PRIVATE S16 cmInet6BuildRecvRtHdr(cmsgData, rtDataLen, rtHdr0, rtOptsArr, info)
5859 U8 *cmsgData; /* flat buffer where to build Route hdr */
5860 U32 rtDataLen; /* byte len of cmsghdr struc+rtHdr ancil data */
5861 CmInetIpv6RtHdr0 *rtHdr0; /* rtHeader0 struct that precedes IPV6 addrss */
5862 CmInetIpv6RtHdr *rtOptsArr;/* IPv6 extensions headers */
5863 CmInetMemInfo *info; /* Memory information */
5866 U32 curDataIdx; /* to keep track where we are in hbh Data */
5867 U8 i; /* loop counter */
5868 S16 ret; /* temporary return value */
5870 TRC2(cmInet6BuildRecvRtHdr)
5872 /* byte len of actual rtHdr ancil data */
5873 rtDataLen -= sizeof(struct cmsghdr);
5875 /* start from beginning */
5878 /* copy next header byte */
5879 rtHdr0->ip6r0_nextHdr = *(cmsgData + curDataIdx);
5882 /* copy header extension length byte */
5883 rtHdr0->ip6r0_hdrExtLen = *(cmsgData + curDataIdx);
5886 /* copy type byte (always 0) */
5887 rtHdr0->ip6r0_type = 0x00;
5890 /* copy segment left byte */
5891 rtHdr0->ip6r0_segLeft = *(cmsgData + curDataIdx);
5894 /* copy 1 reserve byte + 3 strict/loose bytes */
5895 cmMemcpy((U8 *)(&rtOptsArr->slMap),
5896 (U8 *)(cmsgData + curDataIdx), 4);
5899 /* also save reserv byte + 3 sl bytes to rtHdro struc */
5900 rtHdr0->ip6r0_resrvAndSLmap = rtOptsArr->slMap;
5902 /* subtract 8 bytes for Next Hdr, Hdr Ext Len, .... + SL bit map */
5903 rtOptsArr->numAddrs = (rtDataLen - 8)/16;
5905 ret = SGetSBuf(info->region, info->pool,
5906 (Data **)&rtOptsArr->ipv6Addrs,
5907 (Size)rtOptsArr->numAddrs * 16);
5911 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
5912 /* cm_inet_c_001.main_62:Warning fix */
5913 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "SGetSBuf failure 1 in cmInet6BuildRecvRtHdr\n");
5914 CMINETLOGERROR(ERRCLS_ADD_RES, ECMINET032, 0, prntBuf);
5915 #endif /* CMINETDBG */
5919 /* copy all the ipv6 addresses */
5920 for(i=0; i < rtOptsArr->numAddrs; i++)
5922 cmMemcpy((U8 *)(rtOptsArr->ipv6Addrs[i]),
5923 (U8 *)(cmsgData + curDataIdx), 16);
5928 } /* end of cmInet6BuildRecvRtHdr() */
5933 * Fun: cmInet6GetHopLimitValue
5935 * Desc: This function extracts the hop limit value(ttl) of from the
5936 * ancillary data received through recvmsg() call. Then this
5937 * hoplimit value will be passed to upper user as ipHdrParam.
5939 * Ret: ROK - successful
5948 PRIVATE S16 cmInet6GetHopLimitValue
5950 U8 *cmsgData, /* flat buffer where to build ext hdrs */
5951 U32 hopLimitDataLen, /* byte len of cmsghdr + hbh ancil data */
5952 CmInetIpv6HdrParm *ipv6HdrParam /* ipv6 header parameters */
5955 PRIVATE S16 cmInet6GetHopLimitValue(cmsgData, hopLimitDataLen, ipv6HdrParam)
5956 U8 *cmsgData; /* flat buffer where to build ext hdrs */
5957 U32 hopLimitDataLen; /* byte len of cmsghdr + hbh ancil data */
5958 CmInetIpv6HdrParm *ipv6HdrParam; /* ipv6 header parameters */
5961 U16 curDataIdx; /* to keep track where we are in the ancillary Data */
5962 U32 *hopLimitValue; /* ttl/hoplimit value */
5964 hopLimitValue = NULL;
5967 /* get length of actual hbh ancillary data */
5968 hopLimitDataLen -= sizeof(struct cmsghdr);
5970 /* go to the first byte of hop limit which present after cmsghdr struc */
5971 curDataIdx += sizeof(struct cmsghdr);
5973 /* mark that hoplimit(ttl) is present */
5974 ipv6HdrParam->ttl.pres = TRUE;
5976 /* the first byte will be the HopLimit value */
5977 hopLimitValue = (U32 *)(cmsgData);
5978 ipv6HdrParam->ttl.val = (U8)(*hopLimitValue);
5982 #endif /* IPV6_OPTS_SUPPORTED */
5987 * Fun: cmInetRecvMsg
5989 * Desc: Reads data from a socket into a message.
5990 * The buffers for the message are allocated within the
5991 * cmInetRead() function from the pool and region Id set in the
5993 * If the number of octets given by the paramter len is not
5994 * available the function immediately returns with RKDNA.
5995 * If the len parameter is set to CM_INET_READ_ANY, the currently
5996 * available data is read.
5997 * Values for flag parameter:
5999 * CM_INET_NO_FLAG - no additional control flag
6000 * CM_INET_MSG_PEEK - do not destroy data on receive buffer
6002 * Ret: ROK - successful
6003 * ROKDNA - ok, data not available
6004 * RCLOSED - connection closed by peer
6005 * ROUTRES - failed, out of resources
6014 PUBLIC S16 cmInetRecvMsg
6016 CmInetFd *sockFd, /* socket file descriptor */
6017 CmInetAddr *fromAddr, /* sender Internet address/port */
6018 CmInetMemInfo *info, /* buffer allocation info */
6019 Buffer **mPtr, /* received buffer structure */
6020 MsgLen *len, /* number of octets to read */
6021 /* added for IPv6 */
6022 #ifdef IPV6_OPTS_SUPPORTED
6023 CmInetIpHdrParm *ipHdrParams, /* IPv6 extensions headers */
6024 #endif /* IPV6_OPTS_SUPPORTED */
6026 CmInetLocalInf *localIf, /* local interface on which pkt was recvd */
6027 #endif /* LOCAL_INTF */
6028 S32 flags /* additional control flags */
6031 /* added for IPv6 */
6032 #ifdef IPV6_OPTS_SUPPORTED
6034 PUBLIC S16 cmInetRecvMsg(sockFd, fromAddr, info, mPtr, len,
6035 ipHdrParams, localIf, flags)
6036 CmInetFd *sockFd; /* socket file descriptor */
6037 CmInetAddr *fromAddr; /* sender Internet address/port */
6038 CmInetMemInfo *info; /* buffer allocation info */
6039 Buffer **mPtr; /* received buffer structure */
6040 MsgLen *len; /* number of octets to read */
6041 CmInetIpHdrParm *ipHdrParams; /* IPv6 extensions headers */
6042 CmInetLocalInf *localIf; /* local interface on which pkt was recvd */
6043 S32 flags; /* additional control flags */
6045 PUBLIC S16 cmInetRecvMsg(sockFd, fromAddr, info, mPtr, len, ipHdrParams, flags)
6046 CmInetFd *sockFd; /* socket file descriptor */
6047 CmInetAddr *fromAddr; /* sender Internet address/port */
6048 CmInetMemInfo *info; /* buffer allocation info */
6049 Buffer **mPtr; /* received buffer structure */
6050 MsgLen *len; /* number of octets to read */
6051 CmInetIpHdrParm *ipHdrParams; /* IPv6 extensions headers */
6052 S32 flags; /* additional control flags */
6053 #endif /* LOCAL_INTF */
6056 PUBLIC S16 cmInetRecvMsg(sockFd, fromAddr, info, mPtr, len, localIf, flags)
6057 CmInetFd *sockFd; /* socket file descriptor */
6058 CmInetAddr *fromAddr; /* sender Internet address/port */
6059 CmInetMemInfo *info; /* buffer allocation info */
6060 Buffer **mPtr; /* received buffer structure */
6061 MsgLen *len; /* number of octets to read */
6062 CmInetLocalInf *localIf; /* local interface on which pkt was recvd */
6063 S32 flags; /* additional control flags */
6065 PUBLIC S16 cmInetRecvMsg(sockFd, fromAddr, info, mPtr, len, flags)
6066 CmInetFd *sockFd; /* socket file descriptor */
6067 CmInetAddr *fromAddr; /* sender Internet address/port */
6068 CmInetMemInfo *info; /* buffer allocation info */
6069 Buffer **mPtr; /* received buffer structure */
6070 MsgLen *len; /* number of octets to read */
6071 S32 flags; /* additional control flags */
6072 #endif /* LOCAL_INTF */
6073 #endif /* IPV6_OPTS_SUPPORTED */
6076 #if (defined(WIN32) || defined(CMINETFLATBUF))
6077 S32 ret; /* temporary return value */
6078 U32 pendLen; /* pending data length */
6079 S32 recvLen; /* number of received octets by recvmsg() */
6080 MsgLen bufLen; /* entire number of received octets */
6081 MsgLen curLen; /* current number of octets in buffer */
6082 Data *recvBuf; /* receive buffer */
6083 Data *bufPtr; /* current buffer position */
6084 Buffer *mBuf; /* received message */
6085 U32 remAddrLen; /* length of remote address */
6086 struct sockaddr_in *remAddr; /* remote Internet address */
6087 #ifdef IPV6_SUPPORTED
6088 struct sockaddr_in6 *remAddr6; /* remote Internet address */
6089 struct sockaddr_in6 remSockAddr; /* to get packet's source IP address */
6091 CmInetSockAddr remSockAddr; /* to get packet's source IP address */
6092 #endif /* IPV6_SUPPORTED */
6094 S32 ret; /* temporary return value */
6095 /* cm_inet_c_001.main_58: Fix for g++ compilation warning */
6097 U32 pendLen; /* pending data length */
6098 S32 numBuf; /* number of allocated dBufs */
6099 S32 recvLen; /* number of received octets by recvmsg() */
6100 MsgLen bufLen; /* entire number of received octets */
6101 struct msghdr msg; /* message header */
6102 /* cm_inet_c_001.main_54: Fix for Klockworks issue */
6103 Buffer *tempMsg = NULLP; /* temporary message */
6104 CmInetIovec rxArr[CM_INET_MAX_DBUF]; /* dynamic gather array */
6105 Buffer **dBufs = NULLP; /* dynamic array with allocated dBufs */
6106 S16 numDBufs; /* number of allocated dBufs */
6108 /* cm_inet_c_001.main_55: As remAddrLen is only being used when
6109 * WIN32 or CMINETFLATBUF is defined, then Removed variable
6111 struct sockaddr_in *remAddr; /* remote Internet address */
6112 #ifdef IPV6_SUPPORTED
6113 struct sockaddr_in6 *remAddr6; /* remote Internet address */
6114 struct sockaddr_in6 remSockAddr;/* to get packet's source IP address */
6115 /* added for IPv6 ext headers support */
6116 #ifdef IPV6_OPTS_SUPPORTED
6117 CmInetIpv6RtHdr0 rtHdr0; /* type 0 route header */
6118 #endif /* IPV6_OPTS_SUPPORTED */
6121 struct in6_pktinfo *pkt6Info; /* IPv6 IP_PKTINFO */
6122 #endif /* LOCAL_INTF */
6124 #if (defined(SS_LINUX) || defined(_XPG4_2))
6125 U8 ancillData[CM_INET_IPV6_ANCIL_DATA];
6126 /* from stack for IPv6 ancill data */
6129 CmInetSockAddr remSockAddr; /* to get packet's src IP address */
6130 #if (defined(SS_LINUX) || defined(_XPG4_2))
6131 U8 ancillData[CM_INET_IPV4_ANCIL_DATA];
6132 /* from stack for IPv4 ancill data */
6134 #endif /* IPV6_SUPPORTED */
6135 /* added new definitions */
6136 Bool allocFlatBuf; /* allocate a flat buffer */
6137 /* cm_inet_c_001.main_54: Fix for Klockworks issue */
6138 Data *recvBuf = NULLP; /* receive buffer */
6141 struct in_pktinfo *pkt4Info; /* IPv4 IP_PKTINFO */
6143 #endif /* SS_LINUX */
6144 #if (defined(IPV6_OPTS_SUPPORTED) || defined(LOCAL_INTF))
6145 struct cmsghdr *cmsgptr;/* pointer to struct cmsghdr */
6147 #endif /* WIN32 | CMINETFLATBUF */
6148 /* used by getsockopt */
6150 /* cm_inet_c_001.main_55:Removed unused variables errValue and optLen */
6154 #if (ERRCLASS & ERRCLS_INT_PAR)
6155 /* error check on parameters */
6156 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) ||
6157 (info == NULLP) || (mPtr == NULLP) || (len == NULLP))
6161 #endif /* ERRCLASS & ERRCLS_INT_PAR */
6165 /*cm_inet_c_001.main_48 variables declaration */
6166 #if !((defined(WIN32) || defined(CMINETFLATBUF)))
6171 #if (defined(WIN32) || defined(CMINETFLATBUF))
6173 #ifdef IPV6_SUPPORTED
6175 #endif /* IPV6_SUPPORTED */
6177 #ifdef IPV6_SUPPORTED
6180 #endif /* IPV6_SUPPORTED */
6182 #if (defined(SS_LINUX) || defined(_XPG4_2))
6183 cmMemset((U8*)ancillData, 0, sizeof(ancillData));
6184 #endif /* SS_LINUX || _XPG4_2 */
6186 #endif /* (WIN32 | CMINETFLATBUF) */
6188 /* clear the structure */
6189 cmMemset((U8*)&remSockAddr, 0, sizeof(remSockAddr));
6191 /* get number of pending data */
6192 /* removed 3rd arg memInfo. MemInfo is no longer
6193 needed as we call ioctl for all sockets */
6195 /* cm_inet_c_001.main_48 : call ioctl only for STREAM
6196 * sockets now. For Non-Stream sockets(Raw & UDP), fix
6197 * pending length to CM_INET_MAX_UDPRAW_MSGSIZE
6199 if(sockFd->type == CM_INET_STREAM)
6201 ret = cmInetGetNumRead(sockFd, &pendLen);
6204 /* ret may be RFAILED or ROUTRES */
6210 /* cm_inet_c_001.main_48 : pendLen is set 1 greater
6211 * than the #defined value. If recvFrom/recvMsg
6212 * returns the len == pendLen, we would drop the
6213 * message as the msg len is larger than the largest
6214 * msg we are willing to accept.
6216 pendLen = CM_INET_MAX_UDPRAW_MSGSIZE+1;
6220 /* check if connection got closed */
6223 if (sockFd->type == CM_INET_STREAM)
6225 /* cm_inet_c_001.main_50:
6226 * cm_inet_c_001.main_56: Removed comment for cm_inet_c_001.main_50 as
6227 * the current patch changes its functionality */
6228 U8 readBuf[1]; /* declaration of variable for Peek */
6231 * cm_inet_c_001.main_56:
6232 * We are peeking the socket buffer again with peek as on some machines
6233 * like solaris, there is a latency observed in ioctl. In such cases,
6234 * ioctl may return 0, even though there are bytes available to read.
6235 * We reconfirm through peek whether 0 means EOF or its ioctl latency
6238 ret = cmInetPeekNew(sockFd, NULLP, info, 0, 1, readBuf);
6243 /* cm_inet_c_001.main_56:
6244 * Returning ROKDNA even cmInetPeekNew returns ROK. Because currently
6245 * we are not sure about pending length. Anyway socket FD already set,
6246 * we do another iteration to get exact pendLen value. We cannot call
6247 * cmInetGetNumRead at this point because of latency between the ioctl
6248 * call and recvfrom call issues on some machines ioctl call may
6249 * return ZERO even their a data to read. */
6253 /* cm_inet_c_001.main_52: Support for partial reception */
6254 /* cm_inet_c_001.main_59: Fix for compilation warning */
6255 if ((sockFd->type == CM_INET_STREAM) && (*len > (MsgLen)pendLen))
6257 /* cm_inet_c_001.main_54: Fix for Klockworks issue */
6258 *len = (MsgLen)pendLen;
6261 /* check if there are enough pending data to read */
6262 if ((*len == CM_INET_READ_ANY) || ((U32)*len <= pendLen))
6264 if (*len == CM_INET_READ_ANY)
6266 /* added check for TCP socket. Pending data length in
6267 the socket recv buffer is determined by ioctl call in
6269 For TCP it can't be > CM_INET_MAX_MSG_LEN. */
6270 if (sockFd->type == CM_INET_STREAM)
6272 /* max message length is limited to control the memory usage */
6273 if (pendLen > CM_INET_MAX_MSG_LEN)
6274 pendLen = CM_INET_MAX_MSG_LEN;
6276 /* cm_inet_c_001.main_48 : removed the check for
6277 * Non Stream sockets (pendLen < MAX_UDPRAW_MSGSIZE)
6278 * as we are hardcoding pendLen for Non-Stream sockets.
6281 /* read all pending data */
6282 /* cm_inet_c_001.main_54: Fix for Klockworks issue */
6283 bufLen = (MsgLen)pendLen;
6284 *len = (MsgLen)pendLen;
6288 /* cm_inet_c_001.main_45- Returning CM_INET_MAX_MSG_LEN when input is larger than
6291 /* max message length is limited to control the memory usage */
6292 if ((*len) > CM_INET_MAX_MSG_LEN)
6294 (*len) = CM_INET_MAX_MSG_LEN;
6297 /* read data length given by user */
6301 #if (defined(WIN32) || defined(CMINETFLATBUF))
6303 /* set destination Internet address structure */
6304 if (fromAddr != NULLP)
6306 remAddrLen = sizeof(remSockAddr);
6313 /* allocate flat receive buffer */
6314 ret = SGetSBuf(info->region, info->pool, &recvBuf, bufLen);
6323 * maybe needs more than one recvfrom() call to read an entire
6324 * message from a stream socket (TCP)
6328 /* added separate recvfrom calls different OS */
6330 /*cm_inet_c_001.main_42 1. In Vx-Works the 5th and 6th parameter of recvfrom
6331 system call are either NULL or should be valid pointer.*/
6332 #if( defined(SS_VW) || defined(HPOS) || defined(SS_PS))
6334 recvLen = recvfrom(sockFd->fd, (S8 *)bufPtr, curLen, 0,
6335 (struct sockaddr *)&remSockAddr, (int *)&remAddrLen);
6337 recvLen = recvfrom(sockFd->fd, (S8 *)bufPtr, curLen, 0,
6338 NULLP, (int *)&remAddrLen);
6340 #if ( defined(SUNOS) || defined(SS_LINUX))
6342 recvLen = recvfrom(sockFd->fd, (S8 *)bufPtr, curLen, 0,
6343 (struct sockaddr *)&remSockAddr, (socklen_t *)&remAddrLen);
6345 recvLen = recvfrom(sockFd->fd, (S8 *)bufPtr, curLen, 0,
6346 NULLP, (socklen_t *)&remAddrLen);
6349 recvLen = recvfrom(sockFd->fd, (S8 *)bufPtr, curLen, 0,
6350 &remSockAddr, (S32 *)&remAddrLen);
6352 recvLen = recvfrom(sockFd->fd, (S8 *)bufPtr, curLen, 0,
6353 NULLP, (S32 *)&remAddrLen);
6355 #endif /* defined(SUNOS) || defined(SS_LINUX) */
6356 #endif /* defined(SS_VW) || defined(HPOS) || defined(SS_PS) */
6358 if (recvLen == INET_ERR)
6361 /* moved cleanup here */
6362 SPutSBuf(info->region, info->pool, recvBuf, bufLen);
6364 /* added check ERR_WOULDBLOCK */
6365 if ((INET_ERR_CODE == ERR_AGAIN) ||
6366 (INET_ERR_CODE == ERR_WOULDBLOCK))
6373 /* In Windows the recvfrom function fails
6374 * with error code which maps to either WSAECONNABORTED. If
6375 * this happens then cmInetRecvMsg must return RCLOSED */
6376 if ((INET_ERR_CODE == ERR_CONNABORTED) ||
6377 (INET_ERR_CODE == ERR_CONNRESET))
6385 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
6386 /* cm_inet_c_001.main_62:Warning fix */
6387 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetRecvMsg() Failed : error(%d),"
6388 " sockFd->fd(%ld)\n", INET_ERR_CODE, sockFd->fd);
6389 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET034, 0, prntBuf);
6391 /* cm_inet_c_001.main_62:Warning fix */
6392 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetRecvMsg() Failed : error(%d),"
6393 " sockFd->fd(%d)\n", INET_ERR_CODE, sockFd->fd);
6394 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET034, 0, prntBuf);
6395 #endif /*ALIGN_64BIT*/
6396 #endif /* CMINETDBG */
6404 * a message is always read atomically on a datagram socket,
6405 * therefore it's ok to read less than pending data!
6408 if ((sockFd->type == CM_INET_RAW) ||
6409 (sockFd->type == CM_INET_DGRAM))
6414 #else /* CM_INET2 */
6415 if (sockFd->type == CM_INET_DGRAM)
6420 #endif /* CM_INET2 */
6421 } /* while (curLen > 0) (only for stream sockets) */
6423 /* For UDP, it is possible to receive
6424 * a 0 byte datagram, in this case just return ROKDNA.
6427 if ((sockFd->type == CM_INET_DGRAM || sockFd->type == CM_INET_RAW)
6430 if ((sockFd->type == CM_INET_DGRAM) && (*len == 0))
6433 SPutSBuf(info->region, info->pool, recvBuf, bufLen);
6437 /* cm_inet_c_001.main_48 : If Received
6438 * len == CM_INET_MAX_UDPRAW_MSGSIZE+1
6442 if ((sockFd->type == CM_INET_DGRAM || sockFd->type == CM_INET_RAW)
6443 && (*len == (CM_INET_MAX_UDPRAW_MSGSIZE+1)))
6445 if ((sockFd->type == CM_INET_DGRAM)
6446 && (*len == (CM_INET_MAX_UDPRAW_MSGSIZE+1)))
6451 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
6452 /* cm_inet_c_001.main_62:Warning fix */
6453 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetRecvMsg(),recevied a message"
6454 " > than allowed(%lu), sockFd->fd(%ld) \n",
6455 CM_INET_MAX_UDPRAW_MSGSIZE, sockFd->fd);
6456 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET068, 0, prntBuf);
6458 /* cm_inet_c_001.main_62:Warning fix */
6459 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetRecvMsg(),recevied a message"
6460 " > than allowed(%lu), sockFd->fd(%d) \n",
6461 CM_INET_MAX_UDPRAW_MSGSIZE, sockFd->fd);
6462 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET068, 0, prntBuf);
6463 #endif /*ALIGN_64BIT*/
6465 SPutSBuf(info->region, info->pool, recvBuf, bufLen);
6469 /* cm_inet_c_001.main_48 : copy data to a message structure */
6470 ret = SGetMsg(info->region, info->pool, &mBuf);
6474 SPutSBuf(info->region, info->pool, recvBuf, bufLen);
6479 if ((sockFd->type == CM_INET_DGRAM) ||
6480 (sockFd->type == CM_INET_RAW))
6482 ret = SAddPstMsgMult(recvBuf, *len, mBuf);
6486 ret = SAddPstMsgMult(recvBuf, bufLen, mBuf);
6489 #else /* CM_INET2 */
6490 if (sockFd->type == CM_INET_DGRAM)
6492 ret = SAddPstMsgMult(recvBuf, *len, mBuf);
6496 ret = SAddPstMsgMult(recvBuf, bufLen, mBuf);
6498 #endif /* CM_INET2 */
6502 SPutSBuf(info->region, info->pool, recvBuf, bufLen);
6508 /* setup return destination Internet address */
6509 /* added the check of (remAddrLen > 0) */
6510 if ((fromAddr != NULLP) && (remAddrLen > 0))
6512 #ifdef IPV6_SUPPORTED
6513 if (remAddrLen == sizeof(struct sockaddr_in6))
6515 remAddr6 = (struct sockaddr_in6 *)&remSockAddr;
6516 fromAddr->type = CM_INET_IPV6ADDR_TYPE;
6517 fromAddr->u.ipv6Addr.port = CM_INET_NTOH_U16(remAddr6->sin6_port);
6518 CM_INET_COPY_IPV6ADDR(&fromAddr->u.ipv6Addr.ipv6NetAddr,
6519 &remAddr6->sin6_addr);
6523 remAddr = (struct sockaddr_in *)&remSockAddr;
6524 fromAddr->type = CM_INET_IPV4ADDR_TYPE;
6525 fromAddr->u.ipv4Addr.port = CM_INET_NTOH_U16(remAddr->sin_port);
6526 fromAddr->u.ipv4Addr.address = CM_INET_NTOH_U32(remAddr->sin_addr.s_addr);
6529 remAddr = (struct sockaddr_in *)&remSockAddr;
6530 fromAddr->port = CM_INET_NTOH_U16(remAddr->sin_port);
6531 fromAddr->address = CM_INET_NTOH_U32(remAddr->sin_addr.s_addr);
6532 #endif /* IPV6_SUPPORTED */
6536 SPutSBuf(info->region, info->pool, recvBuf, bufLen);
6538 #else /* end of Win NT/flat buffer specific part */
6540 /* Initialise variable */
6541 allocFlatBuf = FALSE;
6544 * maybe needs more than one recvmsg() call to read entire message
6545 * on a stream socket
6549 /* allocate gather vector, it's a dynamic array */
6550 numDBufs = CM_INET_MAX_DBUF;
6552 ret = SGetSBuf(info->region, info->pool, (Data**)&dBufs,
6553 numDBufs*sizeof(Buffer*));
6559 /* Allocate dBufs for gather read */
6560 /* allocate dBufs for gathering read */
6561 if (sockFd->type == CM_INET_STREAM)
6562 ret = buildRecvBuf(info, bufLen, rxArr, dBufs, numDBufs, &msg,
6565 ret = buildRecvBuf(info, bufLen, rxArr, dBufs, numDBufs, &msg,
6569 /* check if the function returned RNA */
6572 /* Incase of UDP/RAW messages allocate a flat buffer. Incase
6573 * of TCP ignore this error condition. The user will call
6574 * cmInetRecvMsg again */
6575 /* cm_inet_c_001.main_62:Warning fix */
6576 if (sockFd->type != (U8)CM_INET_STREAM)/* G++ */
6579 #ifdef T2K_MEM_LEAK_DBG
6580 char * file = __FILE__;
6581 U32 line = __LINE__;
6584 /* cleanup the dBuf array */
6585 for (i = 0; i < msg.msg_iovlen; i++)
6586 SPutDBuf(info->region, info->pool, dBufs[i]);
6588 SPutSBuf(info->region, info->pool, (Data*)dBufs,
6589 numDBufs * sizeof(Buffer*));
6591 /* allocate flat receive buffer */
6592 ret = SGetSBuf(info->region, info->pool, &recvBuf, bufLen);
6596 allocFlatBuf = TRUE;
6598 /* update the message structure */
6600 rxArr[0].iov_base = (Void*)recvBuf;
6601 rxArr[0].iov_len = (U32)bufLen;
6603 rxArr[0].iov_base = (S8*)recvBuf;
6604 rxArr[0].iov_len = bufLen;
6605 #endif /* SS_LINUX */
6606 msg.msg_iov = rxArr;
6612 SPutSBuf(info->region, info->pool, (Data*)dBufs,
6613 numDBufs*sizeof(Buffer*));
6618 numBuf = msg.msg_iovlen;
6620 /* setup destination Internet address structure */
6621 if (fromAddr != NULLP)
6624 msg.msg_name = (Void*)&remSockAddr;
6627 msg.msg_name = (char *)&remSockAddr;
6629 msg.msg_name = (caddr_t)&remSockAddr;
6631 #endif /* SS_LINUX */
6632 msg.msg_namelen = sizeof(remSockAddr);
6636 msg.msg_name = NULLP;
6637 msg.msg_namelen = 0;
6640 /* added defined(_XPG4_2). Also changed the
6642 #if (defined(SS_LINUX) || defined(_XPG4_2))
6643 msg.msg_control = ancillData;
6644 msg.msg_controllen = sizeof(ancillData);
6646 msg.msg_accrights = NULLP;
6647 msg.msg_accrightslen = 0;
6648 #endif /* SS_LINUX */
6650 recvLen = recvmsg(sockFd->fd, &msg, flags);
6651 if ((recvLen == INET_ERR) || (recvLen > CM_INET_MAX_MSG_LEN))
6653 /* Moved up the cleanup precedures here before returning */
6654 /* Cleanup flat buffer if allocated */
6656 SPutSBuf(info->region, info->pool, recvBuf, bufLen);
6660 for (i = 0; i < numBuf; i++)
6662 #ifdef T2K_MEM_LEAK_DBG
6663 char * file = __FILE__;
6664 U32 line = __LINE__;
6667 SPutDBuf(info->region, info->pool, dBufs[i]);
6669 SPutSBuf(info->region, info->pool, (Data*)dBufs,
6670 numDBufs*sizeof(Buffer*));
6673 /* cm_inet_c_001.main_50 - Free the buffer only when valid, it might be that
6674 * it has partially received data
6676 /* added check ERR_AGAIN when CMINETFLATBUF is not defined.
6677 added check ERR_WOULDBLOCK */
6678 if ((INET_ERR_CODE == ERR_AGAIN) ||
6679 (INET_ERR_CODE == ERR_WOULDBLOCK))
6681 /* cm_inet_c_001.main_50 : If message is read partially then just return
6682 * OK without freeing the mPtr. This will gaurd us
6683 * against unexpected WOULDBLOCKS observed in solaris
6691 /* cm_inet_c_001.main_50 - Free the buffer only when valid, it might be that
6692 * it has partially received data
6700 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
6701 /* cm_inet_c_001.main_62:Warning fix */
6702 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetRecvMsg() Failed : error(%d),"
6703 " sockFd->fd(%ld)\n", INET_ERR_CODE, sockFd->fd);
6704 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET035, 0, prntBuf);
6706 /* cm_inet_c_001.main_62:Warning fix */
6707 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetRecvMsg() Failed : error(%d),"
6708 " sockFd->fd(%d)\n", INET_ERR_CODE, sockFd->fd);
6709 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET035, 0, prntBuf);
6710 #endif /*ALIGN_64BIT*/
6711 #endif /* CMINETDBG */
6713 /* If this happens then cmInetRecvMsg must return RCLOSED.
6714 * Needed for getting icmp msgs */
6715 if (INET_ERR_CODE == ERR_CONNABORTED)
6725 /* added for IPv6 extn headers */
6726 #if (defined(IPV6_OPTS_SUPPORTED) || defined(LOCAL_INTF))
6728 /* check if ancillary data has been received.
6729 * Return the allocated memory when no ancillary data received */
6730 #if (defined(SS_LINUX) || defined(_XPG4_2))
6731 if (msg.msg_controllen)
6733 cmsgptr = CMSG_FIRSTHDR(&msg);
6739 #endif /* SS_LINUX || _XPG4_2 */
6741 if (cmsgptr != NULLP)
6743 #ifdef IPV6_OPTS_SUPPORTED
6744 if(ipHdrParams != NULLP)
6746 ipHdrParams->u.ipv6HdrParm.ttl.pres = FALSE;
6747 ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.hbhHdrPrsnt = FALSE;
6748 ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.destOptsPrsnt = FALSE;
6749 ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.rtOptsPrsnt = FALSE;
6751 /* get all ancillary data objects recvd one by one */
6752 for (cmsgptr = CMSG_FIRSTHDR(&msg); cmsgptr != NULLP;
6753 cmsgptr = CMSG_NXTHDR(&msg, cmsgptr))
6755 if (cmsgptr->cmsg_level == IPPROTO_IPV6)
6757 /* Initialise ipHdrParams properly */
6758 ipHdrParams->type = CM_INET_IPV6ADDR_TYPE;
6760 if (cmsgptr->cmsg_type == IPV6_HOPOPTS)
6762 /* build up HBH opt array from recvd ancillary data */
6763 ret = cmInet6BuildRecvHopOptsArr(
6764 (U8 *)CMSG_DATA(cmsgptr), cmsgptr->cmsg_len,
6765 &ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.hbhOptsArr,
6769 ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.hbhHdrPrsnt =
6773 else if(cmsgptr->cmsg_type == IPV6_DSTOPTS)
6775 else if ((cmsgptr->cmsg_type == IPV6_DSTOPTS) ||
6776 (cmsgptr->cmsg_type == IPV6_RTHDRDSTOPTS))
6777 #endif /* SS_LINUX */
6779 /* build up Dest opt array from recvd ancillary data */
6780 ret = cmInet6BuildRecvDstOptsArr(
6781 (U8 *)CMSG_DATA(cmsgptr), cmsgptr->cmsg_len,
6782 &ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.destOptsArr,
6786 ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.destOptsPrsnt =
6789 else if (cmsgptr->cmsg_type == IPV6_RTHDR)
6791 /* build up Route Hdr from recvd ancillary data */
6792 ret = cmInet6BuildRecvRtHdr(
6793 (U8 *)CMSG_DATA(cmsgptr), cmsgptr->cmsg_len, &rtHdr0,
6794 &ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.rtOptsArr,
6798 ipHdrParams->u.ipv6HdrParm.ipv6ExtHdr.rtOptsPrsnt =
6801 else if(cmsgptr->cmsg_type == IPV6_HOPLIMIT)
6803 /* get the received hoplimit */
6804 ret = cmInet6GetHopLimitValue((U8 *)CMSG_DATA(cmsgptr),
6805 cmsgptr->cmsg_len, &ipHdrParams->u.ipv6HdrParm);
6812 #endif /* IPV6_OPTS_SUPPORTED */
6814 #ifdef IPV6_SUPPORTED
6816 for (cmsgptr = CMSG_FIRSTHDR(&msg); cmsgptr != NULLP;
6817 cmsgptr = CMSG_NXTHDR(&msg, cmsgptr))
6819 if(cmsgptr->cmsg_type == IPV6_PKTINFO)
6821 pkt6Info = (struct in6_pktinfo *)CMSG_DATA(cmsgptr);
6822 localIf->intfPrsnt = TRUE;
6823 localIf->localIf = pkt6Info->ipi6_ifindex;
6824 localIf->localIfAddr.type = CM_INET_IPV6ADDR_TYPE;
6825 cmMemcpy((U8 *)&localIf->localIfAddr.u.ipv6NetAddr,
6826 (U8 *)(int *)&pkt6Info->ipi6_addr, 16);
6829 #endif /* LOCAL_INTF */
6832 #if (defined(SS_LINUX) && defined(LOCAL_INTF))
6833 #ifdef IPV6_SUPPORTED
6834 if(sockFd->protType == AF_INET)
6837 for (cmsgptr = CMSG_FIRSTHDR(&msg); cmsgptr != NULL;
6838 cmsgptr = CMSG_NXTHDR(&msg, cmsgptr))
6840 if (cmsgptr->cmsg_level == IPPROTO_IP &&
6841 cmsgptr->cmsg_type == IP_PKTINFO)
6843 pkt4Info = (struct in_pktinfo *)CMSG_DATA(cmsgptr);
6844 localIf->intfPrsnt = TRUE;
6845 localIf->localIf = pkt4Info->ipi_ifindex;
6846 localIf->localIfAddr.type = CM_INET_IPV4ADDR_TYPE;
6847 localIf->localIfAddr.u.ipv4NetAddr =
6848 ntohl(*(int *)&pkt4Info->ipi_addr);
6851 #ifdef IPV6_SUPPORTED
6854 #endif /* SS_LINUX */
6856 #endif /* IPV6_OPTS_SUPPORTED || LOCAL_INTF */
6858 /* setup return destination Internet address */
6859 if (fromAddr != NULLP)
6861 #ifdef IPV6_SUPPORTED
6862 if (msg.msg_namelen == sizeof(struct sockaddr_in6))
6864 remAddr6 = (struct sockaddr_in6 *)&remSockAddr;
6865 fromAddr->type = CM_INET_IPV6ADDR_TYPE;
6866 fromAddr->u.ipv6Addr.port =
6867 CM_INET_NTOH_U16(remAddr6->sin6_port);
6868 CM_INET_COPY_IPV6ADDR(&fromAddr->u.ipv6Addr.ipv6NetAddr,
6869 &remAddr6->sin6_addr);
6873 remAddr = (struct sockaddr_in *)&remSockAddr;
6874 fromAddr->type = CM_INET_IPV4ADDR_TYPE;
6875 fromAddr->u.ipv4Addr.port = CM_INET_NTOH_U16(remAddr->sin_port);
6876 fromAddr->u.ipv4Addr.address =
6877 CM_INET_NTOH_U32(remAddr->sin_addr.s_addr);
6880 remAddr = (struct sockaddr_in *)&remSockAddr;
6881 fromAddr->port = CM_INET_NTOH_U16(remAddr->sin_port);
6882 fromAddr->address = CM_INET_NTOH_U32(remAddr->sin_addr.s_addr);
6883 #endif /* IPV6_SUPPORTED */
6886 /* Incase a flat buffer was allocated get
6887 * a message to pass up */
6893 ret = SGetMsg(info->region, info->pool, &tempMsg);
6897 SPutSBuf(info->region, info->pool, recvBuf, bufLen);
6901 /* cm_inet_c_001.main_48 : A 0 len UDP packet could be received */
6904 ret = SAddPstMsgMult(recvBuf, recvLen, tempMsg);
6907 SPutSBuf(info->region, info->pool, recvBuf, bufLen);
6915 SPutSBuf(info->region, info->pool, recvBuf, bufLen);
6916 /* cm_inet_c_001.main_48 :flat buffers are allocated
6917 * for non -TCP sockets. On these sockets we can receive
6918 * only one message at a time
6920 /* cm_inet_c_001.main_54: Fix for Klockworks issue */
6921 *len = (MsgLen)recvLen;
6926 /* build message out of dBufs */
6927 ret = buildRecvMsg(info, rxArr, numBuf, recvLen, dBufs, &tempMsg);
6930 /* Deallocate previously allocated
6934 SPutSBuf(info->region, info->pool, (Data*)dBufs,
6935 numDBufs*sizeof(Buffer*));
6942 /* it's first recvmsg() call */
6947 /* concatenate messages */
6948 ret = SCatMsg(*mPtr, tempMsg, M1M2);
6954 SPutSBuf(info->region, info->pool, (Data*)dBufs,
6955 numDBufs*sizeof(Buffer*));
6961 SPutSBuf(info->region, info->pool, (Data*)dBufs,
6962 numDBufs*sizeof(Buffer*));
6965 * a message is always read atomically on a datagram socket,
6966 * therefore it's ok to read less than pending data!
6969 if ((sockFd->type == CM_INET_DGRAM) ||
6970 (sockFd->type == CM_INET_RAW))
6972 /* cm_inet_c_001.main_54: Fix for Klockworks issue */
6973 *len = (MsgLen)recvLen;
6976 #else /* CM_INET2 */
6977 if (sockFd->type == CM_INET_DGRAM)
6979 /* cm_inet_c_001.main_54: Fix for Klockworks issue */
6980 *len = (MsgLen)recvLen;
6983 #endif /* CM_INET2 */
6984 } /* while(bufLen > 0) (only for stream sockets) */
6986 /* cm_inet_c_001.main_48 : For UDP, it is possible to receive
6987 * a 0 byte datagram, in this case just return ROKDNA
6991 if ((sockFd->type == CM_INET_DGRAM || sockFd->type == CM_INET_RAW)
6994 if ((sockFd->type == CM_INET_DGRAM) && (*len == 0))
7006 /* Received len == CM_INET_MAX_UDPRAW_MSGSIZE+1
7011 if ((sockFd->type == CM_INET_DGRAM || sockFd->type == CM_INET_RAW)
7012 && (*len == (CM_INET_MAX_UDPRAW_MSGSIZE+1)))
7014 if ((sockFd->type == CM_INET_DGRAM)
7015 && (*len == (CM_INET_MAX_UDPRAW_MSGSIZE+1)))
7026 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
7027 /* cm_inet_c_001.main_62:Warning fix */
7028 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetRecvMsg() recevied a message > than"
7029 " allowed(%d),sockFd->fd(%ld)\n",
7030 CM_INET_MAX_UDPRAW_MSGSIZE, sockFd->fd);
7031 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET069, 0, prntBuf);
7033 /* cm_inet_c_001.main_62:Warning fix */
7034 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetRecvMsg() recevied a message > than"
7035 " allowed(%d),sockFd->fd(%d)\n",
7036 CM_INET_MAX_UDPRAW_MSGSIZE, sockFd->fd);
7037 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET069, 0, prntBuf);
7044 #endif /* WIN32 | CMINETFLATBUF */
7048 /* not enough data pending yet */
7053 } /* end of cmInetRecvMsg */
7056 /* cm_inet_c_001.main_56: Added new function cmInetPeekNew() */
7060 * Fun: cmInetPeekNew
7062 * Desc: Reads some data from the socket without destroying the socket
7064 * The data is specified by the byte positon (first byte is at
7065 * position 0) and the length.
7067 * Ret: ROK - successful
7068 * ROKDNA - ok, data not available
7069 * RCLOSED - connection closed by peer
7072 * Notes: Following are the differences from the cmInetPeek to cmInetPeekNew.
7073 * This primitive does not call the select function as this is already
7074 * taken care by the called primitive. This primitive will not use any
7075 * ioctl calls, because on some machines due to latency in ioctl call
7076 * length may return as ZERO, even there is some data to be read from
7077 * the socket and this primitive only peek buffer using recvfrom.
7079 * Caller of this function need to allocate the sufficient memory to hold
7080 * the data peeked from the socket i.e. dataPos + dataLen. Socket data
7081 * will be copied in the "data" starting from dataPos offset.
7083 * For example, caller passed the following values to this function.
7084 * dataPos = 2 and dataLen = 10,then size of data buffer received should
7085 * be minimum of (dataPos + dataLen)12 bytes and socket data will be
7086 * copied in the data buffer from offset 2 (dataPos) onwards.
7093 PUBLIC S16 cmInetPeekNew
7095 CmInetFd *sockFd, /* socket file descriptor */
7096 CmInetAddr *fromAddr, /* sender Internet address/port */
7097 CmInetMemInfo *info, /* buffer allocation info */
7098 MsgLen dataPos, /* position of data */
7099 MsgLen dataLen, /* length of read data */
7100 Data *data /* read data */
7103 PUBLIC S16 cmInetPeekNew(sockFd, fromAddr, info, dataPos, dataLen, data)
7104 CmInetFd *sockFd; /* socket file descriptor */
7105 CmInetAddr *fromAddr; /* sender Internet address/port */
7106 CmInetMemInfo *info; /* buffer allocation info */
7107 MsgLen dataPos; /* position of data */
7108 MsgLen dataLen; /* length of read data */
7109 Data *data; /* read data */
7112 /* cm_inet_c_001.main_57 - Fix for validation and compilation warning */
7113 S32 recvLen; /* number of received octets */
7114 S32 remAddrLen; /* length of remote address length */
7115 struct sockaddr_in *remAddr; /* remote Internet address */
7116 #ifdef IPV6_SUPPORTED
7117 struct sockaddr_in6 *remAddr6; /* remote Internet IPV6 address */
7118 struct sockaddr_in6 remSockAddr; /* to get packet's source IP address */
7120 CmInetSockAddr remSockAddr; /* to get packet's source IP address */
7121 #endif /* IPV6_SUPPORTED */
7123 TRC2(cmInetPeeknew);
7125 #if (ERRCLASS & ERRCLS_INT_PAR)
7126 /* error check on parameters */
7127 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) ||
7128 (info == NULLP) || (data == NULLP) ||
7129 (dataPos < 0) || (dataLen < 0))
7133 #endif /* ERRCLASS & ERRCLS_INT_PAR */
7135 /* check if fromAddr is present or not */
7136 if (fromAddr != NULLP)
7138 remAddrLen = sizeof(remSockAddr);
7145 /* added different recvfrom calls with different 6th arg for
7146 * different OS If remAddrLen is 0, pass NULLP */
7147 #if( defined(SS_VW) || defined(HPOS) || defined(SS_PS))
7149 recvLen = recvfrom(sockFd->fd,(S8*)(data + dataPos), (dataLen),
7150 CM_INET_MSG_PEEK, &remSockAddr, (int*)&remAddrLen);
7152 recvLen = recvfrom(sockFd->fd,(S8*)(data + dataPos), (dataLen),
7153 CM_INET_MSG_PEEK, NULLP, (int*)&remAddrLen);
7155 #if ( defined(SUNOS) || defined(SS_LINUX))
7157 recvLen = recvfrom(sockFd->fd, (S8*)(data + dataPos),(dataLen),
7158 CM_INET_MSG_PEEK, (struct sockaddr *)&remSockAddr,
7159 (socklen_t *)&remAddrLen);
7161 recvLen = recvfrom(sockFd->fd, (S8*)(data + dataPos),(dataLen),
7162 CM_INET_MSG_PEEK, NULLP, (socklen_t *)&remAddrLen);
7165 recvLen = recvfrom(sockFd->fd,(S8*)(data + dataPos), (dataLen),
7166 CM_INET_MSG_PEEK, &remSockAddr, (S32*)&remAddrLen);
7168 recvLen = recvfrom(sockFd->fd,(S8*)(data + dataPos), (dataLen),
7169 CM_INET_MSG_PEEK, NULLP, (S32*)&remAddrLen);
7170 #endif /* defined(SUNOS) || defined(SS_LINUX) */
7171 #endif /* defined(SS_VW) || defined(HPOS) || defined(SS_PS) */
7173 /* removed the check of returned remAddrLen */
7174 if (recvLen == INET_ERR)
7176 /* added check ERR_WOULDBLOCK */
7177 if ((INET_ERR_CODE == ERR_AGAIN) ||
7178 (INET_ERR_CODE == ERR_WOULDBLOCK))
7183 /* cm_inet_c_001.main_61: added host unreachable check */
7184 if ((INET_ERR_CODE == ERR_CONNABORTED) ||
7185 (INET_ERR_CODE == ERR_CONNRESET) ||
7186 (INET_ERR_CODE == ERR_HOSTUNREACH) ||
7187 (INET_ERR_CODE == ERR_CONNREFUSED))
7194 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
7195 /* cm_inet_c_001.main_62:Warning fix */
7196 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetPeekNew() Failed : error(%d), sockFd->fd(%ld)\n",
7197 INET_ERR_CODE, sockFd->fd);
7198 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET070, 0, prntBuf);
7200 /* cm_inet_c_001.main_62:Warning fix */
7201 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetPeekNew() Failed : error(%d), sockFd->fd(%d)\n",
7202 INET_ERR_CODE, sockFd->fd);
7203 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET070, 0, prntBuf);
7205 #endif /* CMINETDBG */
7209 else if (recvLen == 0)
7214 /* cm_inet_c_001.main_57 - Fix for validation */
7215 if (recvLen < (S32)dataLen) /* maybe happen */
7220 /* setup return destination Internet address */
7221 /* added the check of (remAddLen > 0) */
7222 if ((fromAddr != NULLP) && (remAddrLen > 0))
7224 #ifdef IPV6_SUPPORTED
7225 cmMemset((U8*)fromAddr, 0, sizeof(fromAddr));
7226 if (remAddrLen == sizeof(struct sockaddr_in6))
7228 remAddr6 = (struct sockaddr_in6 *)&remSockAddr;
7229 fromAddr->type = CM_INET_IPV6ADDR_TYPE;
7230 fromAddr->u.ipv6Addr.port =
7231 CM_INET_NTOH_U16(remAddr6->sin6_port);
7232 CM_INET_COPY_IPV6ADDR(&fromAddr->u.ipv6Addr.ipv6NetAddr,
7233 &remAddr6->sin6_addr);
7237 remAddr = (struct sockaddr_in *)&remSockAddr;
7238 fromAddr->type = CM_INET_IPV4ADDR_TYPE;
7239 fromAddr->u.ipv4Addr.port = CM_INET_NTOH_U16(remAddr->sin_port);
7240 fromAddr->u.ipv4Addr.address =
7241 CM_INET_NTOH_U32(remAddr->sin_addr.s_addr);
7244 remAddr = (struct sockaddr_in *)&remSockAddr;
7245 fromAddr->port = CM_INET_NTOH_U16(remAddr->sin_port);
7246 fromAddr->address = CM_INET_NTOH_U32(remAddr->sin_addr.s_addr);
7247 #endif /* IPV6_SUPPORTED */
7251 } /* end of cmInetPeeknew */
7258 * Desc: Reads some data from the socket without destroying the socket
7260 * The data is specified by the byte positon (first byte is at
7261 * position 0) and the length.
7263 * Ret: ROK - successful
7264 * ROKDNA - ok, data not available
7265 * RCLOSED - connection closed by peer
7275 PUBLIC S16 cmInetPeek
7277 CmInetFd *sockFd, /* socket file descriptor */
7278 CmInetAddr *fromAddr, /* sender Internet address/port */
7279 CmInetMemInfo *info, /* buffer allocation info */
7280 MsgLen dataPos, /* position of data */
7281 MsgLen dataLen, /* length of read data */
7282 Data *data /* read data */
7285 PUBLIC S16 cmInetPeek(sockFd, fromAddr, info, dataPos, dataLen, data)
7286 CmInetFd *sockFd; /* socket file descriptor */
7287 CmInetAddr *fromAddr; /* sender Internet address/port */
7288 CmInetMemInfo *info; /* buffer allocation info */
7289 MsgLen dataPos; /* position of data */
7290 MsgLen dataLen; /* length of read data */
7291 Data *data; /* read data */
7294 /* cm_inet_c_001.main_54: Fix for Klockworks issue */
7295 Data *recvBuf = NULLP; /* plain receive buffer */
7296 /* cm_inet_c_001.main_47: 102069 Changed from S32 to MsgLen for bufLen*/
7297 MsgLen bufLen; /* buffer length */
7298 MsgLen i; /* index */
7299 MsgLen j; /* index */
7300 S32 ret; /* temporary return value */
7301 U32 timeout; /* timeout for cmInetSelect() */
7302 U32 *timeoutPtr; /* pointer to timeout */
7303 S16 numFdS; /* number of ready descriptors */
7304 /* cm_inet_c_001.main_45 - fixing the UMR issue in 64bit linux */
7305 U32 pendLen = 0; /* pending data length */
7306 S32 recvLen; /* number of received octets */
7307 S32 remAddrLen; /* length of remote address length */
7308 CmInetFdSet readFdS; /* socket file descriptor set */
7309 struct sockaddr_in *remAddr; /* remote Internet address */
7310 #ifdef IPV6_SUPPORTED
7311 struct sockaddr_in6 *remAddr6; /* remote Internet IPV6 address */
7312 struct sockaddr_in6 remSockAddr; /* to get packet's source IP address */
7314 CmInetSockAddr remSockAddr; /* to get packet's source IP address */
7315 #endif /* IPV6_SUPPORTED */
7319 #if (ERRCLASS & ERRCLS_INT_PAR)
7320 /* error check on parameters */
7321 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) ||
7322 (info == NULLP) || (data == NULLP) ||
7323 (dataPos < 0) || (dataLen < 0))
7327 #endif /* ERRCLASS & ERRCLS_INT_PAR */
7329 /* check if there are some datas */
7330 if (sockFd->blocking)
7337 /* poll (non-blocking) */
7339 timeoutPtr = &timeout;
7341 CM_INET_FD_ZERO(&readFdS);
7342 CM_INET_FD_SET(sockFd, &readFdS);
7344 ret = cmInetSelect(&readFdS, NULLP, timeoutPtr, &numFdS);
7345 if (CM_INET_FD_ISSET(sockFd, &readFdS))
7347 /* get number of pending data */
7348 /* removed 3rd arg memInfo. MemInfo is no longer needed as we
7349 call ioctl for all sockets */
7350 ret = cmInetGetNumRead(sockFd, &pendLen);
7353 /* cm_inet_c_001.main_50
7354 * Return RCLOSED if cmInetGetNumRead returns RCLOSED. For other
7355 * errors just return RFAILED.
7363 /* check if connection got closed */
7367 /* cm_inet_c_001.main_50
7368 * Due to latency (mostly in solaris) sometimes ioctl(FIONREAD)
7369 * (inside cmInetGetNumRead) returns pend length as 0 on a TCP
7370 * socket that select says is ready to read. This should not be
7371 * considered as connection closed. So return ROKDNA instead of
7372 * RCLOSED even for TCP sockets
7376 /* added check for TCP/UDP socket. Pending data len in the socket
7377 recv buffer is determined by ioctl call in cmInetGetNumRead.
7378 For TCP it can't be > CM_INET_MAX_MSG_LEN.
7379 For UDP it can't be > CM_INET_MAX_UDPRAW_MSGSIZE. */
7380 if (sockFd->type == CM_INET_STREAM)
7382 /* max message length is limited to control the memory usage */
7383 if (pendLen > CM_INET_MAX_MSG_LEN)
7384 pendLen = CM_INET_MAX_MSG_LEN;
7385 /* In STREAM remote address is not required */
7390 if (pendLen > CM_INET_MAX_UDPRAW_MSGSIZE)
7391 pendLen = CM_INET_MAX_UDPRAW_MSGSIZE;
7393 remAddrLen = sizeof(CmInetSockAddr);
7396 /* check if there are enough pending data to read */
7397 bufLen = dataPos + dataLen;
7399 /* check if fromAddr is present or not */
7400 if (fromAddr != NULLP)
7402 remAddrLen = sizeof(remSockAddr);
7409 /* cm_inet_c_001.main_58: Fix for g++ compilation warning */
7410 if ((MsgLen)pendLen >= bufLen)
7412 /* allocate receive buffer (flat structure) */
7413 ret = SGetSBuf(info->region, info->pool, &recvBuf, bufLen);
7419 /* added different recvfrom calls with
7420 * different 6th arg for different OS */
7422 /* If remAddrLen is 0, pass NULLP */
7423 #if( defined(SS_VW) || defined(HPOS) || defined(SS_PS))
7425 recvLen = recvfrom(sockFd->fd,(S8*)recvBuf, bufLen,
7426 CM_INET_MSG_PEEK, &remSockAddr, (int*)&remAddrLen);
7428 recvLen = recvfrom(sockFd->fd,(S8*)recvBuf, bufLen,
7429 CM_INET_MSG_PEEK, NULLP, (int*)&remAddrLen);
7431 #if ( defined(SUNOS) || defined(SS_LINUX))
7433 recvLen = recvfrom(sockFd->fd, (S8*)recvBuf,bufLen,
7434 CM_INET_MSG_PEEK, (struct sockaddr *)&remSockAddr,
7435 (socklen_t *)&remAddrLen);
7437 recvLen = recvfrom(sockFd->fd, (S8*)recvBuf,bufLen,
7438 CM_INET_MSG_PEEK, NULLP, (socklen_t *)&remAddrLen);
7441 recvLen = recvfrom(sockFd->fd,(S8*)recvBuf, bufLen,
7442 CM_INET_MSG_PEEK, &remSockAddr, (S32*)&remAddrLen);
7444 recvLen = recvfrom(sockFd->fd,(S8*)recvBuf, bufLen,
7445 CM_INET_MSG_PEEK, NULLP, (S32*)&remAddrLen);
7446 #endif /* defined(SUNOS) || defined(SS_LINUX) */
7447 #endif /* defined(SS_VW) || defined(HPOS) || defined(SS_PS) */
7449 /* removed the check of returned remAddrLen */
7450 if (recvLen == INET_ERR)
7453 /* moved cleanup here */
7454 SPutSBuf(info->region, info->pool, recvBuf, bufLen);
7456 /* added check ERR_WOULDBLOCK */
7457 if ((INET_ERR_CODE == ERR_AGAIN) ||
7458 (INET_ERR_CODE == ERR_WOULDBLOCK))
7464 /* moved up the cleanup */
7468 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
7469 /* cm_inet_c_001.main_62:Warning fix */
7470 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetPeek() Failed : error(%d), sockFd->fd(%ld)\n",
7471 INET_ERR_CODE, sockFd->fd);
7472 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET036, 0, prntBuf);
7474 /* cm_inet_c_001.main_62:Warning fix */
7475 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetPeek() Failed : error(%d), sockFd->fd(%d)\n",
7476 INET_ERR_CODE, sockFd->fd);
7477 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET036, 0, prntBuf);
7479 #endif /* CMINETDBG */
7481 if ((INET_ERR_CODE == ERR_CONNABORTED) ||
7482 (INET_ERR_CODE == ERR_CONNRESET))
7490 if (recvLen < (S32)bufLen) /* maybe happen */
7493 SPutSBuf(info->region, info->pool, recvBuf, bufLen);
7498 for (j = 0, i = dataPos; i < bufLen; j++, i++)
7499 data[j] = recvBuf[i];
7501 /* setup return destination Internet address */
7502 /* added the check of (remAddLen > 0) */
7503 if ((fromAddr != NULLP) && (remAddrLen > 0))
7505 #ifdef IPV6_SUPPORTED
7506 cmMemset((U8*)fromAddr, 0, sizeof(fromAddr));
7507 if (remAddrLen == sizeof(struct sockaddr_in6))
7509 remAddr6 = (struct sockaddr_in6 *)&remSockAddr;
7510 fromAddr->type = CM_INET_IPV6ADDR_TYPE;
7511 fromAddr->u.ipv6Addr.port =
7512 CM_INET_NTOH_U16(remAddr6->sin6_port);
7513 CM_INET_COPY_IPV6ADDR(&fromAddr->u.ipv6Addr.ipv6NetAddr,
7514 &remAddr6->sin6_addr);
7518 remAddr = (struct sockaddr_in *)&remSockAddr;
7519 fromAddr->type = CM_INET_IPV4ADDR_TYPE;
7520 fromAddr->u.ipv4Addr.port = CM_INET_NTOH_U16(remAddr->sin_port);
7521 fromAddr->u.ipv4Addr.address =
7522 CM_INET_NTOH_U32(remAddr->sin_addr.s_addr);
7525 remAddr = (struct sockaddr_in *)&remSockAddr;
7526 fromAddr->port = CM_INET_NTOH_U16(remAddr->sin_port);
7527 fromAddr->address = CM_INET_NTOH_U32(remAddr->sin_addr.s_addr);
7528 #endif /* IPV6_SUPPORTED */
7532 SPutSBuf(info->region, info->pool, recvBuf, bufLen);
7536 /* not enough data pending yet */
7542 /* no data pending */
7547 } /* end of cmInetPeek */
7554 * Desc: Close a socket gracefully.
7556 * Ret: ROK - successful
7566 PUBLIC S16 cmInetClose
7568 CmInetFd *sockFd /* socket file descriptor */
7571 PUBLIC S16 cmInetClose(sockFd)
7572 CmInetFd *sockFd; /* socket file descriptor */
7575 S32 ret; /* temporary return value */
7579 #if (ERRCLASS & ERRCLS_INT_PAR)
7580 /* error check on parameters */
7581 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd))
7585 #endif /* ERRCLASS & ERRCLS_INT_PAR */
7588 ret = closesocket(sockFd->fd);
7590 ret = close(sockFd->fd);
7592 if (ret == INET_ERR)
7596 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
7597 /* cm_inet_c_001.main_62:Warning fix */
7598 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetClose() Failed : error(%d), sockFd->fd(%ld)\n",
7599 INET_ERR_CODE, sockFd->fd);
7600 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET037, 0, prntBuf);
7602 /* cm_inet_c_001.main_62:Warning fix */
7603 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetClose() Failed : error(%d), sockFd->fd(%d)\n",
7604 INET_ERR_CODE, sockFd->fd);
7605 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET037, 0, prntBuf);
7606 #endif /*ALIGN_64BIT*/
7607 #endif /* CMINETDBG */
7612 } /* end of cmInetClose */
7617 * Fun: cmInetShutdown
7619 * Desc: Close an Internet connection with more control over the data of
7620 * the full-duplex connection.
7621 * Values for the howTo parameter:
7623 * CM_INET_SHTDWN_RECV - discard data in receive buffer
7624 * CM_INET_SHTDWN_SEND - discard data in transmit buffer
7625 * CM_INET_SHTDWN_BOTH - discard data in receive and transmit buffer
7627 * Ret: ROK - successful
7630 * Notes: This function does not free the socket descriptor but only closes the
7631 * connection (cmInetClose() has to be called afterwards).
7632 * No error is returned if the socket is not connected while calling
7640 PUBLIC S16 cmInetShutdown
7642 CmInetFd *sockFd, /* socket file descriptor */
7643 S32 howTo /* operation flag */
7646 PUBLIC S16 cmInetShutdown(sockFd, howTo)
7647 CmInetFd *sockFd; /* socket file descriptor */
7648 S32 howTo; /* operation flag */
7651 S32 ret; /* temporary return value */
7653 TRC2(cmInetShutdown);
7655 #if (ERRCLASS & ERRCLS_INT_PAR)
7656 /* error check on parameters */
7657 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd))
7661 #endif /* ERRCLASS & ERRCLS_INT_PAR */
7663 ret = shutdown(sockFd->fd, howTo);
7664 if (ret == INET_ERR)
7666 if (INET_ERR_CODE == ERR_NOTCONN)
7668 /* socket is not connected */
7676 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
7677 /* cm_inet_c_001.main_62:Warning fix */
7678 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetShutdown() Failed : error(%d),"
7679 " sockFd->fd(%ld)\n", INET_ERR_CODE, sockFd->fd);
7680 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET038, 0, prntBuf);
7682 /* cm_inet_c_001.main_62:Warning fix */
7683 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetShutdown() Failed : error(%d),"
7684 " sockFd->fd(%d)\n", INET_ERR_CODE, sockFd->fd);
7685 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET038, 0, prntBuf);
7686 #endif /*ALIGN_64BIT*/
7687 #endif /* CMINETDBG */
7693 } /* end of cmInetShutdown */
7700 * Desc: Allows multiplex i/o requests among multiple sockets.
7701 * If the parameter mSecTimeout points to a value of zero the
7702 * call immediatley returns (poll), if it is a null pointer, the
7703 * timeout is set to infinit.
7704 * numFdS returns the number of ready file descriptors contained
7705 * in the file descriptor sets
7707 * Ret: ROK - successful
7708 * RTIMEOUT - timout expired
7718 PUBLIC S16 cmInetSelect
7720 CmInetFdSet *readFdS, /* read socket descriptor file set */
7721 CmInetFdSet *writeFdS, /* write socket descriptor file set */
7722 U32 *mSecTimeout, /* timeout in msecs */
7723 S16 *numFdS /* number of ready descriptors */
7726 PUBLIC S16 cmInetSelect(readFdS, writeFdS, mSecTimeout, numFdS)
7727 CmInetFdSet *readFdS; /* read socket descriptor file set */
7728 CmInetFdSet *writeFdS; /* write socket descriptor file set */
7729 U32 *mSecTimeout; /* timeout in msecs */
7730 S16 *numFdS; /* number of ready descriptors */
7733 S32 ret; /* temporary return value */
7734 struct timeval timeout; /* timeout structure */
7735 struct timeval *timeoutPtr;
7738 #if (ERRCLASS & ERRCLS_INT_PAR)
7739 /* error check on parameters */
7740 if (numFdS == NULLP)
7744 #endif /* ERRCLASS & ERRCLS_INT_PAR */
7748 if (mSecTimeout != NULLP)
7750 timeout.tv_sec = *mSecTimeout / 1000;
7751 timeout.tv_usec = (*mSecTimeout % 1000) * 1000;
7752 timeoutPtr = &timeout;
7756 /* infinite timeout */
7762 timeout.tv_usec = 1;
7765 /* cm_inet_c_001.main_53 - Removed do-while loop */
7766 ret = select(FD_SETSIZE, readFdS, writeFdS, (fd_set*)0, timeoutPtr);
7768 /* cm_inet_c_001.main_53 - Return ROKDNA in case select was interrupted */
7769 if ((ret == INET_ERR) && (INET_ERR_CODE == ERR_EINTR))
7774 /* timeout occured */
7780 if (ret == INET_ERR)
7782 /* asa: Added a check for ERR_INVAL to return ROK
7783 * readFdS and writeFdS may be passed as NULL to
7784 * cmInetSelect() call
7786 switch(errCode = INET_ERR_CODE)
7793 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
7794 /* cm_inet_c_001.main_62:Warning fix */
7795 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSelect() Failed : error(%d)\n",
7797 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET039, 0, prntBuf);
7798 #endif /* CMINETDBG */
7801 } /* end of switch */
7804 /* return number of ready file descriptors */
7805 /* cm_inet_c_001.main_54: Fix for Klockworks issue */
7809 } /* end of cmInetSelect */
7816 * Desc: Sets a socket option.
7817 * The function supports following options:
7819 * CM_INET_OPT_BLOCK:
7820 * value: CM_INET_OPT_DISABLE non-blocking
7821 * value: CM_INET_OPT_ENABLE blocking
7823 * CM_INET_OPT_REUSEADDR:
7824 * value: CM_INET_OPT_ENABLE reuse address
7826 * CM_INET_OPT_BROADCAST:
7827 * value: CM_INET_OPT_DISABLE
7828 * value: CM_INET_OPT_ENABLE
7830 * CM_INET_OPT_KEEPALIVE:
7831 * value: CM_INET_OPT_DISABLE
7832 * value: CM_INET_OPT_ENABLE
7834 * CM_INET_OPT_RX_BUF_SIZE:
7835 * value: receive buffer size in bytes
7837 * CM_INET_OPT_TX_BUF_SIZE:
7838 * value: transmitter buffer size in bytes
7840 * CM_INET_OPT_ADD_MCAST_MBR:
7841 * value: address of CmInetMCastInf structure
7843 * CM_INET_OPT_DRP_MCAST_MBR:
7844 * value: address of CmInetMCastInf structure
7846 * CM_INET_OPT_TCP_NODELAY:
7847 * value: CM_INET_OPT_DISABLE
7848 * value: CM_INET_OPT_ENABLE
7850 * CM_INET_OPT_BSD_COMPAT: For Linux only
7851 * value: CM_INET_OPT_ENABLE
7852 * value: CM_INET_OPT_DISABLE
7854 * CM_INET_OPT_HDR_INCLD:
7855 * value: CM_INET_ENABLE
7856 * value: CM_INET_DISABLE
7858 * CM_INET_OPT_DONT_FRAGMENT:
7859 * value: CM_INET_OPT_ENABLE
7860 * value: CM_INET_DISABLE
7863 * value: Type of Service.
7866 * value: Time To Live.
7868 * CM_INET_OPT_IP_OPTIONS:
7869 * value: IPv4 header option value
7872 * CM_INET_OPT_IP_ROUTER_ALERT:
7873 * value: CM_INET_OPT_DISABLE
7874 * value: CM_INET_OPT_ENABLE
7876 * CM_INET_OPT_IPV4_PKTINFO
7877 * value: CM_INET_OPT_ENABLE
7878 * value: CM_INET_OPT_DISABLE
7880 * CM_INET_OPT_MCAST_LOOP:
7881 * value: CM_INET_OPT_DISABLE
7882 * value: CM_INET_OPT_ENABLE
7884 * CM_INET_OPT_MCAST_IF:
7885 * value: Address of interface.
7887 * CM_INET_OPT_MCAST_TTL:
7888 * value: TTL of the outgoing multicast packet.
7890 * The next options are defined only if IPV6 is
7893 * CM_INET_OPT_ADD_MCAST6_MBR:
7894 * value: address of CmInetMCastInf6 structure
7896 * CM_INET_OPT_DRP_MCAST6_MBR:
7897 * value: address of CmInetMCastInf6 structure
7899 * CM_INET_OPT_MCAST6_LOOP:
7900 * value: CM_INET_OPT_DISABLE
7901 * value: CM_INET_OPT_ENABLE
7903 * CM_INET_OPT_MCAST6_IF:
7904 * value: Interface index
7906 * CM_INET_OPT_MCAST6_HOPS:
7907 * value: multicast hop limit
7909 * CM_INET_OPT_RECVIPV6_HOPLIM:
7910 * value: CM_INET_OPT_ENABLE hop limit will be returned
7912 * value: CM_INET_OPT_DISABLE hop limit wont be returned
7915 * CM_INET_OPT_RECVIPV6_HBHOPTS:
7916 * value: CM_INET_OPT_ENABLE HBH Options will be returned
7918 * value: CM_INET_OPT_DISABLE HBH Options wont be returned
7921 * CM_INET_OPT_RECVIPV6_DSTOPTS:
7922 * value: CM_INET_OPT_ENABLE Dest Options will be returned
7924 * value: CM_INET_OPT_DISABLE Dest Options wont be returned
7927 * CM_INET_OPT_RECVIPV6_RTHDR:
7928 * value: CM_INET_OPT_ENABLE Route Hdr Opt will be turned
7930 * value: CM_INET_OPT_DISABLE Route Hdr Opt will be turned
7931 * OFF on the socket.
7933 * CM_INET_OPT_IP_ROUTER_ALERT6
7934 * value: CM_INET_OPT_ENABLE
7935 * value: CM_INET_OPT_DISABLE
7937 * CM_INET_OPT_IPV6_PKTINFO
7938 * value: CM_INET_OPT_ENABLE Enable sending and receiving
7940 * value: CM_INET_OPT_DISABLE Disable sending and receiving
7943 * CM_INET_OPT_LINGER
7944 * value: address of CmInetSockLinger structure
7946 * CM_INET_OPT_SCTP_EVENTS
7947 * value: address of CmInetSctpSockEvent structure
7949 * CM_INET_OPT_SCTP_PRIM_ADDR
7950 * value: address of CmInetSctpPrimAddr structure
7952 * CM_INET_OPT_SCTP_PEERADDR_PARAMS
7953 * value: address of CmInetSctpPeerAddrParams structure
7956 * Ret: ROK - successful
7958 * RNA - failed, option not available
7959 * (Only when CM_INET2 is defined)
7961 * Notes: The send and receive buffer size may be system
7962 * specific. The cmInetSetOpt() call may return
7963 * successfuly although not the entire buffer size
7970 PUBLIC S16 cmInetSetOpt
7972 CmInetFd *sockFd, /* socket file descriptor */
7973 U32 level, /* option level */
7974 U32 type, /* option type */
7975 Ptr value /* option value */
7978 PUBLIC S16 cmInetSetOpt(sockFd, level, type, value)
7979 CmInetFd *sockFd; /* socket file descriptor */
7980 U32 level; /* option level */
7981 U32 type; /* option type */
7982 Ptr value; /* option value */
7985 S32 ret = ROK; /* temporary return value */
7986 U32 disable = 0; /* disable option */
7987 U32 enable = 1; /* enable option */
7989 /* added for IPv4 options */
7990 #ifdef IPV4_OPTS_SUPPORTED
7991 #if((!defined (SS_VW)) && (!defined(SS_LINUX)))
7992 TknStr64 *tempTknStr64; /* points TknStr64 structure */
7993 /* which has value for IPv4 hdr options.*/
7994 #endif /* SS_VW && SS_LINUX */
7998 #endif /* IPV4_OPTS_SUPPORTED */
8000 #if (defined(SUNOS)|| defined(WIN32) || defined(SS_PS) || defined(SS_VW_MCAST)\
8002 U8 lpEnable = 1; /* multicast loop enable */
8003 U8 lpDisable = 0; /* multicast loop disable */
8004 #endif /* SUNOS || WIN32 || SS_PS || SS_VW_MCAST || HPOS */
8007 BOOL boolEnable = TRUE; /* enable option */
8008 BOOL boolDisable = FALSE; /* disable option */
8011 #if (defined(SUNOS) || defined(WIN32) || defined(SS_PS) || \
8012 defined(SS_VW_MCAST) || defined(HPOS))
8013 struct ip_mreq stMreq;
8014 CmInetMCastInf *mCast;
8015 #endif /* SUNOS || WIN32 || SS_PS || SS_VW_MCAST || HPOS */
8017 #ifdef IPV6_SUPPORTED
8018 U32 loopEna = 1; /* IPv6 multicast loop enable */
8019 U32 loopDis = 0; /* IPv6 multicast loop disable */
8020 struct ipv6_mreq *stMreq6Ptr;
8021 /* cm_inet_c_001.main_44 : some operating system doesnt have icmp6_filter. so
8022 this flag is gaurded under ICMPV6_FILTER_SUPPORTED. so if user want this
8023 support he has to enable the above flag.*/
8024 /* cm_inet_c_001.main_58 : Protaected under flag CM_ICMP_FILTER_SUPPORT
8025 * to support filteration of ICMP messages */
8026 #if (defined(ICMPV6_FILTER_SUPPORTED) || defined(CM_ICMP_FILTER_SUPPORT))
8027 struct icmp6_filter *icmp6Filter;
8028 #endif /* ICMPV6_FILTER_SUPPORTED */
8029 #endif /* IPV6_SUPPORTED */
8031 /* cm_inet_c_001.main_58 : Added new local variables to support filteration
8032 * of ICMP messages */
8034 #ifdef CM_ICMP_FILTER_SUPPORT
8035 struct icmp_filter icmpFilter;
8039 /*cm_inet_c_001.main_38 Updated for TUCL 2.1 Release (Kernel SCTP Support) */
8042 struct sctp_event_subscribe event;
8043 struct sctp_paddrparams addrParams;
8044 struct sctp_setprim setPrim;
8045 struct sockaddr_in *pAddr;
8046 struct sctp_assocparams assocParams;
8047 struct sctp_initmsg initmsg;
8048 struct sctp_rtoinfo rtoinfo;
8049 #ifdef IPV6_SUPPORTED
8050 struct sockaddr_in6 *pAddr6;
8051 #endif /* IPV6_SUPPORTED */
8053 CmInetSockLinger *pSockLinger;
8054 CmInetSctpSockEvent *pSctpEvent;
8055 CmInetSctpPrimAddr *pSctpPrimAddr;
8056 CmInetSctpPeerAddrParams *pSctpPAddrParams;
8057 CmInetSctpRtoInfo *pSctpRtoInfo;
8058 CmInetSctpInitMsg *pSctpInitMsg;
8059 CmInetSctpAssocParams *pSctpAssocParams;
8066 /* cm_inet_c_001.main_58 : Added NULL check for value field */
8072 #if (ERRCLASS & ERRCLS_INT_PAR)
8073 /* error check on parameters */
8074 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd))
8078 #endif /* ERRCLASS & ERRCLS_INT_PAR */
8082 case CM_INET_OPT_BLOCK:
8083 optVal = (U32*)value;
8086 case CM_INET_OPT_ENABLE:
8089 /* cm_inet_c_001.main_59: Fix for compilation warning */
8090 ret = ioctlsocket(sockFd->fd, FIONBIO, (U32 *)&disable);
8093 ret = ioctl(sockFd->fd, FIONBIO, (char*)&disable);
8096 ret = ioctl(sockFd->fd, (S32)FIONBIO, (S32)&disable);
8098 ret = ioctl(sockFd->fd, (S32)FIONBIO, &disable);
8103 sockFd->blocking = 1;
8106 case CM_INET_OPT_DISABLE:
8108 /* cm_inet_c_001.main_59: Fix for compilation warning */
8109 ret = ioctlsocket(sockFd->fd, FIONBIO, (U32 *)&enable);
8112 ret = ioctl(sockFd->fd, FIONBIO, (char*)&enable);
8115 ret = ioctl(sockFd->fd, (S32)FIONBIO, (S32)&enable);
8117 ret = ioctl(sockFd->fd, (S32)FIONBIO, &enable);
8121 sockFd->blocking = 0;
8131 case CM_INET_OPT_REUSEADDR:
8132 optVal = (U32*)value;
8133 if (*optVal == CM_INET_OPT_ENABLE)
8136 ret = setsockopt(sockFd->fd, level, SO_REUSEADDR,
8137 (char*)&boolEnable, sizeof(boolEnable));
8139 ret = setsockopt(sockFd->fd, level, SO_REUSEADDR,
8140 (char*)&enable, sizeof(enable));
8142 setsockopt(sockFd->fd, level, SO_REUSEPORT,
8143 (char*)&enable, sizeof(enable));
8147 else if (*optVal == CM_INET_OPT_DISABLE)
8150 ret = setsockopt(sockFd->fd, level, SO_REUSEADDR,
8151 (char*)&boolDisable, sizeof(boolDisable));
8153 ret = setsockopt(sockFd->fd, level, SO_REUSEADDR,
8154 (char*)&disable, sizeof(disable));
8156 ret = setsockopt(sockFd->fd, level, SO_REUSEPORT,
8157 (char*)&disable, sizeof(disable));
8163 case CM_INET_OPT_BROADCAST:
8164 optVal = (U32*)value;
8165 if (*optVal == CM_INET_OPT_ENABLE)
8168 ret = setsockopt(sockFd->fd, level, SO_BROADCAST,
8169 (char*)&boolEnable, sizeof(boolEnable));
8171 ret = setsockopt(sockFd->fd, level, SO_BROADCAST,
8172 (char*)&enable, sizeof(enable));
8175 else if (*optVal == CM_INET_OPT_DISABLE)
8178 ret = setsockopt(sockFd->fd, level, SO_BROADCAST,
8179 (char*)&boolDisable, sizeof(boolDisable));
8181 ret = setsockopt(sockFd->fd, level, SO_BROADCAST,
8182 (char*)&disable, sizeof(disable));
8187 case CM_INET_OPT_KEEPALIVE:
8188 optVal = (U32*)value;
8189 if (*optVal == CM_INET_OPT_ENABLE)
8192 ret = setsockopt(sockFd->fd, level, SO_KEEPALIVE,
8193 (char*)&boolEnable, sizeof(boolEnable));
8195 ret = setsockopt(sockFd->fd, level, SO_KEEPALIVE,
8196 (char*)&enable, sizeof(enable));
8199 else if (*optVal == CM_INET_OPT_DISABLE)
8202 ret = setsockopt(sockFd->fd, level, SO_KEEPALIVE,
8203 (char*)&boolDisable, sizeof(boolDisable));
8205 ret = setsockopt(sockFd->fd, level, SO_KEEPALIVE,
8206 (char*)&disable, sizeof(disable));
8211 case CM_INET_OPT_RX_BUF_SIZE:
8212 optVal = (U32*)value;
8213 ret = setsockopt(sockFd->fd, level, SO_RCVBUF,
8214 (char*)optVal, sizeof(*optVal));
8217 case CM_INET_OPT_TX_BUF_SIZE:
8218 optVal = (U32*)value;
8219 ret = setsockopt(sockFd->fd, level, SO_SNDBUF,
8220 (char*)optVal, sizeof(*optVal));
8223 case CM_INET_OPT_TCP_NODELAY:
8224 optVal = (U32*)value;
8225 if (*optVal == CM_INET_OPT_ENABLE)
8229 ret = setsockopt(sockFd->fd, level, TCP_NODELAY,
8230 (char*)&boolEnable, sizeof(boolEnable));
8231 #endif /* SS_WINCE */
8233 ret = setsockopt(sockFd->fd, level, TCP_NODELAY,
8234 (char*)&enable, sizeof(enable));
8237 else if (*optVal == CM_INET_OPT_DISABLE)
8241 ret = setsockopt(sockFd->fd, level, TCP_NODELAY,
8242 (char*)&boolDisable, sizeof(boolDisable));
8243 #endif /* SS_WINCE */
8245 ret = setsockopt(sockFd->fd, level, TCP_NODELAY,
8246 (char*)&disable, sizeof(disable));
8251 #if (defined(SUNOS)|| defined(WIN32) || defined(SS_PS) || \
8252 defined(SS_VW_MCAST) || defined(HPOS))
8254 case CM_INET_OPT_ADD_MCAST_MBR:
8255 mCast = (CmInetMCastInf*)value;
8257 /* Copy the addresses to stMreq structure */
8259 stMreq.imr_mcastaddr.s_addr = CM_INET_HTON_U32(mCast->mCastAddr);
8261 stMreq.imr_multiaddr.s_addr = CM_INET_HTON_U32(mCast->mCastAddr);
8263 stMreq.imr_interface.s_addr = CM_INET_HTON_U32(mCast->localAddr);
8265 ret = setsockopt(sockFd->fd, level, IP_ADD_MEMBERSHIP,
8266 (char*)&stMreq, sizeof(stMreq));
8269 case CM_INET_OPT_DRP_MCAST_MBR:
8270 mCast = (CmInetMCastInf*)value;
8272 /* Copy the addresses to stMreq structure */
8274 stMreq.imr_mcastaddr.s_addr = CM_INET_HTON_U32(mCast->mCastAddr);
8276 stMreq.imr_multiaddr.s_addr = CM_INET_HTON_U32(mCast->mCastAddr);
8278 stMreq.imr_interface.s_addr = CM_INET_HTON_U32(mCast->localAddr);
8280 ret = setsockopt(sockFd->fd, level, IP_DROP_MEMBERSHIP,
8281 (char*)&stMreq, sizeof(stMreq));
8284 #endif /* SUNOS || WIN32 || SS_PS || SS_VW_MCAST || HPOS */
8287 /* cm_inet_c_001.main_37 - Enable CMINET_BSDCOMPAT flag if system doesnt
8288 support CM_INET_OPT_BSD_COMPAT */
8289 #ifndef CMINET_BSDCOMPAT
8290 case CM_INET_OPT_BSD_COMPAT:
8291 optVal = (U32*)value;
8292 if (*optVal == CM_INET_OPT_ENABLE)
8294 ret = setsockopt(sockFd->fd, level, SO_BSDCOMPAT,
8295 &enable, sizeof(enable));
8297 else if (*optVal == CM_INET_OPT_DISABLE)
8299 ret = setsockopt(sockFd->fd, level, SO_BSDCOMPAT,
8300 &disable, sizeof(disable));
8303 #endif /* CMINET_BSDCOMPAT */
8304 #endif /* SS_LINUX */
8307 /* Added for support of Raw socket modify according to the
8308 * option available on different platform */
8309 #if (defined(SUNOS)|| defined(WIN32) || defined(SS_PS) || defined(SS_VW) \
8311 case CM_INET_OPT_HDR_INCLD:
8312 optVal = (U32*)value;
8313 if (*optVal == CM_INET_OPT_ENABLE)
8318 ret = setsockopt(sockFd->fd, level, IP_HDRINCL,
8319 (char*)&enable, sizeof(enable));
8322 else if (*optVal == CM_INET_OPT_DISABLE)
8327 ret = setsockopt(sockFd->fd, level, IP_HDRINCL,
8328 (char*)&disable, sizeof(disable));
8333 /* added new options */
8334 #ifdef IPV4_OPTS_SUPPORTED
8336 /* Linux: set Router Alert socket option to Intercept RAW RSVP
8337 packets at the Intermediate node(Router) with Router Alert SET.
8338 This socket option is MUST be set (when this server is opened)
8339 if the RSVP server wants to intercept raw RSVP packets. */
8340 case CM_INET_OPT_IP_ROUTER_ALERT:
8341 optVal = (U32*)value;
8342 if (*optVal == CM_INET_OPT_ENABLE)
8344 ret = setsockopt(sockFd->fd, level, IP_ROUTER_ALERT,
8345 (char*)&enable, sizeof(enable));
8349 else if (*optVal == CM_INET_OPT_DISABLE)
8351 ret = setsockopt(sockFd->fd, level, IP_ROUTER_ALERT,
8352 (char*)&disable, sizeof(disable));
8357 #endif /* SS_LINUX */
8359 /* set Router Alert socket option */
8360 case CM_INET_OPT_IP_OPTIONS:
8361 #if (defined (SS_VW) || defined(SS_LINUX))
8364 tempTknStr64=(TknStr64 *)value;
8365 if (tempTknStr64->pres == TRUE)
8367 if (tempTknStr64->len == 0)
8369 /* disable the IP_OPTIONS for Router Alert. */
8371 ret = setsockopt(sockFd->fd, level, IP_OPTIONS,
8372 (CONSTANT char *)&disableOpt, sizeof(int));
8374 ret = setsockopt(sockFd->fd, level, IP_OPTIONS, NULL, 0);
8378 /* enable the IP_OPTIONS for Router Alert */
8379 ret = setsockopt(sockFd->fd, level, IP_OPTIONS,
8380 (char *)tempTknStr64->val, tempTknStr64->len);
8383 RETVALUE(RFAILED); /* Trying to set IPv4 Hdr option
8384 * without giving option values*/
8385 #endif /* SS_VW || SS_LINUX */
8387 #endif /* IPV4_OPTS_SUPPORTED */
8389 /* added new options */
8390 #if (defined(SS_LINUX) && (!defined(SS_VW) && !defined(WIN32)))
8392 case CM_INET_OPT_IPV4_PKTINFO:
8393 optVal = (U32*)value;
8394 if (*optVal == CM_INET_OPT_ENABLE)
8396 /* set IP_PKTINFO option when IP_ROUTER_ALERT is set in linux */
8397 ret = setsockopt(sockFd->fd, level, IP_PKTINFO,
8398 (char*)&enable, sizeof(enable));
8403 else if (*optVal == CM_INET_OPT_DISABLE)
8405 /* disable IP_PKTINFO when IP_ROUTER_ALERT is set in linux */
8406 ret = setsockopt(sockFd->fd, level, IP_PKTINFO,
8407 (char*)&disable, sizeof(disable));
8413 #endif /* LOCAL_INTF */
8414 #endif /* SS_LINUX */
8416 #endif /* SUNOS || WIN32 || SS_PS || SS_VW || HPOS */
8418 case CM_INET_OPT_DONTFRAGMENT:
8419 optVal = (U32*)value;
8420 if (*optVal == CM_INET_OPT_ENABLE)
8423 ret = setsockopt(sockFd->fd, level, IP_DONTFRAGMENT,
8424 (char*)&boolEnable, sizeof(boolEnable));
8427 else if (*optVal == CM_INET_OPT_DISABLE)
8430 ret = setsockopt(sockFd->fd, level, IP_DONTFRAGMENT,
8431 (char*)&boolDisable, sizeof(boolDisable));
8436 /* also add these 2 options for VxWorks */
8437 #if (defined(SUNOS)|| defined(WIN32) || defined(HPOS) || defined(SS_VW))
8438 case CM_INET_OPT_TOS:
8439 optVal = (U32*)value;
8440 ret = setsockopt(sockFd->fd, level, IP_TOS,
8441 (char*)optVal, sizeof(*optVal));
8444 case CM_INET_OPT_TTL:
8445 optVal = (U32*)value;
8446 ret = setsockopt(sockFd->fd, level, IP_TTL,
8447 (char*)optVal, sizeof(*optVal));
8449 #endif /* SUNOS || WIN32 || HPOS || SS_VW */
8450 #endif /* CM_INET2 */
8452 #if (defined(SUNOS)|| defined(WIN32) || defined(SS_PS) || defined(SS_VW_MCAST) \
8454 case CM_INET_OPT_MCAST_LOOP:
8455 optVal = (U32*)value;
8456 if (*optVal == CM_INET_OPT_ENABLE)
8459 ret = setsockopt(sockFd->fd, level, IP_MULTICAST_LOOP,
8460 (char *)&lpEnable, sizeof(lpEnable));
8462 ret = setsockopt(sockFd->fd, level, IP_MULTICAST_LOOP,
8463 (CONSTANT char *)&lpEnable, sizeof(lpEnable));
8469 ret = setsockopt(sockFd->fd, level, IP_MULTICAST_LOOP,
8470 (char *)&lpDisable, sizeof(lpDisable));
8472 ret = setsockopt(sockFd->fd, level, IP_MULTICAST_LOOP,
8473 (CONSTANT char *)&lpDisable, sizeof(lpDisable));
8478 case CM_INET_OPT_MCAST_IF:
8479 optVal = (U32*)value;
8480 *optVal = CM_INET_HTON_U32((U32)*optVal);
8481 ret = setsockopt(sockFd->fd, level, IP_MULTICAST_IF,
8482 (char *)optVal, sizeof(struct in_addr));
8485 case CM_INET_OPT_MCAST_TTL:
8486 optVal = (U32*)value;
8487 /* remove CONSTANT in setsockopt for VW */
8489 ret = setsockopt(sockFd->fd, level, IP_MULTICAST_TTL,
8490 (char *)optVal, sizeof(U8));
8492 ret = setsockopt(sockFd->fd, level, IP_MULTICAST_TTL,
8493 (CONSTANT char *)optVal, sizeof(U8));
8496 #endif /* SUNOS || WIN32 || SS_PS || SS_VW_MCAST || HPOS */
8498 #ifdef IPV6_SUPPORTED
8499 case CM_INET_OPT_IPV6_TTL:
8500 optVal = (U32*)value;
8501 ret = setsockopt(sockFd->fd, level, IPV6_UNICAST_HOPS,
8502 (char*)optVal, sizeof(*optVal));
8505 case CM_INET_OPT_ADD_MCAST6_MBR:
8506 stMreq6Ptr = (struct ipv6_mreq *)value;
8507 ret = setsockopt(sockFd->fd, level, IPV6_JOIN_GROUP,
8508 (char*)stMreq6Ptr, sizeof(struct ipv6_mreq));
8511 case CM_INET_OPT_DRP_MCAST6_MBR:
8512 stMreq6Ptr = (struct ipv6_mreq *)value;
8513 ret = setsockopt(sockFd->fd, level, IPV6_LEAVE_GROUP,
8514 (char*)stMreq6Ptr, sizeof(struct ipv6_mreq));
8517 case CM_INET_OPT_MCAST6_LOOP:
8518 optVal = (U32*)value;
8519 if (*optVal == CM_INET_OPT_ENABLE)
8521 ret = setsockopt(sockFd->fd, level, IPV6_MULTICAST_LOOP,
8522 &loopEna, sizeof(loopEna));
8526 ret = setsockopt(sockFd->fd, level, IPV6_MULTICAST_LOOP,
8527 &loopDis, sizeof(loopDis));
8531 case CM_INET_OPT_MCAST6_IF:
8532 ret = setsockopt(sockFd->fd, level, IPV6_MULTICAST_IF,
8533 (U32 *)value, sizeof(U32));
8536 case CM_INET_OPT_MCAST6_HOPS:
8537 optVal = (U32*)value;
8538 ret = setsockopt(sockFd->fd, level, IPV6_MULTICAST_HOPS,
8539 (char *)optVal, sizeof(U32));
8542 /* cm_inet_c_001.main_44 : some operating system doesnt have icmp6_filter. so
8543 this flag is gaurded under ICMPV6_SUPPORTED. so if user want this
8544 support he has to enable the above flag.*/
8545 /* cm_inet_c_001.main_58 : Protaected under flag CM_ICMP_FILTER_SUPPORT
8546 * to support filteration of ICMP messages */
8547 #if (defined(ICMPV6_FILTER_SUPPORTED) || defined(CM_ICMP_FILTER_SUPPORT))
8548 case CM_INET_OPT_ICMP6_FILTER:
8549 icmp6Filter = (struct icmp6_filter *)value;
8550 ret = setsockopt(sockFd->fd, level, ICMP6_FILTER,
8551 (char *)icmp6Filter, sizeof(struct icmp6_filter));
8553 #endif /* ICMPV6_FILTER_SUPPORTED */
8555 /* added new options */
8556 #ifdef IPV6_OPTS_SUPPORTED
8557 case CM_INET_OPT_RECVIPV6_HOPLIM:
8558 optVal = (U32*)value;
8560 ret = setsockopt(sockFd->fd, level, IPV6_HOPLIMIT,
8561 (char *)optVal, sizeof(U32));
8563 ret = setsockopt(sockFd->fd, level, IPV6_HOPLIMIT,
8564 (char *)optVal, sizeof(U32));
8565 /* enable the reception of IPv6 HopLimit value as ancillary data */
8566 ret = setsockopt(sockFd->fd, level, IPV6_RECVHOPLIMIT,
8567 (char*)&enable, sizeof(enable));
8568 #endif /* SS_LINUX */
8572 case CM_INET_OPT_RECVIPV6_HBHOPTS:
8573 optVal = (U32*)value;
8575 ret = setsockopt(sockFd->fd, level, IPV6_HOPOPTS,
8576 (char *)optVal, sizeof(U32));
8578 ret = setsockopt(sockFd->fd, level, IPV6_RECVHOPOPTS,
8579 (char *)optVal, sizeof(U32));
8580 #endif /* SS_LINUX */
8583 case CM_INET_OPT_RECVIPV6_DSTOPTS:
8584 optVal = (U32*)value;
8586 ret = setsockopt(sockFd->fd, level, IPV6_DSTOPTS,
8587 (char *)optVal, sizeof(U32));
8589 ret = setsockopt(sockFd->fd, level, IPV6_RECVDSTOPTS,
8590 (char *)optVal, sizeof(U32));
8591 #endif /* SS_LINUX */
8594 case CM_INET_OPT_RECVIPV6_RTHDR:
8595 optVal = (U32*)value;
8597 ret = setsockopt(sockFd->fd, level, IPV6_RTHDR,
8598 (char *)optVal, sizeof(U32));
8600 ret = setsockopt(sockFd->fd, level, IPV6_RECVRTHDR,
8601 (char *)optVal, sizeof(U32));
8602 #endif /* SS_LINUX */
8605 /* works ONLY for IPPROTO_RAW type socket. so if it this socket
8606 * option is tried to set for IPPROTO_RSVP, then it is supposed
8607 * to fail with EINVAL according to net/ipv6/ipv6_sockglue.c
8609 * if HI_SRVC_RAW_RAW is not used during ServOpenReq as the server
8610 * type, then it will fail here due to above reason */
8612 case CM_INET_OPT_IP_ROUTER_ALERT6:
8613 optVal = (U32*)value;
8614 if(*optVal == CM_INET_OPT_ENABLE)
8615 ret = setsockopt(sockFd->fd, IPPROTO_IPV6, IPV6_ROUTER_ALERT,
8616 (char *)&enable, sizeof(enable));
8618 ret = setsockopt(sockFd->fd, level, IPV6_ROUTER_ALERT,
8619 (char *)&disable, sizeof(disable));
8622 #endif /* SS_LINUX */
8623 #endif /* IPV6_OPTS_SUPPORTED */
8626 case CM_INET_OPT_IPV6_PKTINFO:
8627 optVal = (U32*)value;
8629 ret = setsockopt(sockFd->fd, level, IPV6_PKTINFO,
8630 (char *)optVal, sizeof(U32));
8632 ret = setsockopt(sockFd->fd, level, IPV6_RECVPKTINFO,
8633 (char *)&enable, sizeof(enable));
8634 #endif /* SS_LINUX */
8636 #endif /* LOCAL_INTF */
8638 #endif /* IPV6_SUPPORTED */
8640 /*cm_inet_c_001.main_38 Updated for TUCL 2.1 Release (Kernel SCTP Support) */
8642 case CM_INET_OPT_LINGER:
8643 pSockLinger = (CmInetSockLinger *)value;
8645 cmMemset((U8*)&lngr, 0, sizeof(struct linger));
8647 if (pSockLinger->enable == TRUE)
8652 lngr.l_linger = pSockLinger->lingerTime;
8653 ret = setsockopt(sockFd->fd, level, SO_LINGER, &lngr, sizeof(lngr));
8656 case CM_INET_OPT_SCTP_EVENTS:
8657 pSctpEvent = (CmInetSctpSockEvent *)value;
8659 cmMemset((U8*)&event, 0, sizeof(struct sctp_event_subscribe));
8661 if (pSctpEvent->dataIoEvent == TRUE)
8662 event.sctp_data_io_event = 1;
8664 if (pSctpEvent->associationEvent == TRUE)
8665 event.sctp_association_event = 1;
8667 if (pSctpEvent->addressEvent == TRUE)
8668 event.sctp_address_event = 1;
8670 if (pSctpEvent->sendFailureEvent == TRUE)
8671 event.sctp_send_failure_event = 1;
8673 if (pSctpEvent->peerErrorEvent == TRUE)
8674 event.sctp_peer_error_event = 1;
8676 if (pSctpEvent->shutdownEvent == TRUE)
8677 event.sctp_shutdown_event = 1;
8679 if (pSctpEvent->partialDeliveryEvent == TRUE)
8680 event.sctp_partial_delivery_event = 1;
8682 if (pSctpEvent->adaptationLayerEvent == TRUE)
8684 event.sctp_adaption_layer_event = 1;
8686 event.sctp_adaptation_layer_event = 1;
8689 ret = setsockopt(sockFd->fd, level, SCTP_EVENTS, &event, sizeof(event));
8692 case CM_INET_OPT_SCTP_PRIM_ADDR:
8693 pSctpPrimAddr = (CmInetSctpPrimAddr *)value;
8695 cmMemset((U8*)&setPrim, 0, sizeof(struct sctp_setprim));
8697 #ifdef IPV6_SUPPORTED
8698 if (pSctpPrimAddr->addr.type == CM_INET_IPV6ADDR_TYPE)
8700 if (sockFd->protType == AF_INET)
8704 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
8705 /* cm_inet_c_001.main_62:Warning fix */
8706 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "Invalid address: sockFd->protType(%d),"
8707 " sockFd->fd(%ld)\n", sockFd->protType, sockFd->fd);
8708 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET040, 0, prntBuf);
8710 /* cm_inet_c_001.main_62:Warning fix */
8711 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "Invalid address: sockFd->protType(%d),"
8712 " sockFd->fd(%d)\n", sockFd->protType, sockFd->fd);
8713 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET040, 0, prntBuf);
8714 #endif /*ALIGN_64BIT*/
8715 #endif /* CMINETDBG */
8719 pAddr6 = (struct sockaddr_in6*)&(setPrim.ssp_addr);
8720 pAddr6->sin6_family = AF_INET6;
8721 pAddr6->sin6_port = CM_INET_HTON_U16(pSctpPrimAddr->port);
8722 CM_INET_COPY_IPV6ADDR(&pAddr6->sin6_addr.s6_addr, &pSctpPrimAddr->addr.u.ipv6NetAddr);
8726 pAddr = (struct sockaddr_in*)&(setPrim.ssp_addr);
8727 pAddr->sin_family = AF_INET;
8728 pAddr->sin_port = CM_INET_HTON_U16(pSctpPrimAddr->port);
8729 pAddr->sin_addr.s_addr = CM_INET_HTON_U32(pSctpPrimAddr->addr.u.ipv4NetAddr);
8732 pAddr = (struct sockaddr_in*)&(setPrim.ssp_addr);
8733 pAddr->sin_family = AF_INET;
8734 pAddr->sin_port = CM_INET_HTON_U16(pSctpPrimAddr->port);
8735 pAddr->sin_addr.s_addr = CM_INET_HTON_U32(pSctpPrimAddr->addr.u.ipv4NetAddr);
8736 #endif /* IPV6_SUPPORTED */
8738 setPrim.ssp_assoc_id = pSctpPrimAddr->assocId;
8740 ret = setsockopt(sockFd->fd, level, SCTP_PRIMARY_ADDR, &setPrim, sizeof(setPrim));
8743 case CM_INET_OPT_SCTP_PEERADDR_PARAMS:
8744 pSctpPAddrParams = (CmInetSctpPeerAddrParams *)value;
8746 cmMemset((U8*)&addrParams, 0, sizeof(struct sctp_paddrparams));
8749 if (pSctpPAddrParams->s.addrPres == TRUE)
8751 #ifdef IPV6_SUPPORTED
8752 if (pSctpPAddrParams->s.addr.type == CM_INET_IPV6ADDR_TYPE)
8754 if (sockFd->protType == AF_INET)
8758 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
8759 /* cm_inet_c_001.main_62:Warning fix */
8760 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "Invalid address: sockFd->protType(%d),"
8761 " sockFd->fd(%ld)\n", sockFd->protType, sockFd->fd);
8762 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET041, 0, prntBuf);
8764 /* cm_inet_c_001.main_62:Warning fix */
8765 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "Invalid address: sockFd->protType(%d),"
8766 " sockFd->fd(%d)\n", sockFd->protType, sockFd->fd);
8767 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET041, 0, prntBuf);
8768 #endif /*ALIGN_64BIT*/
8769 #endif /* CMINETDBG */
8774 pAddr6 = (struct sockaddr_in6*)&(addrParams.spp_address);
8775 pAddr6->sin6_family = AF_INET6;
8776 pAddr6->sin6_port = CM_INET_HTON_U16(pSctpPAddrParams->s.port);
8777 CM_INET_COPY_IPV6ADDR(&pAddr6->sin6_addr.s6_addr, &pSctpPAddrParams->s.addr.u.ipv6NetAddr);
8781 pAddr = (struct sockaddr_in*)&(addrParams.spp_address);
8782 pAddr->sin_family = AF_INET;
8783 pAddr->sin_port = CM_INET_HTON_U16(pSctpPAddrParams->s.port);
8784 pAddr->sin_addr.s_addr = CM_INET_HTON_U32(pSctpPAddrParams->s.addr.u.ipv4NetAddr);
8787 pAddr = (struct sockaddr_in*)&(addrParams.spp_address);
8788 pAddr->sin_family = AF_INET;
8789 pAddr->sin_port = CM_INET_HTON_U16(pSctpPAddrParams->s.port);
8790 pAddr->sin_addr.s_addr = CM_INET_HTON_U32(pSctpPAddrParams->s.addr.u.ipv4NetAddr);
8791 #endif /* IPV6_SUPPORTED */
8795 #ifdef IPV6_SUPPORTED
8796 if (sockFd->protType == AF_INET6)
8797 addrParams.spp_address.ss_family = AF_INET6;
8799 addrParams.spp_address.ss_family = AF_INET;
8801 addrParams.spp_address.ss_family = AF_INET;
8805 /* Not validating the address, whether addr is a valid address or not */
8807 addrParams.spp_assoc_id = pSctpPAddrParams->assocId;
8808 /*cm_inet_c_001.main_58 : fix for klockwork issue */
8809 addrParams.spp_pathmaxrxt = (U16)pSctpPAddrParams->pathMaxRxt;
8811 if (pSctpPAddrParams->hbEnblFlag == CM_INET_OPT_ENABLE)
8812 addrParams.spp_hbinterval = pSctpPAddrParams->hbInterval;
8814 addrParams.spp_hbinterval = 0;
8817 addrParams.spp_flags = 0;
8819 if (pSctpPAddrParams->pmtudFlag == CM_INET_OPT_ENABLE)
8821 addrParams.spp_flags |= SPP_PMTUD_ENABLE;
8822 addrParams.spp_pathmtu = pSctpPAddrParams->pathMtu;
8824 else if(pSctpPAddrParams->pmtudFlag == CM_INET_OPT_DISABLE)
8825 addrParams.spp_flags |= SPP_PMTUD_DISABLE;
8827 if (pSctpPAddrParams->sackDelayFlag == CM_INET_OPT_ENABLE)
8829 addrParams.spp_flags |= SPP_SACKDELAY_ENABLE;
8830 addrParams.spp_sackdelay = pSctpPAddrParams->sackDelay;
8832 else if(pSctpPAddrParams->sackDelayFlag == CM_INET_OPT_DISABLE)
8833 addrParams.spp_flags |= SPP_SACKDELAY_DISABLE;
8835 if (pSctpPAddrParams->hbEnblFlag == CM_INET_OPT_ENABLE)
8837 addrParams.spp_flags |= SPP_HB_ENABLE;
8838 addrParams.spp_hbinterval = pSctpPAddrParams->hbInterval;
8840 else if(pSctpPAddrParams->hbEnblFlag == CM_INET_OPT_DISABLE)
8841 addrParams.spp_flags |= SPP_HB_DISABLE;
8843 ret = setsockopt(sockFd->fd, level, SCTP_PEER_ADDR_PARAMS, &addrParams, sizeof(addrParams));
8846 case CM_INET_OPT_SCTP_ASSOC_PARAMS:
8847 pSctpAssocParams = (CmInetSctpAssocParams *)value;
8849 cmMemset((U8*)&assocParams, 0, sizeof(struct sctp_assocparams));
8851 assocParams.sasoc_cookie_life = pSctpAssocParams->cookieLife;
8852 assocParams.sasoc_asocmaxrxt = pSctpAssocParams->assocMaxReTx;
8853 assocParams.sasoc_assoc_id = pSctpAssocParams->assocId;
8854 assocParams.sasoc_number_peer_destinations = pSctpAssocParams->numberOfPeerDest;
8855 assocParams.sasoc_peer_rwnd = pSctpAssocParams->peerRwnd;
8856 assocParams.sasoc_local_rwnd = pSctpAssocParams->localRwnd;
8858 ret = setsockopt(sockFd->fd, level, SCTP_ASSOCINFO, &assocParams, sizeof(assocParams));
8861 case CM_INET_OPT_SCTP_RTO_INFO:
8862 pSctpRtoInfo = (CmInetSctpRtoInfo *)value;
8864 cmMemset((U8*)&rtoinfo, 0, sizeof(struct sctp_rtoinfo));
8866 rtoinfo.srto_assoc_id = pSctpRtoInfo->assocId;
8867 rtoinfo.srto_initial = pSctpRtoInfo->rtoInitial;
8868 rtoinfo.srto_max = pSctpRtoInfo->rtoMax;
8869 rtoinfo.srto_min = pSctpRtoInfo->rtoMin;
8871 ret = setsockopt(sockFd->fd, level, SCTP_RTOINFO, &rtoinfo, sizeof(rtoinfo));
8874 case CM_INET_OPT_SCTP_INIT_MSG:
8875 pSctpInitMsg = (CmInetSctpInitMsg *)value;
8877 cmMemset((U8*)&initmsg, 0, sizeof(struct sctp_initmsg));
8879 initmsg.sinit_max_attempts = pSctpInitMsg->maxInitReTx;
8880 initmsg.sinit_max_init_timeo = pSctpInitMsg->maxInitTimeout;
8881 initmsg.sinit_num_ostreams = pSctpInitMsg->numOstreams;
8882 initmsg.sinit_max_instreams = pSctpInitMsg->maxInstreams;
8884 ret = setsockopt(sockFd->fd, level, SCTP_INITMSG, &initmsg, sizeof(initmsg));
8887 #endif /*CM_LKSCTP*/
8889 /* cm_inet_c_001.main_58 : Added to support filteration of ICMP
8890 * messages and protected under CM_ICMP_FILTER_SUPPORT flag. Its a
8891 * partial implementaion for icmp filter done for TUCL */
8893 #ifdef CM_ICMP_FILTER_SUPPORT
8894 case CM_INET_OPT_ICMP_FILTER:
8895 optVal = (U32*)value;
8896 ret = setsockopt(sockFd->fd, level, ICMP_FILTER,
8897 optVal, sizeof(icmpFilter));
8903 /* wrong socket option type */
8908 if (ret == INET_ERR)
8912 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
8913 /* cm_inet_c_001.main_62:Warning fix */
8914 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSetOpt() Failed : error(%d), sockFd->fd(%ld)\n",
8915 INET_ERR_CODE, sockFd->fd);
8916 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET042, 0, prntBuf);
8918 /* cm_inet_c_001.main_62:Warning fix */
8919 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetSetOpt() Failed : error(%d), sockFd->fd(%d)\n",
8920 INET_ERR_CODE, sockFd->fd);
8921 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET042, 0, prntBuf);
8922 #endif /*ALIGN_64BIT*/
8923 #endif /* CMINETDBG */
8927 } /* end of cmInetSetOpt */
8933 * Fun: cmInetGetNumRead
8935 * Desc: Gives the number of pending octets in the socket receive buffer.
8937 * Ret: ROK - successful
8947 PUBLIC S16 cmInetGetNumRead
8949 CmInetFd *sockFd, /* socket file descriptor */
8950 U32 *dataLen /* number of pending octets */
8951 /* removed 3rd argument memInfo */
8954 PUBLIC S16 cmInetGetNumRead(sockFd, dataLen)
8955 CmInetFd *sockFd; /* socket file descriptor */
8956 U32 *dataLen; /* number of pending octets */
8957 /* removed 3rd argument memInfo */
8960 S32 ret; /* temporary return value */
8962 /* removed local variables added for recvfrom call */
8964 TRC2(cmInetGetNumRead);
8966 #if (ERRCLASS & ERRCLS_INT_PAR)
8967 /* error check on parameters */
8968 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) ||
8975 /* use ioctl call for all types of socket to get length of
8976 pending data in the socket recv buffer */
8978 /* cm_inet_c_001.main_59: Fix for compilation warning */
8979 ret = ioctlsocket(sockFd->fd, FIONREAD, (U32 *)dataLen);
8982 ret = ioctl(sockFd->fd, FIOREAD, (char*)dataLen);
8985 ret = ioctl(sockFd->fd, FIONREAD, (S32)dataLen);
8987 ret = ioctl(sockFd->fd, FIONREAD, dataLen);
8992 /* For UDP socket assign the length of pending data in the
8993 socket recv buffer to largest datagram size.
8994 Removed recvfrom call & necessary processing for it. */
8996 if (ret == INET_ERR)
8998 /* removed error check CONABORTED added for recvfrom call.
8999 Also return value changed from RCLOSED to ROK */
9000 /* Check for reset connection */
9001 /* cm_inet_c_001.main_45: Close the TCP connection only when err is one of these*/
9002 if ((INET_ERR_CODE == ERR_CONNREFUSED) ||
9003 (INET_ERR_CODE == ERR_CONNABORTED) ||
9004 (INET_ERR_CODE == ERR_TIMEDOUT))
9008 /* cm_inet_c_001.main_50
9009 * Return RCLOSED instead of ROK to initiate connection closure.
9010 * ROK will be returned only if the ioctl call above returns ROK.
9011 * The routines calling this function have been modified to not
9012 * return RCLOSED when this function returns ROK with pending data
9013 * length value of 0. This modification is needed because:
9014 * Due to latency (mostly in solaris) sometimes ioctl(FIONREAD)
9015 * returns successfully with pend length as 0 on a TCP socket that
9016 * select says is ready to read. This should not be considered as
9017 * connection closed.
9022 /* removed error check ERR_WOULDBLOCK */
9023 /* cm_inet_c_001.main_45: Dont close the connection in case of ERR_CONNRESET */
9024 if ((INET_ERR_CODE == ERR_AGAIN) ||
9025 (INET_ERR_CODE == ERR_CONNRESET))
9032 /* cm_inet_c_001.main_45: Change 2048 to CM_INET_MAX_UDPRAW_MSGSIZE */
9033 *dataLen = CM_INET_MAX_UDPRAW_MSGSIZE;
9035 #endif /* SS_LINUX */
9037 /* removed error debug printing added for recvfrom call. */
9041 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
9042 /* cm_inet_c_001.main_62:Warning fix */
9043 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetGetNumRead() Failed : error(%d),"
9044 " sockFd->fd(%ld)\n", INET_ERR_CODE, sockFd->fd);
9045 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET043, 0, prntBuf);
9047 /* cm_inet_c_001.main_62:Warning fix */
9048 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetGetNumRead() Failed : error(%d),"
9049 " sockFd->fd(%d)\n", INET_ERR_CODE, sockFd->fd);
9050 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET043, 0, prntBuf);
9051 #endif /*ALIGN_64BIT*/
9052 #endif /* CMINETDBG */
9057 } /* end of cmInetGetNumRead */
9063 * Fun: cmInetGetHostByName
9065 * Desc: Resolves a host name into the appropriate 4 byte Internet
9068 * Ret: ROK - successful
9078 PUBLIC S16 cmInetGetHostByName
9080 S8 *hostName, /* host name */
9081 CmInetIpAddrTbl *addrTbl /* Address Table of IPV4 Addresses */
9084 PUBLIC S16 cmInetGetHostByName (hostName, addrTbl)
9085 S8 *hostName; /* host name */
9086 CmInetIpAddrTbl *addrTbl; /* Address Table of IPV4 Addresses */
9090 U8 numAddrs; /* Number of Addresses */
9093 #if (defined(WIN32) || defined(SS_LINUX) || defined(HPOS))
9094 struct hostent *hostid; /* pointer to host information */
9097 struct hostent hostid; /* host information */
9098 S8 infoBuf[CM_INET_MAX_INFO]; /* info buffer */
9099 S32 err; /* error code */
9101 #endif /* WIN32 || SS_LINUX || HPOS */
9103 TRC2(cmInetGetHostByName)
9105 #if (ERRCLASS & ERRCLS_INT_PAR)
9106 /* error check on parameters */
9107 if ((hostName == NULLP) || (addrTbl == NULLP))
9111 #endif /* ERRCLASS & ERRCLS_INT_PAR */
9120 #if (defined(WIN32) || defined(SS_LINUX) || defined(HPOS))
9121 hostid = gethostbyname(hostName);
9125 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
9126 /* cm_inet_c_001.main_62:Warning fix */
9127 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetGetHostByName() Failed : error(%d),"
9128 " hostName(%p)\n", INET_ERR_CODE, hostName);
9129 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET044, 0, prntBuf);
9130 #endif /* CMINETDBG */
9133 if (hostid->h_addrtype != AF_INET)
9136 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
9137 /* cm_inet_c_001.main_62:Warning fix */
9138 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetGetHostByName() Failed : error(%d),"
9139 " hostName(%p), hostid->h_addrtype(%d)\n",
9140 INET_ERR_CODE, hostName, hostid->h_addrtype);
9141 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET045, 0, prntBuf);
9142 #endif /* CMINETDBG */
9147 while ((numAddrs < CM_INET_IPV4_NUM_ADDR) &&
9148 (hostid->h_addr_list[numAddrs] != NULLP))
9150 addrTbl->netAddr[addrTbl->count++] =
9151 CM_INET_NTOH_U32 (*((U32 *) hostid->h_addr_list[numAddrs]));
9161 vwIpAddr = hostGetByName(hostName);
9162 if (vwIpAddr == INET_ERR)
9165 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
9166 /* cm_inet_c_001.main_62:Warning fix */
9167 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetGetHostByName() Failed : error(%d),"
9168 " hostName(%p)\n", INET_ERR_CODE, hostName);
9169 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET046, 0, prntBuf);
9170 #endif /* CMINETDBG */
9173 CM_COPY_VWIPADDR(vwIpAddr, &(addrTbl->netAddr[addrTbl->count]));
9178 err = 0; /* err is not reset by gethostnyname_r()! */
9180 gethostbyname_r(hostName, &hostid, infoBuf, CM_INET_MAX_INFO, (int*)&err);
9181 if ((hostid.h_addrtype != AF_INET) || (err < 0))
9184 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
9185 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetGetHostByName() Failed : error(%d), hostName(%p),"
9186 " hostid.h_addrtype(%d)\n",
9187 INET_ERR_CODE, hostName, hostid.h_addrtype);
9188 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET047, 0, prntBuf);
9189 #endif /* CMINETDBG */
9194 while ((numAddrs < CM_INET_IPV4_NUM_ADDR) &&
9195 (hostid.h_addr_list[numAddrs] != NULLP))
9197 addrTbl->netAddr[addrTbl->count++] =
9198 CM_INET_NTOH_U32 (*((U32 *) hostid.h_addr_list[numAddrs]));
9204 #endif /* WIN32 || SS_LINUX || HPOS */
9208 } /* end of cmInetGetHostByName */
9211 /* The getipnodebyname is not supported on all the Solaris Operating system
9212 * versions. This has to be supported on operating systems that support IPV6
9213 * as per the RFC on the IPV6 socket interface. Hence this function is moved
9214 * under the IPV6_SUPPORTED flag */
9216 /* This function now can be called for both IPv4 and IPv6. However, we will
9217 * call cmInetGetHostByName inside for IPv4. Move all flag dependencies
9218 * inside this function. */
9221 * Fun: cmInetGetIpNodeByName
9223 * Desc: Resolves a host name into the appropriate 4 byte Internet
9224 * address or into the appropriate 16 byte IPV6 address.
9225 * This function is expected to be thread safe and should be used
9226 * instead of the cmInetGetHostByName function.
9228 * Ret: ROK - successful
9237 PUBLIC S16 cmInetGetIpNodeByName
9239 S8 *hostName, /* host name */
9240 CmInetIpAddrArr *addrArr /* Array of addressed filled in */
9243 PUBLIC S16 cmInetGetIpNodeByName(hostName, addrArr)
9244 S8 *hostName; /* host name */
9245 CmInetIpAddrArr *addrArr; /* Array of addressed filled in */
9248 /* for return value from cmInetGetHostByName */
9249 #ifndef IPV6_SUPPORTED
9254 U8 numAddrs=0; /* Number of addresses */
9255 int err=0; /* error code */
9256 struct hostent *hostid; /* host information */
9257 #endif /* SS_LINUX */
9259 #endif /* IPV6_SUPPORTED */
9261 TRC2(cmInetGetIpNodeByName)
9264 #if (ERRCLASS & ERRCLS_INT_PAR)
9265 /* error check on parameters */
9266 if ((hostName == NULLP) || (addrArr == NULLP))
9270 #endif /* ERRCLASS & ERRCLS_INT_PAR */
9272 #ifdef IPV6_SUPPORTED
9276 #ifdef IPV6_SUPPORTED
9277 if (addrArr->type == CM_INET_IPV6ADDR_TYPE)
9278 hostid = getipnodebyname(hostName, AF_INET6, 0, &err);
9280 #endif /* IPV6_SUPPORTED */
9281 hostid = getipnodebyname(hostName, AF_INET, 0, &err);
9285 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
9286 /* cm_inet_c_001.main_62:Warning fix */
9287 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetGetIpNodeByName() Failed : error(%d),"
9288 " hostName(%p), addrArr->type(%d)n",
9289 err, hostName, addrArr->type);
9290 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET048, 0, prntBuf);
9291 #endif /* CMINETDBG */
9295 #ifdef IPV6_SUPPORTED
9296 if (addrArr->type == CM_INET_IPV6ADDR_TYPE)
9298 if (hostid->h_addrtype == AF_INET6)
9300 while ((numAddrs < CM_INET_IPV6_NUM_ADDR) &&
9301 (hostid->h_addr_list[numAddrs] != NULLP))
9303 /* Use the cminet fill macro here */
9304 CM_INET_COPY_IPV6ADDR(&addrArr->u.ipv6AddrArr.netAddr[numAddrs],
9305 hostid->h_addr_list[numAddrs]);
9306 addrArr->u.ipv6AddrArr.count++;
9313 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
9314 /* cm_inet_c_001.main_62:Warning fix */
9315 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetGetIpNodeByName() Failed : error(%d),"
9316 " hostName(%p), addrArr->type(%d),hostid->h_addrtype(%d) \n",
9317 err, hostName, addrArr->type, hostid->h_addrtype);
9318 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET049, 0, prntBuf);
9319 #endif /* CMINETDBG */
9324 #endif /* IPV6_SUPPORTED */
9326 if (hostid->h_addrtype == AF_INET)
9328 while ((numAddrs < CM_INET_IPV4_NUM_ADDR) &&
9329 (hostid->h_addr_list[numAddrs] != NULLP))
9331 addrArr->u.ipv4AddrArr.count ++;
9332 addrArr->u.ipv4AddrArr.netAddr[numAddrs] =
9333 CM_INET_NTOH_U32 (*((U32 *) hostid->h_addr_list[numAddrs]));
9340 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
9341 /* cm_inet_c_001.main_62:Warning fix */
9342 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetGetIpNodeByName() Failed : error(%d),"
9343 " hostName(%p), hostid->h_addrtype(%d), addrArr->type(%d)\n",
9344 err, hostName, hostid->h_addrtype, addrArr->type);
9345 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET050, 0, prntBuf);
9346 #endif /* CMINETDBG */
9350 #endif /* SS_LINUX */
9355 ret = cmInetGetHostByName(hostName, &addrArr->u.ipv4AddrArr);
9357 #endif /* IPV6_SUPPORTED */
9359 } /* end of cmInetGetIpNodeByName */
9366 * Desc: Converts an ASCII string containig an internet address
9367 * ("xxx.xxx.xxx.xxx") into a CmInetIpAddr (U32) format.
9368 * This function is a wrapper for the inet_addr() call.
9370 * Ret: ROK - successful
9380 PUBLIC S16 cmInetAddr(
9381 S8 *asciiAddr, /* ascii address representation */
9382 CmInetIpAddr *address /* 4 byte interent address */
9385 PUBLIC S16 cmInetAddr(asciiAddr, address)
9386 S8 *asciiAddr; /* ascii address representation */
9387 CmInetIpAddr *address; /* 4 byte interent address */
9392 #if (ERRCLASS & ERRCLS_INT_PAR)
9393 /* error check on parameters */
9394 if (asciiAddr == NULLP)
9398 #endif /* ERRCLASS & ERRCLS_INT_PAR */
9400 *address = inet_addr(asciiAddr);
9401 if (*address == (U32)ERR_INADDRNONE)
9403 /* asciiAddr does not contain a valid internet address */
9415 * Desc: Converts an CmInetIPAddr based IP address into a string
9416 * of the format "xxx.xxx.xxx.xxx".
9417 * This function is a wrapper for the inet_ntoa() call.
9419 * Ret: ROK - successful
9422 * Notes: This function delivers a pointer to a static buffer
9423 * within the system. Therefore the string has to be copied
9424 * by the caller before another call is made!
9431 PUBLIC S16 cmInetNtoa(
9432 CmInetIpAddr address, /* 4 byte interent address */
9433 S8 **asciiAddr /* ascii address representation */
9436 PUBLIC S16 cmInetNtoa(address, asciiAddr)
9437 CmInetIpAddr address; /* 4 byte interent address */
9438 S8 **asciiAddr; /* ascii address representation */
9441 struct in_addr inetAddr; /* internet address structure */
9445 #if (ERRCLASS & ERRCLS_INT_PAR)
9446 /* error check on parameters */
9447 if (asciiAddr == NULLP)
9451 #endif /* ERRCLASS & ERRCLS_INT_PAR */
9453 inetAddr.s_addr = address;
9455 *asciiAddr = inet_ntoa(inetAddr);
9456 if (*asciiAddr == NULL)
9467 * Desc: Converts an network address into a string.
9468 * This function is a wrapper for the inet_ntop() call.
9470 * Ret: ROK - successful
9473 * Notes: This function copies the resulting string to the buffer pointed to
9474 * by asciiaddr,which must be a non NULL pointer.The caller specifies
9475 * the number of bytes available in this buffer in the argument len.
9482 PUBLIC S16 cmInetNtop(
9483 U8 type, /* ip address type */
9484 Void *address, /* 4/16 byte interent address */
9485 S8 *asciiAddr, /* ascii adress representation */
9489 PUBLIC S16 cmInetNtop(type,address, asciiAddr,len)
9490 U8 type; /* ip address type */
9491 Void *address; /* 4/16 byte interent address */
9492 S8 *asciiAddr; /* ascii adress representation */
9500 #if (ERRCLASS & ERRCLS_INT_PAR)
9501 /* error check on parameters */
9502 if (asciiAddr == NULLP || address == NULLP || len == 0 )
9507 #endif /* ERRCLASS & ERRCLS_INT_PAR */
9510 case CM_INET_IPV4ADDR_TYPE :
9513 case CM_INET_IPV6ADDR_TYPE :
9517 if(inet_ntop(domain,address,asciiAddr,len) == NULL)
9526 /* The inet_pton is not supported on all the Solaris Operating system
9527 * versions. This has to be supported on operating systems that support
9528 * IPV6 as per the RFC on the IPV6 socket interface. Hence this function
9529 *is moved under the IPV6_SUPPORTED flag */
9530 #ifdef IPV6_SUPPORTED
9537 * Desc: Converts a IP address string to address.
9539 * Ret: ROK - successful
9549 PUBLIC S16 cmInetPton(
9550 CmInetIpAddr *address, /* 4 byte interent address */
9551 S8 *asciiAddr /* ascii address representation */
9554 PUBLIC S16 cmInetPton(address, asciiAddr)
9555 CmInetIpAddr *address; /* 4 byte interent address */
9556 S8 *asciiAddr; /* ascii address representation */
9563 #if (ERRCLASS & ERRCLS_INT_PAR)
9564 /* error check on parameters */
9565 if ((asciiAddr == NULLP) || (address == NULLP))
9569 #endif /* ERRCLASS & ERRCLS_INT_PAR */
9571 ret = inet_pton(AF_INET, asciiAddr, (void *)address);
9578 } /* end of cmInetPton */
9580 #endif /* IPV6_SUPPORTED */
9582 #ifdef IPV6_SUPPORTED
9588 * Desc: Converts a IP address string to IPV6 address suitable
9589 * to be used in bind.
9591 * Ret: ROK - successful
9600 PUBLIC S16 cmInetPton6(
9601 CmInetIpAddr6 *address6, /* 16 byte interent address */
9602 S8 *asciiAddr /* ascii address representation */
9605 PUBLIC S16 cmInetPton6(address6, asciiAddr)
9606 CmInetIpAddr6 *address6; /* 16 byte interent address */
9607 S8 *asciiAddr; /* ascii address representation */
9613 struct sockaddr_storage ss;
9614 U32 sslen = sizeof(ss);
9618 #if (ERRCLASS & ERRCLS_INT_PAR)
9619 /* error check on parameters */
9620 if ((asciiAddr == NULLP) || (address6 == NULLP))
9624 #endif /* ERRCLASS & ERRCLS_INT_PAR */
9627 ret = inet_pton(AF_INET6, asciiAddr, (void *)address6);
9633 /* cm_inet_c_001.main_44 : In windows inet_pton is not implemented. so we are using the below function
9634 * to convert the ipv6 address string to appropriate form */
9635 WSAStringToAddressA((LPTSTR)asciiAddr, AF_INET6, NULL, (struct sockaddr*)&ss, &sslen);
9636 cmMemcpy((U8*)address6, (U8*)&(((struct sockaddr_in6 *)&ss)->sin6_addr), sizeof(CmInetIpAddr6));
9640 } /* end of cmInetPton6 */
9641 #endif /* IPV6_SUPPORTED */
9647 * Fun: cmInetGetMemSize
9649 * Desc: This function gives the max number of static buffer space that
9650 * the internet library will allocate.
9652 * Ret: ROK - successful
9661 PUBLIC S16 cmInetGetMemSize(
9662 S32 *size /* max used memory size */
9665 PUBLIC S16 cmInetGetMemSize(size)
9666 S32 *size; /* max used memory size */
9670 /* max static memory size depends on max flat buffer size */
9671 *size = CM_INET_MAX_MSG_LEN;
9673 /* max static memory size depends on max flat buffer or iovect size */
9674 *size = CM_INET_MAX_MSG_LEN;
9686 * Desc: This function initializes the socket library.
9688 * Ret: ROK - successful
9690 * Notes: Required only for Winsock and not for 4.3BSD
9697 PUBLIC S16 cmInetInit(
9701 PUBLIC S16 cmInetInit(Void)
9709 version = MAKEWORD(CM_INET_HIGH_VER, CM_INET_LOW_VER);
9710 err = WSAStartup(version, &data);
9725 * Desc: This function de initializes the socket library. The
9726 * WINSOCK implementation de registers the application and
9727 * releases any resources allocated on behalf of the
9730 * Ret: ROK - successful
9732 * Notes: Required only for Winsock and not for 4.3BSD
9739 PUBLIC S16 cmInetDeInit(
9743 PUBLIC S16 cmInetDeInit(Void)
9757 }/* end of cmInetDeInit() */
9762 * Fun: cmInetGetSockName
9764 * Desc: This function is used to retireve the current name
9765 * for the specified socket descriptor. It returns the
9766 * local association(address and port) for the socket.
9768 * Ret: ROK - successful
9771 * Notes: Please note if the socket was bound to CM_INET_INADDR_ANY
9772 * cmInetGetSockName() will not necessarily return the local
9773 * address information unless the socket has been connected.
9780 PUBLIC S16 cmInetGetSockName
9782 CmInetFd *sockFd, /* socket file descriptor */
9786 PUBLIC S16 cmInetGetSockName(sockFd, locAddr)
9787 CmInetFd *sockFd; /* socket file descriptor */
9788 CmInetAddr *locAddr;
9791 struct sockaddr_in *sockAddr;
9792 #ifdef IPV6_SUPPORTED
9793 struct sockaddr_in6 *sockAddr6;
9794 struct sockaddr_in6 lclSockAddr;
9796 CmInetSockAddr lclSockAddr;
9797 #endif /* IPV6_SUPPORTED */
9802 #endif /* SS_LINUX */
9804 /*cm_inet_c_001.main_58 : fix for klockwork issue */
9807 TRC2(cmInetGetSockName);
9809 #if (ERRCLASS & ERRCLS_INT_PAR)
9810 /* error check on parameters */
9811 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd) ||
9816 #endif /* ERRCLASS & ERRCLS_INT_PAR */
9818 cmMemset((U8*)&lclSockAddr, 0, sizeof(lclSockAddr));
9819 size = sizeof(lclSockAddr);
9822 ret = getsockname(sockFd->fd, (CmInetSockAddr*)&lclSockAddr,
9823 (socklen_t *)&size);
9825 ret = getsockname(sockFd->fd, (CmInetSockAddr*)&lclSockAddr, (int*)&size);
9826 #endif /* SS_LINUX */
9830 switch(errCode = INET_ERR_CODE)
9833 sockAddr = (struct sockaddr_in *)&lclSockAddr;
9834 #ifdef IPV6_SUPPORTED
9835 locAddr->type = CM_INET_IPV4ADDR_TYPE;
9836 locAddr->u.ipv4Addr.port = CM_INET_NTOH_U16(sockAddr->sin_port);
9838 locAddr->port = CM_INET_NTOH_U16(sockAddr->sin_port);
9839 #endif /* IPV6_SUPPORTED */
9845 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
9846 /* cm_inet_c_001.main_62:Warning fix */
9847 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetGetHostByName() Failed : error(%d),"
9848 " sockFd->fd(%ld)\n", INET_ERR_CODE, sockFd->fd);
9849 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET051, 0, prntBuf);
9851 /* cm_inet_c_001.main_62:Warning fix */
9852 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetGetHostByName() Failed : error(%d),"
9853 " sockFd->fd(%d)\n", INET_ERR_CODE, sockFd->fd);
9854 CMINETLOGERROR(ERRCLS_INT_PAR, ECMINET051, 0, prntBuf);
9855 #endif /* ALIGN_64BIT */
9856 #endif /* CMINETDBG */
9858 }/* end of switch */
9862 /* Fill the returned address in to locAddr */
9863 #ifdef IPV6_SUPPORTED
9864 cmMemset((U8*)locAddr, 0, sizeof(CmInetAddr));
9865 if (size == sizeof(struct sockaddr_in6))
9867 sockAddr6 = (struct sockaddr_in6 *)&lclSockAddr;
9868 locAddr->type = CM_INET_IPV6ADDR_TYPE;
9869 locAddr->u.ipv6Addr.port = CM_INET_NTOH_U16(sockAddr6->sin6_port);
9870 CM_INET_COPY_IPV6ADDR(&locAddr->u.ipv6Addr.ipv6NetAddr,
9871 &sockAddr6->sin6_addr);
9875 sockAddr = (struct sockaddr_in *)&lclSockAddr;
9876 locAddr->type = CM_INET_IPV4ADDR_TYPE;
9877 locAddr->u.ipv4Addr.port = CM_INET_NTOH_U16(sockAddr->sin_port);
9878 locAddr->u.ipv4Addr.address =
9879 CM_INET_NTOH_U32(sockAddr->sin_addr.s_addr);
9882 sockAddr = (struct sockaddr_in *)&lclSockAddr;
9883 locAddr->port = CM_INET_NTOH_U16(sockAddr->sin_port);
9884 locAddr->address = CM_INET_NTOH_U32(sockAddr->sin_addr.s_addr);
9885 #endif /* IPV6_SUPPORTED */
9887 }/* end of cmInetGetSockName() */
9889 /* New functions to peek into the file descriptor
9891 #if (defined(SUNOS) || defined(WIN32) || defined(SS_LINUX) || defined(SS_VW) \
9896 * Fun: cmInetFdSetInfoInit
9898 * Desc: This function is used to initialise operating system specific
9899 * data that will be used to peek into the file descriptor lists
9900 * to get the sockets that are set
9902 * Ret: ROK - successful
9912 PUBLIC S16 cmInetFdSetInfoInit
9914 CmInetFdSetInfo *fdSetInfo
9917 PUBLIC S16 cmInetFdSetInfoInit(fdSetInfo)
9918 CmInetFdSetInfo *fdSetInfo;
9921 #if (defined(SUNOS) || defined(SS_LINUX) || defined(SS_VW) || defined(HPOS))
9926 #endif /* SUNOS || SS_LINUX || SS_VW */
9928 #if (ERRCLASS & ERRCLS_INT_PAR)
9929 if (fdSetInfo == NULLP)
9931 #endif /* ERRCLASS & ERRCLS_INT_PAR */
9933 if (fdSetInfo->initDone == TRUE)
9937 fdSetInfo->numFds = 0;
9940 #if (defined(SUNOS) || defined(SS_LINUX) || defined(SS_VW)|| defined(HPOS))
9941 /* Check if we are on a big endian machine */
9944 fdSetInfo->bigEndian = FALSE;
9946 fdSetInfo->bigEndian = TRUE;
9948 fdSetInfo->arIdx = 0;
9949 fdSetInfo->ar[0] = 0xff;
9951 /* Initialise the array */
9952 /* The array contains bit positions for the first bit
9953 * for each integer from 1 to 2^8.
9955 for (arIdx = 1; arIdx < 256; arIdx++)
9957 /* cm_inet_c_001.main_54: Fix for Klockworks issue */
9958 curByte = (U8)arIdx;
9965 fdSetInfo->ar[arIdx] = bitPos;
9969 curByte = curByte >> 1;
9972 /* Calculate the number of array elements in this fd_set */
9973 #if (defined(SS_LINUX) && !defined(_GNU_SOURCE))
9974 fdSetInfo->numArElems = sizeof(CmInetFdSet)/sizeof(fdSet->__fds_bits[0]);
9976 fdSetInfo->numArElems = sizeof(CmInetFdSet)/sizeof(fdSet->fds_bits[0]);
9977 #endif /* SS_LINUX */
9978 #endif /* SUNOS || SS_LINUX || SS_VW || HPOS */
9980 fdSetInfo->initDone = TRUE;
9982 }/* end of cmInetFdSetInfoInit() */
9989 * Desc: This function is used to get the file descriptor from the
9990 * file descriptor set.
9992 * Ret: ROK - successful
9993 * ROKDNA - socket not found
9995 * RNA - failed, initialisation not done
9997 * Notes: If the application modifies fdSet between calls to this
9998 * function then the results are undefined. This function should
9999 * be called in a loop till either it returns - not ROK, or if
10000 * all sockets in the file descriptor set are processed.
10007 PUBLIC S16 cmInetGetFd
10009 CmInetFdSetInfo *fdSetInfo,
10010 CmInetFdSet *fdSet,
10011 CmInetFdType *sockFd
10014 PUBLIC S16 cmInetGetFd(fdSetInfo, fdSet, sockFd)
10015 CmInetFdSetInfo *fdSetInfo;
10016 CmInetFdSet *fdSet;
10017 CmInetFdType *sockFd;
10020 /*cm_inet_c_001.main_58 : Fix for klockwork issue */
10021 #if (!defined (WIN32))
10022 U32 sizOfFdSetArElem;
10028 #endif /* !defined (WIN32) */
10030 #if (ERRCLASS & ERRCLS_INT_PAR)
10031 if ((fdSetInfo == NULLP) || (fdSet == NULLP) || (sockFd == NULLP))
10034 if (fdSetInfo->initDone != TRUE)
10036 #endif /* ERRCLASS & ERRCLS_INT_PAR */
10039 #if (ERRCLASS & ERRCLS_DEBUG)
10040 if (fdSetInfo->numFds > FD_SETSIZE)
10042 #endif /* ERRCLASS & ERRCLS_DEBUG */
10043 /* cm_inet_c_001.main_32 : Corrected check for number of fd set in
10044 a fdset for WIN32*/
10045 if (fdSetInfo->numFds >= fdSet->fd_count)
10048 *sockFd = fdSet->fd_array[fdSetInfo->numFds];
10049 fdSetInfo->numFds += 1;
10053 /* cm_inet_c_001.main_59: Protected under if not defined WIN32 */
10054 #if (!defined (WIN32))
10055 /* Start with arIdx and continue upto number of array elements. */
10056 curIdx = fdSetInfo->arIdx;
10059 #if (defined(SS_LINUX) && !defined(_GNU_SOURCE))
10060 sizOfFdSetArElem = sizeof(fdSet->__fds_bits[0]);
10062 sizOfFdSetArElem = sizeof(fdSet->fds_bits[0]);
10063 #endif /* SS_LINUX */
10065 for (curIdx = fdSetInfo->arIdx; curIdx < fdSetInfo->numArElems;
10068 #if (defined(SS_LINUX) && !defined(_GNU_SOURCE))
10069 if (fdSet->__fds_bits[curIdx])
10071 if (fdSet->fds_bits[curIdx])
10072 #endif /* SS_LINUX */
10074 /* Walk through the bytes in this element */
10075 #if (defined(SS_LINUX) && !defined(_GNU_SOURCE))
10076 tempByte = (U8 *)&fdSet->__fds_bits[curIdx];
10078 tempByte = (U8 *)&fdSet->fds_bits[curIdx];
10079 #endif /* SS_LINUX */
10081 /* Set the starting byte offset */
10082 if (fdSetInfo->bigEndian)
10083 tempByte += sizOfFdSetArElem - 1;
10085 for (bytesScanned = 0; bytesScanned < sizOfFdSetArElem;
10090 bitPos = fdSetInfo->ar[*tempByte];
10091 /* cm_inet_c_001.main_54: Fix for Klockworks issue */
10092 fdSetInfo->arIdx = (U16)curIdx;
10093 /* Calculate fd depending on where we are */
10094 *sockFd = ((bytesScanned << 3) + bitPos);
10095 *sockFd += (curIdx * (sizOfFdSetArElem << 3));
10096 /* Clear the file descriptor */
10097 *tempByte &= ~(1 << bitPos);
10100 if (fdSetInfo->bigEndian)
10113 #endif /* SUNOS || SS_LINUX || SS_VW || HPOS */
10114 } /* end of cmInetGetFd */
10116 #endif /* SUNOS || WIN32 || SS_LINUX || SS_VW || HPOS */
10119 /* add cmInetConvertStrToIpAddr and
10120 * cmInetAsciiToIpv4 functions */
10123 * Fun: cmInetConvertStrToIpAddr
10125 * Desc: This function parses the input string for an IPV4/IPV6 address.
10127 * 1) IPV4 in dot number format:
10129 * 2) IPV6, in uncompressed, compressed, and IPV4 embedded format
10130 * 10:20:30:40:502:610:70C:80ad
10132 * 45::AB:34:123.34.5.667
10134 * Ret: ROK - SUCCESS
10135 * RFAILED - FAILURE
10144 PUBLIC S16 cmInetConvertStrToIpAddr
10146 U16 len, /* Length of IP address */
10147 U8 *val, /* Domain Name String */
10148 CmInetNetAddr *address /* IP Address */
10151 PUBLIC S16 cmInetConvertStrToIpAddr(len, val, address)
10152 U16 len; /* Length of IP address */
10153 U8 *val; /* Domain Name String */
10154 CmInetNetAddr *address; /* IP Address */
10157 U8 idx; /* Index for string*/
10158 U8 ipv4[CM_INET_IPV4ADDR_SIZE]; /* IPV4 Address bytes */
10159 #ifdef IPV6_SUPPORTED
10160 U16 *ipv6; /* IPV6 Address bytes */
10161 U16 ipv6Reg[8]; /* regular IPV6 Address bytes */
10162 U16 ipv6Cmp[8]; /* compressed IPV6 Address bytes */
10163 U8 numBlk; /* number of blocks in IPV6 addr */
10164 Bool compressed; /* IPV6 in compressed format */
10165 U8 ipv6Idx; /* counter for IPV6 */
10166 U8 blkBeginIdx; /* IPV6, char index for the
10167 beginning of the block */
10168 U8 i; /* counter for IPV6 */
10169 S16 retVal; /* return value */
10170 Bool embedIPV4 = FALSE; /* IPV4 embedded in IPV6 ? */
10171 #endif /* IPV6_SUPPORTED*/
10173 TRC2(cmInetConvertStrToIpAddr)
10176 #ifdef IPV6_SUPPORTED
10179 compressed = FALSE;
10181 ipv6 = ipv6Reg; /* assign pointer to IPV6 regular, uncompressed */
10182 cmMemset((U8 *)ipv6Reg, 0, CM_INET_IPV6ADDR_SIZE);
10183 cmMemset((U8 *)ipv6Cmp, 0, CM_INET_IPV6ADDR_SIZE);
10184 #endif /* IPV6_SUPPORTED*/
10186 cmMemset((U8 *)ipv4, 0, CM_INET_IPV4ADDR_SIZE);
10188 /* Check for IP Address */
10189 while ((val[idx] != '.') && (val[idx] != ':') &&
10192 #if (ERRCLASS & ERRCLS_DEBUG)
10193 if (((val[idx] < '0') || (val[idx] > '9')) &&
10194 ((val[idx] < 'a') || (val[idx] > 'f')) &&
10195 ((val[idx] < 'A') || (val[idx] > 'F')))
10200 #endif /* (ERRCLASS & ERRCLS_DEBUG) */
10202 /* Convert Ascii to integer */
10203 CM_INET_ATOI(ipv4[0], val[idx]);
10205 #ifdef IPV6_SUPPORTED
10206 /* convert Ascii to hex */
10207 CM_INET_ATOH(ipv6[0], val[idx]);
10208 #endif /* IPV6_SUPPORTED */
10210 idx++; /* move to the next character */
10211 } /* while, try to determine IPV4 or IPV6 */
10213 #if (ERRCLASS & ERRCLS_DEBUG)
10214 if ((val[idx] != '.') && (val[idx] != ':'))
10218 } /* if, couldn't determine IPV4 or IPV6 */
10219 #endif /* (ERRCLASS & ERRCLS_DEBUG) */
10222 if (val[idx] == '.')
10225 cmInetAsciiToIpv4(3, &(ipv4[1]), (U16)(len - idx), &(val[idx]));
10227 address->type = CM_INET_IPV4ADDR_TYPE;
10228 CM_INET_GET_IPV4_ADDR_FRM_STRING(address->u.ipv4NetAddr, ipv4);
10230 #ifdef IPV6_SUPPORTED
10233 numBlk = 1; /* already converted the 1st block */
10235 while ((val[idx] != '\0') && (idx < len) && (numBlk <= 8))
10237 idx++; /* go to the next char, either a number or the 2nd : */
10238 if (val[idx] == ':')
10240 #if (ERRCLASS & ERRCLS_DEBUG)
10241 if (compressed == TRUE)
10243 /* can't have 2 :: */
10246 #endif /* (ERRCLASS & ERRCLS_DEBUG) */
10249 idx++; /* skip the : */
10252 } /* if, IPV6 in compressed format :: */
10256 } /* else, uncompressed, convert next block */
10258 numBlk++; /* increase number of blocks */
10260 /* assign the index the beginning of the block */
10263 while(val[idx] != ':' && val[idx] != '\0' && idx < len)
10265 if (val[idx] == '.')
10267 /* convert number to IPV4 */
10268 ipv6[ipv6Idx] = 0; /* clear out whatever we did */
10269 cmMemset((U8 *)ipv4, 0, CM_INET_IPV4ADDR_SIZE);
10270 retVal = cmInetAsciiToIpv4(4, ipv4, len - blkBeginIdx,
10271 &(val[blkBeginIdx]));
10272 /* stop the loop, embedded IPV4 is the last part of
10280 } /* if, '.' means IPV4 address embedded in IPV6 */
10282 #if (ERRCLASS & ERRCLS_DEBUG)
10283 if (((val[idx] < '0') || (val[idx] > '9')) &&
10284 ((val[idx] < 'a') || (val[idx] > 'f')) &&
10285 ((val[idx] < 'A') || (val[idx] > 'F')))
10290 #endif /* (ERRCLASS & ERRCLS_DEBUG) */
10292 /* Convert Ascii to integer */
10293 CM_INET_ATOH(ipv6[ipv6Idx], val[idx]);
10295 /* move to the next index */
10297 } /* while, convert a block of 16 bits Hex number */
10298 if (embedIPV4 == TRUE)
10300 ipv6Idx--; /* deccrease in case of compressed IPV6 */
10301 break; /* stop the while look */
10302 } /* if, IPV4 embedded in IPV6 */
10303 } /* while, IPV6 parsing */
10304 if (compressed == TRUE)
10306 if (embedIPV4 == TRUE)
10308 numBlk = 5; /* the last 2 blocks are IPV4 */
10309 } /* if, IPV4 embedded */
10312 numBlk = 7; /* copy from the last block */
10313 } /* else, no embedded IPV4 */
10315 /* type cast U8 over -1 becasue we want to copy the last block,
10318 for (i = ipv6Idx; i != (U8) (-1); i --)
10320 ipv6Reg[numBlk] = ipv6Cmp[i];
10322 } /* for, copying compress IPV6 to regular IPV6 */
10323 } /* if, compressed format */
10325 if (embedIPV4 == TRUE)
10327 ipv6Reg[6] = PutHiByte(ipv6Reg[6], ipv4[0]);
10328 ipv6Reg[6] = PutLoByte(ipv6Reg[6], ipv4[1]);
10329 ipv6Reg[7] = PutHiByte(ipv6Reg[7], ipv4[2]);
10330 ipv6Reg[7] = PutLoByte(ipv6Reg[7], ipv4[3]);
10331 } /* if, IPV4 embedded */
10333 /* convert IPV6 to cmInetIpv6 */
10334 address->type = CM_INET_IPV6ADDR_TYPE;
10335 cmMemcpy((U8 *)address->u.ipv6NetAddr,
10336 (CONSTANT U8 *) ipv6Reg, CM_INET_IPV6ADDR_SIZE);
10338 #endif /* IPV6_SUPPORTED */
10341 } /* cmInetConvertStrToIpAddr */
10346 * Fun: cmInetAsciiToIpv4
10348 * Desc: This function parses the input string to an IPV4 address.
10349 * The input string can be
10350 * - the whole IPV4 address, '123.43.45.56', or
10351 * - a part of it. '34.56.454'
10352 * numBytes: number of bytes needs to be converted, IPV4 has
10353 * 4 bytes. If we are only converting the end of an
10354 * address, this number needs to be adjusted. For
10355 * example, when converting '34.56.454]', the number
10358 * Ret: ROK - SUCCESS
10359 * RFAILED - FAILURE
10367 PUBLIC S16 cmInetAsciiToIpv4
10369 U8 numBytes, /* number of Byte to convert */
10370 U8 *ipv4Addr, /* IPV4 Address */
10371 U16 len, /* Length of IP address */
10372 U8 *val /* Domain Name String */
10375 PUBLIC S16 cmInetAsciiToIpv4(numBytes, ipv4Addr, len, val)
10376 U8 numBytes; /* number of Byte to convert */
10377 U8 *ipv4Addr; /* IPV4 Address */
10378 U16 len; /* Length of IP address */
10379 U8 *val; /* Domain Name String */
10382 U8 byteCount; /* Byte Count */
10383 U8 idx; /* Index for string*/
10385 TRC2(cmInetAsciiToIpv4)
10388 for (byteCount = 0; byteCount < numBytes; byteCount++)
10390 while((val[idx] != '.') && (idx < len))
10392 #if (ERRCLASS & ERRCLS_DEBUG)
10393 if (val[idx] < '0' || val[idx] > '9')
10398 #endif /* (ERRCLASS & ERRCLS_DEBUG) */
10400 /* Convert Ascii to integer */
10401 CM_INET_ATOI(ipv4Addr[byteCount], val[idx]);
10403 /* move to the next index */
10410 } /* cmInetAsciiToIpv4 */
10412 /* cm_inet_c_001.main_34:Added wrapper function for getaddrinfo and freeaddrinfo */
10413 #if (!defined(SS_VW) && !defined(SS_PS) && !defined(WIN32))
10417 * Fun: cmInetGetAddrInfo
10419 * Desc: a socket file descriptor to a local Internet
10422 * Ret: Value returned by getaddrinfo
10431 PUBLIC S32 cmInetGetAddrInfo
10433 CONSTANT S8 *node, /* Network addr which has to be resolved */
10434 CONSTANT S8 *service, /* Sets the port number in network addr */
10435 CONSTANT CmInetAddrInfo *hints, /* Specifies preferred socket type or protocol */
10436 CmInetAddrInfo **res /* Link list of addrInfo structure */
10439 PUBLIC S32 cmInetGetAddrInfo(node,service,hints,res)
10440 CONSTANT S8 *node; /* Network addr which has to be resolved */
10441 CONSTANT S8 *service; /* Sets the port number in network addr */
10442 CONSTANT CmInetAddrInfo *hints; /* Specifies preferred socket type or protocol */
10443 CmInetAddrInfo **res; /* Link list of addrInfo structure */
10447 TRC2(cmInetGetAddrInfo);
10450 #if (ERRCLASS & ERRCLS_INT_PAR)
10451 /* error check on parameters */
10452 if ((node == NULLP) || (hints == NULLP))
10456 #endif /* ERRCLASS & ERRCLS_INT_PAR */
10458 ret = getaddrinfo(node,service,hints,res);
10462 #ifndef ALIGN_64BIT
10463 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
10464 /* cm_inet_c_001.main_62:Warning fix */
10465 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetGetAddrInfo() Failed : error(%ld), node(%p),"
10466 " service(%p)\n", ret, node, service);
10467 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET052, 0, prntBuf);
10469 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
10470 /* cm_inet_c_001.main_62:Warning fix */
10471 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE, "cmInetGetAddrInfo() Failed : error(%d), node(%p),"
10472 " service(%p)\n ", ret, node, service);
10473 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET053, 0, prntBuf);
10474 #endif /* ALIGN_64BIT */
10475 #endif /* CMINETDBG */
10478 } /* end of cmInetGetAddrInfo */
10483 * Fun: cmInetFreeAddrInfo
10485 * Desc: Free the dynamically allocated addrinfo structure
10496 PUBLIC Void cmInetFreeAddrInfo
10498 CmInetAddrInfo *res /* Link list of addrInfo structure */
10501 PUBLIC Void cmInetFreeAddrInfo(res)
10502 CmInetAddrInfo *res; /* Link list of addrInfo structure */
10505 TRC2(cmInetFreeAddrInfo);
10507 #if (ERRCLASS & ERRCLS_INT_PAR)
10508 /* error check on parameters */
10511 #endif /* ERRCLASS & ERRCLS_INT_PAR */
10514 } /* end of cmInetFreeAddrInfo */
10516 #endif /* SS_VW | SS_PS | WIN32*/
10518 /* cm_inet_c_001.main_36 : 1. Added new interface - cmInetFlushRecvBuf()
10519 to flush the data from socket receive buffer. */
10520 #ifdef CM_INET_FLUSH_RECV_BUF
10524 * Fun: cmInetFlushRcvBuf
10526 * Desc: Reads all the data from a socket and throw it!!
10527 * The buffers for the receive buffer for recvfrom() are allocated from the stack.
10529 * Ret: ROK - successful
10530 * ROKDNA - ok, data not available
10531 * RCLOSED - connection closed by peer
10532 * ROUTRES - failed, out of resources
10541 PUBLIC S16 cmInetFlushRecvBuf
10543 CmInetFd *sockFd, /* socket file descriptor */
10544 MsgLen *len, /* number of octects to be flushed */
10545 S32 flags /* additional control flags */
10548 PUBLIC S16 cmInetFlushRecvBuf(sockFd, len, flags)
10549 CmInetFd *sockFd; /* socket file descriptor */
10550 MsgLen *len; /* number of octects to be flushed */
10551 S32 flags; /* additional control flags */
10555 Data recvTempBuf[CM_INET_MAX_BYTES_READ];
10557 #if (defined(WIN32) || defined(CMINETFLATBUF))
10558 S32 ret; /* temporary return value */
10559 U32 pendLen; /* pending data length */
10560 S32 recvLen; /* number of received octets by recvmsg() */
10561 MsgLen curLen; /* current number of octets in buffer */
10562 U32 remAddrLen; /* length of remote address */
10563 struct sockaddr_in *remAddr; /* remote Internet address */
10564 #ifdef IPV6_SUPPORTED
10565 struct sockaddr_in6 remSockAddr; /* to get packet's source IP address */
10567 CmInetSockAddr remSockAddr; /* to get packet's source IP address */
10568 #endif /* IPV6_SUPPORTED */
10570 S32 ret; /* temporary return value */
10571 MsgLen curLen; /* current number of octets in buffer */
10572 U32 pendLen; /* pending data length */
10573 S32 recvLen; /* number of received octets by recvmsg() */
10574 struct msghdr msg; /* message header */
10575 CmInetIovec rxArr[CM_INET_MAX_DBUF]; /* dynamic gather array */
10576 U32 remAddrLen; /* length of remote address */
10577 #ifdef IPV6_SUPPORTED
10578 struct sockaddr_in6 remSockAddr;/* to get packet's source IP address */
10580 #if (defined(SS_LINUX) || defined(_XPG4_2))
10581 U8 ancillData[CM_INET_IPV6_ANCIL_DATA];
10582 /* from stack for IPv6 ancill data */
10585 CmInetSockAddr remSockAddr; /* to get packet's src IP address */
10586 #if (defined(SS_LINUX) || defined(_XPG4_2))
10587 U8 ancillData[CM_INET_IPV4_ANCIL_DATA];
10588 /* from stack for IPv4 ancill data */
10590 #endif /* IPV6_SUPPORTED */
10591 #endif /* WIN32 | CMINETFLATBUF */
10593 /* used by getsockopt */
10594 U32 errValue; /* error value */
10595 U32 optLen; /* option length */
10597 TRC2(cmInetFlushRcvBuf)
10599 #if (ERRCLASS & ERRCLS_INT_PAR)
10600 /* error check on parameters */
10601 if ((sockFd == NULLP) || CM_INET_INV_SOCK_FD(sockFd))
10605 #endif /* ERRCLASS & ERRCLS_INT_PAR */
10608 #if (defined(WIN32) || defined(CMINETFLATBUF))
10610 #endif /* (WIN32 | CMINETFLATBUF) */
10612 /* clear the structure */
10613 cmMemset((U8*)&remSockAddr, 0, sizeof(remSockAddr));
10615 /* get number of pending data */
10616 ret = cmInetGetNumRead(sockFd, &pendLen);
10619 /* ret may be RFAILED or ROUTRES */
10623 /* check if connection got closed */
10626 if (sockFd->type == CM_INET_STREAM)
10629 /* cm_inet_c_001.main_50
10630 * Due to latency (mostly in solaris) sometimes ioctl(FIONREAD)
10631 * (inside cmInetGetNumRead) returns pend length as 0 on a TCP
10632 * socket that select says is ready to read. This should not be
10633 * considered as connection closed. So return ROKDNA instead of
10639 /* clear error if there is any, because if there is internal error
10640 * here it will cause infinite loop in TUCL */
10643 optLen = sizeof(int);
10645 ret = getsockopt(sockFd->fd, SOL_SOCKET, SO_ERROR,
10646 (char*)&errValue, (socklen_t *)&optLen);
10648 #if (defined(SS_VW) || defined(SS_PS))
10649 ret = getsockopt(sockFd->fd, SOL_SOCKET, SO_ERROR,
10650 (char*)&errValue, (int *)&optLen);
10653 ret = getsockopt(sockFd->fd, SOL_SOCKET, SO_ERROR,
10654 (char*)&errValue, (int *)&optLen);
10655 #endif /* SS_WINCE */
10657 #endif /* SS_LINUX */
10658 if (ret == INET_ERR)
10661 #ifndef ALIGN_64BIT
10662 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
10663 /* cm_inet_c_001.main_62:Warning fix */
10664 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetFlushRecvBuf() Failed : error(%d),"
10665 " sockFd->fd(%ld)\n", INET_ERR_CODE, sockFd->fd);
10666 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET054, 0, prntBuf);
10668 /* cm_inet_c_001.main_62:Warning fix */
10669 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetFlushRecvBuf() Failed : error(%d),"
10670 " sockFd->fd(%d)\n", INET_ERR_CODE, sockFd->fd);
10671 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET054, 0, prntBuf);
10672 #endif /*ALIGN_64BIT*/
10673 #endif /* CMINETDBG */
10679 /* added separate recvfrom calls different OS */
10680 #if( defined(SS_VW) || defined(HPOS) || defined(SS_PS))
10681 recvLen = recvfrom(sockFd->fd, (S8 *)&tempBuf, pendLen, 0,
10682 (struct sockaddr *)&remSockAddr, (int *)&remAddrLen);
10684 #if ( defined(SUNOS) || defined(SS_LINUX))
10685 recvLen = recvfrom(sockFd->fd, (S8 *)&tempBuf, pendLen, 0,
10686 NULLP, (socklen_t *)&remAddrLen);
10688 recvLen = recvfrom(sockFd->fd, (S8 *)&tempBuf, pendLen, 0,
10689 NULLP, (S32 *)&remAddrLen);
10691 #endif /* defined(SUNOS) || defined(SS_LINUX) */
10692 #endif /* defined(SS_VW) || defined(HPOS) || defined(SS_PS) */
10697 }/* if (pendLen == 0)*/
10700 if((*len == CM_INET_READ_THROW) || (*len >= CM_INET_MAX_BYTES_READ))
10702 curLen = CM_INET_MAX_BYTES_READ;
10706 curLen = *len; /*set to given number of messasges to be flushed */
10709 if((*len != CM_INET_READ_THROW) && (*len < pendLen))
10714 #if (defined(WIN32) || defined(CMINETFLATBUF))
10718 * maybe needs more than one recvfrom() call to read an entire
10723 cmMemset((U8*)recvTempBuf, 0, CM_INET_MAX_BYTES_READ);
10724 /* added separate recvfrom calls different OS */
10726 #if( defined(SS_VW) || defined(HPOS) || defined(SS_PS))
10727 recvLen = recvfrom(sockFd->fd, (S8 *)recvTempBuf, curLen, 0,
10728 (struct sockaddr *)&remSockAddr, (int *)&remAddrLen);
10730 #if ( defined(SUNOS) || defined(SS_LINUX))
10731 recvLen = recvfrom(sockFd->fd, (S8 *)recvTempBuf, curLen, 0,
10732 (struct sockaddr *)&remSockAddr, (socklen_t *)&remAddrLen);
10734 recvLen = recvfrom(sockFd->fd, (S8 *)recvTempbuf, curLen, 0,
10735 &remSockAddr, (S32 *)&remAddrLen);
10737 #endif /* defined(SUNOS) || defined(SS_LINUX) */
10738 #endif /* defined(SS_VW) || defined(HPOS) || defined(SS_PS) */
10740 if (recvLen == INET_ERR)
10743 /* added check ERR_WOULDBLOCK */
10744 if ((INET_ERR_CODE == ERR_AGAIN) ||
10745 (INET_ERR_CODE == ERR_WOULDBLOCK))
10752 /* In Windows the recvfrom function fails
10753 * with error code which maps to either WSAECONNABORTED. If
10754 * this happens then cmInetFlushRecvBuf must return RCLOSED */
10755 if ((INET_ERR_CODE == ERR_CONNABORTED) ||
10756 (INET_ERR_CODE == ERR_CONNRESET))
10763 #ifndef ALIGN_64BIT
10764 /* cm_inet_c_001.main_54 : CMINETLOGERROR added insted of SDisp */
10765 /* cm_inet_c_001.main_62:Warning fix */
10766 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetFlushRecvBuf() Failed : error(%d),"
10767 " sockFd->fd(%ld)\n", INET_ERR_CODE, sockFd->fd);
10768 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET055, 0, prntBuf);
10770 /* cm_inet_c_001.main_62:Warning fix */
10771 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetFlushRecvBuf() Failed : error(%d),"
10772 " sockFd->fd(%d)\n", INET_ERR_CODE, sockFd->fd);
10773 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET055, 0, prntBuf);
10774 #endif /*ALIGN_64BIT*/
10775 #endif /* CMINETDBG */
10780 if(recvLen < curLen)
10783 pendLen -= recvLen;
10785 if(pendLen < curLen)
10788 } /* while (curLen > 0) */
10790 #else /* end of Win NT/flat buffer specific part */
10793 * maybe needs more than one recvmsg() call to read entire message
10794 * on a stream socket
10798 cmMemset((U8*)recvTempBuf, 0, CM_INET_MAX_BYTES_READ);
10799 /* update the message structure */
10801 rxArr[0].iov_base = (Void*)recvTempBuf;
10802 rxArr[0].iov_len = (U32)curLen;
10804 rxArr[0].iov_base = (S8*)recvTempBuf;
10805 rxArr[0].iov_len = curLen;
10806 #endif /* SS_LINUX */
10807 msg.msg_iov = rxArr;
10808 msg.msg_iovlen = 1;
10810 msg.msg_name = NULLP;
10811 msg.msg_namelen = 0;
10813 /* added defined(_XPG4_2). Also changed the
10815 #if (defined(SS_LINUX) || defined(_XPG4_2))
10816 msg.msg_control = ancillData;
10817 msg.msg_controllen = sizeof(ancillData);
10820 msg.msg_accrights = NULLP;
10821 msg.msg_accrightslen = 0;
10822 #endif /* SS_LINUX */
10824 recvLen = recvmsg(sockFd->fd, &msg, flags);
10825 if ((recvLen == INET_ERR) || (recvLen > CM_INET_MAX_MSG_LEN))
10827 /* added check ERR_AGAIN when CMINETFLATBUF is not defined.
10828 added check ERR_WOULDBLOCK */
10829 if ((INET_ERR_CODE == ERR_AGAIN) ||
10830 (INET_ERR_CODE == ERR_WOULDBLOCK))
10837 #ifndef ALIGN_64BIT
10838 /* cm_inet_c_001.main_54: CMINETLOGERROR added insted of SDisp */
10839 /* cm_inet_c_001.main_62:Warning fix */
10840 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetFlushRecvBuf() Failed : error(%d),"
10841 " sockFd->fd(%ld)\n", INET_ERR_CODE, sockFd->fd);
10842 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET056, 0, prntBuf);
10844 /* cm_inet_c_001.main_62:Warning fix */
10845 snprintf(prntBuf, CMINET_PRNT_BUF_SIZE,"cmInetFlushRecvBuf() Failed : error(%d),"
10846 " sockFd->fd(%d)\n", INET_ERR_CODE, sockFd->fd);
10847 CMINETLOGERROR(ERRCLS_DEBUG, ECMINET056, 0, prntBuf);
10848 #endif /*ALIGN_64BIT*/
10849 #endif /* CMINETDBG */
10851 /* If this happens then cmInetFlushRecvBuf must return RCLOSED.
10852 * Needed for getting icmp msgs */
10853 if (INET_ERR_CODE == ERR_CONNABORTED)
10859 }/* if ((recvLen == INET_ERR) || (recvLen > CM_INET_MAX_MSG_LEN))*/
10861 if(recvLen < curLen)
10864 pendLen -= recvLen;
10866 if(pendLen < curLen)
10869 } /* while(curLen > 0) */
10871 #endif /* WIN32 | CMINETFLATBUF */
10875 } /* end of cmInetFlushRecvBuf */
10877 #endif /* CM_INET_FLUSH_RECV_BUF*/
10879 /**********************************************************************
10881 **********************************************************************/