Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

663 lines
19 KiB

  1. //=============================================================================
  2. // Copyright (c) 1997 Microsoft Corporation
  3. //
  4. // File: table.h
  5. //
  6. // Abstract:
  7. // This module contains declarations for interface and group table
  8. // structures, related macros, and function prototypes.
  9. //
  10. // Author: K.S.Lokesh (lokeshs@) 11-1-97
  11. //
  12. // Revision History:
  13. //=============================================================================
  14. #ifndef _IGMP_TABLE_H_
  15. #define _IGMP_TABLE_H_
  16. //
  17. // forward declarations
  18. //
  19. struct _IF_TABLE_ENTRY;
  20. struct _GROUP_TABLE_ENTRY;
  21. struct _GI_ENTRY;
  22. //
  23. // struct: GLOBAL_CONFIG (same as mib structs in igmprm.h)
  24. //
  25. typedef IGMP_MIB_GLOBAL_CONFIG GLOBAL_CONFIG;
  26. typedef PIGMP_MIB_GLOBAL_CONFIG PGLOBAL_CONFIG;
  27. //---------------------------------------------------
  28. // struct: IGMP_GLOBAL_STATS
  29. //---------------------------------------------------
  30. typedef struct _GLOBAL_STATS {
  31. DWORD CurrentGroupMemberships;
  32. DWORD GroupMembershipsAdded;
  33. LARGE_INTEGER TimeWhenRtrStarted;
  34. } IGMP_GLOBAL_STATS, *PIGMP_GLOBAL_STATS;
  35. //-------------------------------------------------
  36. // static group structures(external)
  37. //-------------------------------------------------
  38. typedef struct _STATIC_GROUP_V3 {
  39. IGMP_STATIC_GROUP_V3;
  40. DWORD Sources[0];
  41. } STATIC_GROUP_V3, *PSTATIC_GROUP_V3;
  42. typedef struct _MIB_GROUP_INFO_V3 {
  43. IGMP_MIB_GROUP_INFO_V3;
  44. IGMP_MIB_GROUP_SOURCE_INFO_V3 Sources[0];
  45. } MIB_GROUP_INFO_V3, *PMIB_GROUP_INFO_V3;
  46. typedef PIGMP_MIB_GROUP_INFO PMIB_GROUP_INFO;
  47. typedef IGMP_MIB_GROUP_INFO MIB_GROUP_INFO;
  48. #define GET_FIRST_STATIC_GROUP_V3(pConfig) \
  49. ((PSTATIC_GROUP_V3)((PIGMP_MIB_IF_CONFIG)(pConfig)+1))
  50. #define GET_NEXT_STATIC_GROUP_V3(pStaticGroupV3) \
  51. ((PSTATIC_GROUP_V3) ((PCHAR)pStaticGroupV3+sizeof(IGMP_STATIC_GROUP_V3) \
  52. +sizeof(IPADDR)*pStaticGroupV3->NumSources))
  53. //----------------------------------------------------------------------------
  54. // struct: IF_STATIC_GROUP
  55. //----------------------------------------------------------------------------
  56. typedef struct _IF_STATIC_GROUP {
  57. LIST_ENTRY Link;
  58. STATIC_GROUP_V3;
  59. } IF_STATIC_GROUP, *PIF_STATIC_GROUP;
  60. //---------------------------------------------------------------
  61. // struct: IGMP_IF_CONFIG (same as mib structs in igmprm.h)
  62. //
  63. // if they are made different, then CopyMemory should not be used
  64. //---------------------------------------------------------------
  65. typedef struct _IGMP_IF_CONFIG {
  66. IGMP_MIB_IF_CONFIG;
  67. //v3: NonQuerier saves old values
  68. DWORD RobustnessVariableOld;
  69. DWORD GenQueryIntervalOld;
  70. DWORD OtherQuerierPresentIntervalOld;
  71. DWORD GroupMembershipTimeoutOld;
  72. DWORD ExtSize;
  73. LIST_ENTRY ListOfStaticGroups;
  74. } IGMP_IF_CONFIG, *PIGMP_IF_CONFIG;
  75. //---------------------------------------------------
  76. // struct: IF_INFO
  77. //---------------------------------------------------
  78. typedef struct _IF_INFO {
  79. UCHAR QuerierState; //if made DWORD, then change to interlocked operations
  80. DWORD QuerierIpAddr;
  81. LONGLONG QuerierPresentTimeout; //when the last query was heard. only if I am not querier
  82. LONGLONG LastQuerierChangeTime; // when the last querier was changed
  83. LONGLONG V1QuerierPresentTime; //when the last v1 query was heard
  84. LONGLONG OtherVerPresentTimeWarn; //when the last warning was given
  85. DWORD StartupQueryCountCurrent;
  86. DWORD GroupQueriesSent;
  87. DWORD GroupQueriesReceived;
  88. LONGLONG TimeWhenActivated;
  89. DWORD TotalIgmpPacketsReceived;
  90. DWORD TotalIgmpPacketsForRouter;
  91. DWORD GenQueriesSent;
  92. DWORD GenQueriesReceived;
  93. DWORD WrongVersionQueries;
  94. DWORD JoinsReceived;
  95. DWORD LeavesReceived;
  96. DWORD CurrentGroupMemberships;
  97. DWORD GroupMembershipsAdded;
  98. DWORD WrongChecksumPackets;
  99. DWORD ShortPacketsReceived;
  100. DWORD LongPacketsReceived;
  101. DWORD PacketsWithoutRtrAlert;
  102. DWORD PacketSize;
  103. } IF_INFO, *PIF_INFO;
  104. //---------------------------------------------------
  105. // struct RAS_CLIENT_INFO
  106. //---------------------------------------------------
  107. typedef struct _RAS_CLIENT_INFO {
  108. DWORD SendFailures;
  109. DWORD TotalIgmpPacketsReceived;
  110. DWORD TotalIgmpPacketsForRouter;
  111. DWORD GenQueriesReceived;
  112. DWORD JoinsReceived;
  113. DWORD LeavesReceived;
  114. DWORD CurrentGroupMemberships;
  115. DWORD GroupMembershipsAdded;
  116. DWORD GroupMembershipsRemoved;
  117. DWORD WrongChecksumPackets;
  118. DWORD ShortPacketsReceived;
  119. DWORD LongPacketsReceived;
  120. DWORD WrongVersionQueries;
  121. } RAS_CLIENT_INFO, *PRAS_CLIENT_INFO;
  122. //---------------------------------------------------
  123. // struct: RAS_TABLE_ENTRY
  124. //---------------------------------------------------
  125. typedef struct _RAS_TABLE_ENTRY {
  126. LIST_ENTRY LinkByAddr;
  127. LIST_ENTRY HTLinkByAddr;
  128. LIST_ENTRY ListOfSameClientGroups;
  129. DWORD NHAddr;
  130. struct _IF_TABLE_ENTRY *IfTableEntry;
  131. DWORD Status;
  132. RAS_CLIENT_INFO Info;
  133. DWORD CreationFlags; // see below.
  134. } RAS_TABLE_ENTRY, *PRAS_TABLE_ENTRY;
  135. //---------------------------------------------------
  136. // struct: RAS_TABLE
  137. //---------------------------------------------------
  138. #define RAS_HASH_TABLE_SZ 256
  139. typedef struct _RAS_TABLE {
  140. LIST_ENTRY ListByAddr; //links ras clients
  141. LIST_ENTRY HashTableByAddr[RAS_HASH_TABLE_SZ];
  142. struct _IF_TABLE_ENTRY *pIfTable; //ptr to interface table entry
  143. DWORD RefCount;
  144. DWORD Status;
  145. } RAS_TABLE, *PRAS_TABLE;
  146. //---------------------------------------------------
  147. // struct: SOCKET_EVENT_ENTRY
  148. //---------------------------------------------------
  149. typedef struct _SOCKET_EVENT_ENTRY {
  150. LIST_ENTRY LinkBySocketEvents;
  151. LIST_ENTRY ListOfInterfaces;
  152. DWORD NumInterfaces;
  153. HANDLE InputWaitEvent;
  154. HANDLE InputEvent;
  155. } SOCKET_EVENT_ENTRY, *PSOCKET_EVENT_ENTRY;
  156. //---------------------------------------------------
  157. // struct: SOCKET_ENTRY
  158. //---------------------------------------------------
  159. typedef struct _SOCKET_ENTRY {
  160. LIST_ENTRY LinkByInterfaces;
  161. SOCKET Socket;
  162. PSOCKET_EVENT_ENTRY pSocketEventsEntry;
  163. } SOCKET_ENTRY, *PSOCKET_ENTRY;
  164. //------------------------------------------------------------------------------
  165. // struct: IF_TABLE_ENTRY
  166. //
  167. // IF-table:Table_RWL protects LinkByAddr, LinkByIndex, HTLinkByIndex
  168. // IpAddr, Status, pBinding
  169. // IF-table:IfTableBucketCS protects ListOfSameIfGroups
  170. // Interlocked operations protect Info, Config
  171. //------------------------------------------------------------------------------
  172. typedef struct _IF_TABLE_ENTRY {
  173. LIST_ENTRY LinkByAddr; // sorted by Ipaddr.only activated interfaces
  174. LIST_ENTRY LinkByIndex; // sorted by Index. all interfaces
  175. LIST_ENTRY HTLinkByIndex; // not sorted within bucket
  176. LIST_ENTRY ListOfSameIfGroups; // sorted by GroupAddr. GI entries for IF (all GIs of Ras clients)
  177. LIST_ENTRY ListOfSameIfGroupsNew; // unmerged list. sorted by GroupAddr. GI entries same as above
  178. DWORD NumGIEntriesInNewList; // used to decide if lists should be merged
  179. UCHAR IfType; // IGMP_IF_ (NOT_RAS,RAS_ROUTER,RAS_SERVER). for external calls, IGMP_IF_PROXY might be set
  180. // set when interface is created. cannot be changed again.
  181. DWORD IfIndex;
  182. IPADDR IpAddr; // set when IF is bound. ==0 for un-numbered IFs.
  183. DWORD Status; // IF_(CREATED/BOUND/ENABLED/ACTIVATED),
  184. // IF_DEACTIVATE_DELETE_FLAG,
  185. // MGM_ENABLED_IGMPRTR_FLAG, IGMPRTR_MPROTOCOL_PRESENT_FLAG
  186. PRAS_TABLE pRasTable; // null if not IGMP_IF_RAS_SERVER. created in _AddIfEntry()
  187. PLIST_ENTRY pProxyHashTable; // g_pProxyHashTable: contains the proxy entries. They are also linked in
  188. // order using the LinkBySameIfGroups field accessed through pite.
  189. IGMP_IF_CONFIG Config;
  190. PIGMP_IF_BINDING pBinding; // null if not bound or unNumbered interface.
  191. IF_INFO Info;
  192. SOCKET_ENTRY SocketEntry; // used by igmpRouter for getting input, and binding to waitEvent
  193. // used by proxy to join the igmp groups as a host.
  194. IGMP_TIMER_ENTRY QueryTimer; // Querier mode: used for sending general query.
  195. IGMP_TIMER_ENTRY NonQueryTimer; // used when in NonQuerier mode: used for detecting other queriers
  196. HANDLE pPrevIfGroupEnumPtr; // points to the next GI entry to be enumerated.
  197. USHORT PrevIfGroupEnumSignature;//used in enumerating interface GI list in order
  198. SOCKET StaticGroupSocket; // used only by igmp Router. created in _CreateIfSockets and
  199. // closed in _DeleteIfSockets.
  200. // Static groups in proxy are joined on SocketEntry.
  201. DWORD CreationFlags; // see below.
  202. } IF_TABLE_ENTRY, *PIF_TABLE_ENTRY;
  203. //
  204. // values for CreationFlags
  205. //
  206. #define REGISTERED_PROTOCOL_WITH_MGM 0x0001
  207. #define TAKEN_INTERFACE_OWNERSHIP_WITH_MGM 0x0002
  208. #define DONE_STAR_STAR_JOIN 0x0004
  209. #define SOCKETS_CREATED 0x0008
  210. // the above flags are cleared during deactivation, while below flags
  211. // are retained across deactivations.
  212. #define CREATION_FLAGS_DEACTIVATION_CLEAR 0x00FF
  213. #define CREATED_PROXY_HASH_TABLE 0x0100
  214. // expand the table if the number of interface is greater than 16
  215. #define IF_HASHTABLE_SZ1 256
  216. #define IF_EXPAND_THRESHOLD1 256
  217. #define IF_HASHTABLE_SZ2 512
  218. //---------------------------------------------------
  219. // struct: IGMP_IF_TABLE
  220. //---------------------------------------------------
  221. typedef struct _IF_TABLE {
  222. LIST_ENTRY ListByAddr;
  223. LIST_ENTRY ListByIndex;
  224. DWORD Status;
  225. DWORD NumBuckets;
  226. DWORD NumInterfaces;
  227. PLIST_ENTRY HashTableByIndex;
  228. PDYNAMIC_CS_LOCK *aIfBucketDCS;
  229. PDYNAMIC_RW_LOCK *aIfBucketDRWL;
  230. CRITICAL_SECTION IfLists_CS; // CS protecting the 1st two lists
  231. } IGMP_IF_TABLE, *PIGMP_IF_TABLE;
  232. //---------------------------------------------------
  233. // struct: GI_INFO
  234. //---------------------------------------------------
  235. typedef struct _GROUP_INFO {
  236. DWORD LastReporter;
  237. LONGLONG GroupUpTime;
  238. LONGLONG GroupExpiryTime;
  239. LONGLONG V1HostPresentTimeLeft;
  240. // version 3 fields
  241. LONGLONG V2HostPresentTimeLeft;
  242. } GI_INFO, *PGROUP_INFO;
  243. //---------------------------------------------------
  244. // struct: GI_ENTRY (group-Interface entry)
  245. //---------------------------------------------------
  246. typedef struct _GI_ENTRY {
  247. LIST_ENTRY LinkByGI;
  248. LIST_ENTRY LinkBySameIfGroups;
  249. LIST_ENTRY LinkBySameClientGroups; //links all ras client groups
  250. DWORD IfIndex;
  251. DWORD Status; //bound,enabled,deleted,activated
  252. BOOL bRasClient; //rasclient or not
  253. BOOL bStaticGroup;
  254. PIF_TABLE_ENTRY pIfTableEntry;
  255. struct _GROUP_TABLE_ENTRY *pGroupTableEntry;
  256. //below two fields valid only for ras
  257. DWORD NHAddr;
  258. PRAS_TABLE_ENTRY pRasTableEntry;
  259. IGMP_TIMER_ENTRY GroupMembershipTimer;
  260. /*timerlock*///LastMemQueryCount left to be sent
  261. DWORD LastMemQueryCount;
  262. IGMP_TIMER_ENTRY LastMemQueryTimer;
  263. IGMP_TIMER_ENTRY LastVer1ReportTimer;/*timelock*/
  264. BYTE Version; //ver1, ver2, ver3
  265. GI_INFO Info;
  266. // igmpv3 fields. ignored for rest.
  267. IGMP_TIMER_ENTRY LastVer2ReportTimer;/*timelock*/
  268. DWORD FilterType;
  269. DWORD NumSources;
  270. LIST_ENTRY *V3InclusionList;
  271. LIST_ENTRY V3InclusionListSorted;
  272. LIST_ENTRY V3ExclusionList;
  273. //query sources
  274. LIST_ENTRY V3SourcesQueryList;
  275. DWORD V3SourcesQueryCount;
  276. BOOL bV3SourcesQueryNow;
  277. IGMP_TIMER_ENTRY V3SourcesQueryTimer;
  278. #if DEBUG_FLAGS_SIGNATURE
  279. DWORD Signature;//0xfadfad02
  280. #endif
  281. } GI_ENTRY, *PGI_ENTRY;
  282. //kslksl1 10
  283. #define SOURCES_BUCKET_SZ 1
  284. //---------------------------------------------------
  285. // struct: GI_SOURCE_ENTRY
  286. //---------------------------------------------------
  287. typedef struct _GI_SOURCE_ENTRY {
  288. LIST_ENTRY LinkSources;
  289. LIST_ENTRY LinkSourcesInclListSorted;
  290. LIST_ENTRY V3SourcesQueryList;
  291. PGI_ENTRY pGIEntry;
  292. BOOL bInclusionList;
  293. IPADDR IpAddr;
  294. //how many more src queries left to be sent
  295. DWORD V3SourcesQueryLeft;
  296. BOOL bInV3SourcesQueryList;
  297. //timeout sources in inc list
  298. IGMP_TIMER_ENTRY SourceExpTimer;
  299. LONGLONG SourceInListTime;
  300. BOOL bStaticSource;
  301. } GI_SOURCE_ENTRY, *PGI_SOURCE_ENTRY;
  302. #define GET_IF_CONFIG_FOR_SOURCE(pSourceEntry) \
  303. pSourceEntry->pGIEntry->pIfTableEntry->Config
  304. #define GET_IF_ENTRY_FOR_SOURCE(pSourceEntry) \
  305. pSourceEntry->pGIEntry->pIfTableEntry
  306. //---------------------------------------------------
  307. // struct: GROUP_TABLE_ENTRY
  308. //---------------------------------------------------
  309. typedef struct _GROUP_TABLE_ENTRY {
  310. LIST_ENTRY HTLinkByGroup;
  311. LIST_ENTRY LinkByGroup; //ordered list of groups
  312. LIST_ENTRY ListOfGIs;
  313. DWORD Group;
  314. DWORD GroupLittleEndian;
  315. DWORD NumVifs;
  316. DWORD Status;
  317. LONGLONG GroupUpTime;
  318. #if DEBUG_FLAGS_SIGNATURE
  319. DWORD Signature; //0xfadfad01
  320. #endif
  321. } GROUP_TABLE_ENTRY, *PGROUP_TABLE_ENTRY;
  322. #define GROUP_HASH_TABLE_SZ 256
  323. //---------------------------------------------------
  324. // struct: GROUP_TABLE
  325. //---------------------------------------------------
  326. typedef struct _GROUP_TABLE {
  327. LOCKED_LIST ListByGroup;
  328. LIST_ENTRY ListByGroupNew;
  329. DWORD NumGroupsInNewList;
  330. DWORD Status;
  331. LONG NumIfs; //Interlocked Operations
  332. DYNAMIC_CS_LOCKED_LIST HashTableByGroup[GROUP_HASH_TABLE_SZ];
  333. } GROUP_TABLE, *PGROUP_TABLE;
  334. //-------------------------------------------------
  335. // Proxy group entry
  336. //-------------------------------------------------
  337. typedef struct _PROXY_GROUP_ENTRY {
  338. LIST_ENTRY HT_Link;
  339. LIST_ENTRY LinkBySameIfGroups;
  340. //v3
  341. LIST_ENTRY ListSources;
  342. DWORD Group;
  343. DWORD GroupLittleEndian;
  344. DWORD RefCount;
  345. LONGLONG InitTime;
  346. BOOL bStaticGroup;
  347. //v3
  348. DWORD NumSources;
  349. DWORD FilterType;
  350. } PROXY_GROUP_ENTRY, *PPROXY_GROUP_ENTRY;
  351. typedef struct _PROXY_SOURCE_ENTRY {
  352. LIST_ENTRY LinkSources;
  353. IPADDR IpAddr;
  354. DWORD RefCount;
  355. BOOL bStaticSource;
  356. DWORD JoinMode;//ALLOW,BLOCK, NO_STATE
  357. DWORD JoinModeIntended;
  358. } PROXY_SOURCE_ENTRY, *PPROXY_SOURCE_ENTRY;
  359. //-------------------------------------------------
  360. // prototypes
  361. //-------------------------------------------------
  362. DWORD
  363. CreateIfSockets (
  364. PIF_TABLE_ENTRY pite
  365. );
  366. VOID
  367. DeleteIfSockets (
  368. PIF_TABLE_ENTRY pite
  369. );
  370. VOID
  371. DeleteAllTimers (
  372. PLIST_ENTRY pHead,
  373. DWORD bEntryType //RAS_CLIENT, NOT_RAS_CLIENT
  374. );
  375. DWORD
  376. DeleteGIEntry (
  377. PGI_ENTRY pgie, //group interface entry
  378. BOOL bUpdateStats,
  379. BOOL bCallMgm
  380. );
  381. VOID
  382. DeleteAllGIEntries(
  383. PIF_TABLE_ENTRY pite
  384. );
  385. VOID
  386. DeleteGIEntryFromIf (
  387. PGI_ENTRY pgie //group interface entry
  388. );
  389. VOID
  390. MergeGroupLists(
  391. );
  392. VOID
  393. MergeIfGroupsLists(
  394. PIF_TABLE_ENTRY pite
  395. );
  396. VOID
  397. MergeProxyLists(
  398. PIF_TABLE_ENTRY pite
  399. );
  400. DWORD
  401. CopyinIfConfig (
  402. PIGMP_IF_CONFIG pConfig,
  403. PIGMP_MIB_IF_CONFIG pConfigExt,
  404. DWORD IfIndex
  405. );
  406. DWORD
  407. CopyinIfConfigAndUpdate (
  408. PIF_TABLE_ENTRY pite,
  409. PIGMP_MIB_IF_CONFIG pConfigExt,
  410. ULONG IfIndex
  411. );
  412. VOID
  413. CopyoutIfConfig (
  414. PIGMP_MIB_IF_CONFIG pConfigExt,
  415. PIF_TABLE_ENTRY pite
  416. );
  417. DWORD
  418. ValidateIfConfig (
  419. PIGMP_MIB_IF_CONFIG pConfigExt,
  420. DWORD IfIndex,
  421. DWORD IfType,
  422. ULONG StructureVersion,
  423. ULONG StructureSize
  424. );
  425. DWORD
  426. InitializeIfTable (
  427. );
  428. VOID
  429. DeInitializeIfTable (
  430. );
  431. DWORD
  432. InitializeGroupTable (
  433. );
  434. VOID
  435. DeInitializeGroupTable (
  436. );
  437. DWORD
  438. InitializeRasTable(
  439. DWORD IfIndex,
  440. PIF_TABLE_ENTRY pite
  441. );
  442. VOID
  443. DeInitializeRasTable (
  444. PIF_TABLE_ENTRY pite,
  445. BOOL bFullCleanup
  446. );
  447. #endif // _IGMP_TABLE_H_