etherMultiLib.c
上传用户:nvosite88
上传日期:2007-01-17
资源大小:4983k
文件大小:6k
源码类别:

VxWorks

开发平台:

C/C++

  1. /* etherMultiLib.c - a library to handle Ethernet multicast addresses */
  2. /* Copyright 1984 - 2001 Wind River Systems, Inc. */
  3. #include "copyright_wrs.h"
  4. /*
  5. modification history
  6. --------------------
  7. 01h,15oct01,rae  merge from truestack ver 01j, base o1g
  8. 01g,14dec97,jdi  doc: cleanup.
  9. 01f,10dec97,kbw  making minor man page fixes
  10. 01e,25oct97,kbw  making minor man page fixes
  11. 01d,26aug97,spm  removed compiler warnings (SPR #7866)
  12. 01c,23oct96,gnn  changed names to follow coding standards; removed some 
  13.                  compiler warnings
  14. 01b,22oct96,gnn  changed printfs to logMsgs
  15. 01a,29mar96,gnn  taken from BSD 4.4 code
  16. */
  17.  
  18. /*
  19. DESCRIPTION
  20. This library manages a list of multicast addresses for network
  21. drivers.  This abstracts the management of these drivers into a device
  22. independant library.
  23. To use this feature, include the following component:
  24. INCLUDE_NETWRS_ETHERMULTILIB
  25. INCLUDE FILES: string.h, errno.h, netinet/in.h, net/if.h, lstLib.h,
  26. etherMultiLib.h
  27. */
  28. /* includes */
  29. #include "vxWorks.h"
  30. #include "logLib.h"
  31. #include "string.h"
  32. #include "errno.h"
  33. #include "netinet/in.h"
  34. #include "net/if.h"
  35. #include "lstLib.h"
  36. #include "end.h"
  37. #include "etherMultiLib.h"
  38. #include "stdlib.h"
  39. #include "memPartLib.h"
  40. /* defints */
  41. /* typedefs */
  42. /* globals */
  43. int etherMultiDebug = 0;
  44. /* locals */
  45. /* forward declarations */
  46. /*****************************************************************************
  47. *
  48. * etherMultiAdd - add multicast address to a multicast address list
  49. *
  50. * This routine adds an Ethernet multicast address list for a given END.
  51. * The address is a six-byte value pointed to by <pAddress>.
  52. * RETURNS: OK or ENETRESET.
  53. */
  54. int etherMultiAdd
  55.     (
  56.     LIST *pList,    /* pointer to list of multicast addresses */
  57.     char* pAddress  /* address you want to add to list */
  58.     )
  59.     {
  60.     
  61.     ETHER_MULTI* pCurr;
  62.     /*
  63.      * Verify that we have valid Ethernet multicast addresses.
  64.      */
  65.     if ((pAddress[0] & 0x01) != 1) {
  66. if (etherMultiDebug)
  67.     logMsg("Invalid address!n", 1, 2, 3, 4, 5, 6);
  68. return (EINVAL);
  69.     }
  70.     /*
  71.      * See if the address range is already in the list.
  72.      */
  73.     for (pCurr = (ETHER_MULTI *)lstFirst(pList); pCurr != NULL && 
  74.     (bcmp(pCurr->addr, pAddress, 6) != 0); 
  75.     pCurr = (ETHER_MULTI *)lstNext(&pCurr->node)); 
  76.     
  77.     if (pCurr != NULL) {
  78. /*
  79.  * Found it; just increment the reference count.
  80.  */
  81. if (etherMultiDebug)
  82.     logMsg("Address already exists!n", 1, 2, 3, 4, 5, 6);
  83. ++pCurr->refcount;
  84. return (0);
  85.     }
  86.     /*
  87.      * New address or range; malloc a new multicast record
  88.      * and link it into the interface's multicast list.
  89.      */
  90.     pCurr = (ETHER_MULTI *) KHEAP_ALLOC(sizeof(ETHER_MULTI));
  91.     if (pCurr == NULL) {
  92. if (etherMultiDebug)
  93.     logMsg("Cannot allocate memory!n", 1, 2, 3, 4, 5, 6);
  94. return (ENOBUFS);
  95.     }
  96.     bcopy((char *)pAddress, (char *)pCurr->addr, 6);
  97.     pCurr->refcount = 1;
  98.     lstAdd(pList, &pCurr->node);
  99.     if (etherMultiDebug)
  100. {
  101. logMsg("Added address is %x:%x:%x:%x:%x:%xn",
  102.     pCurr->addr[0],
  103.     pCurr->addr[1],
  104.     pCurr->addr[2],
  105.     pCurr->addr[3],
  106.     pCurr->addr[4],
  107.     pCurr->addr[5]);
  108. }
  109.     /*
  110.      * Return ENETRESET to inform the driver that the list has changed
  111.      * and its reception filter should be adjusted accordingly.
  112.      */
  113.     return (ENETRESET);
  114.     }
  115. /*****************************************************************************
  116. *
  117. * etherMultiDel - delete an Ethernet multicast address record
  118. *
  119. * This routine deletes an Ethernet multicast address from the list.
  120. * The address is a six-byte value pointed to by <pAddress>.
  121. * RETURNS: OK or ENETRESET.
  122. */
  123. int etherMultiDel
  124.     (
  125.     LIST *pList,    /* pointer to list of multicast addresses */
  126.     char* pAddress  /* address you want to add to list */
  127.     )
  128.     {
  129.     ETHER_MULTI* pCurr;
  130.     /*
  131.      * Look up the address in our list.
  132.      */
  133.     for (pCurr = (ETHER_MULTI *)lstFirst(pList); pCurr != NULL && 
  134.     (bcmp(pCurr->addr, pAddress, 6) != 0); 
  135.     pCurr = (ETHER_MULTI *)lstNext(&pCurr->node)); 
  136.     
  137.     if (pCurr == NULL) {
  138.     return (ENXIO);
  139.     }
  140.     if (--pCurr->refcount != 0) {
  141.     /*
  142.      * Still some claims to this record.
  143.      */
  144.     return (0);
  145.     }
  146.     /*
  147.      * No remaining claims to this record; unlink and free it.
  148.      */
  149.     lstDelete(pList, &pCurr->node);
  150.     KHEAP_FREE((char *)pCurr);
  151.     /*
  152.      * Return ENETRESET to inform the driver that the list has changed
  153.      * and its reception filter should be adjusted accordingly.
  154.      */
  155.     return (ENETRESET);
  156.     }
  157. /*****************************************************************************
  158. * etherMultiGet - retrieve a table of multicast addresses from a driver
  159. *
  160. * This routine runs down the multicast address list stored in a driver
  161. * and places all the entries it finds into the multicast table
  162. * structure passed to it.
  163. *
  164. * RETURNS: OK or ERROR.
  165. */
  166. int etherMultiGet
  167.     (
  168.     LIST* pList,        /* pointer to list of multicast addresses */
  169.     MULTI_TABLE* pTable /* table into which to copy addresses */
  170.     )
  171.     {
  172.     int count = 0;
  173.     int len;
  174.     ETHER_MULTI* pCurr;
  175.     len = pTable->len; /* Save the passed in table length. */
  176.     pTable->len = 0;
  177.     pCurr = (ETHER_MULTI *)lstFirst(pList);
  178.     while (pCurr != NULL && count < len)
  179. {
  180. if (etherMultiDebug)
  181.     {
  182.     logMsg("%x:%x:%x:%x:%x:%xn", 
  183. pCurr->addr[0], 
  184. pCurr->addr[1], 
  185. pCurr->addr[2], 
  186. pCurr->addr[3],
  187. pCurr->addr[4],
  188. pCurr->addr[5]);
  189.     }
  190. bcopy(pCurr->addr, (char *)&pTable->pTable[count], 6);
  191. count+=6;
  192. pTable->len += 6;
  193. pCurr = (ETHER_MULTI *)lstNext(&pCurr->node);
  194. }
  195.     return (OK);
  196.     }