276 lines
6.3 KiB
C
276 lines
6.3 KiB
C
|
/*++
|
|||
|
|
|||
|
Copyright (c) 1992 Microsoft Corporation
|
|||
|
|
|||
|
Module Name:
|
|||
|
|
|||
|
node.h
|
|||
|
|
|||
|
Abstract:
|
|||
|
|
|||
|
This module contains support for the Appletalk Node structure.
|
|||
|
|
|||
|
Author:
|
|||
|
|
|||
|
Jameel Hyder (jameelh@microsoft.com)
|
|||
|
Nikhil Kamkolkar (nikhilk@microsoft.com)
|
|||
|
|
|||
|
Revision History:
|
|||
|
19 Jun 1992 Initial Version
|
|||
|
|
|||
|
Notes: Tab stop: 4
|
|||
|
--*/
|
|||
|
|
|||
|
#ifndef _NODE_
|
|||
|
#define _NODE_
|
|||
|
|
|||
|
#define ANY_ROUTER_NODE 0
|
|||
|
#define UNKNOWN_NODE 0
|
|||
|
#define MAX_ATALK_NODES 256
|
|||
|
#define MIN_USABLE_ATALKNODE 1
|
|||
|
#define MAX_USABLE_ATALKNODE 254
|
|||
|
#define MAX_EXT_ATALKNODE 253
|
|||
|
#define HIGHEST_WORKSTATION_NODE 127
|
|||
|
#define LOWEST_SERVER_NODE 128
|
|||
|
#define ATALK_BROADCAST_NODE ((BYTE)0xFF)
|
|||
|
#define NUM_USER_NODES 2
|
|||
|
|
|||
|
|
|||
|
// NODE STATES
|
|||
|
#define AN_OPEN 0x01
|
|||
|
#define AN_ROUTER_NODE 0x02
|
|||
|
#define AN_ORPHAN_NODE 0x04
|
|||
|
#define AN_CLOSING 0x80
|
|||
|
|
|||
|
// values under which pram nodes are stored
|
|||
|
#define ROUTER_NODE_VALUE L"RouterPramNode"
|
|||
|
#define USER_NODE1_VALUE L"UserPramNode1"
|
|||
|
#define USER_NODE2_VALUE L"UserPramNode2"
|
|||
|
|
|||
|
// Number of slots in the socket hash table stored per node
|
|||
|
#define NODE_DDPAO_HASH_SIZE 8
|
|||
|
|
|||
|
#define AN_SIGNATURE (*(PULONG)"ANOD")
|
|||
|
#if DBG
|
|||
|
#define VALID_ATALK_NODE(pNode) (((pNode) != NULL) && \
|
|||
|
((pNode)->an_Signature == AN_SIGNATURE))
|
|||
|
#else
|
|||
|
#define VALID_ATALK_NODE(pNode) ((pNode) != NULL)
|
|||
|
#endif
|
|||
|
typedef struct _ATALK_NODE
|
|||
|
{
|
|||
|
|
|||
|
#if DBG
|
|||
|
ULONG an_Signature;
|
|||
|
#endif
|
|||
|
|
|||
|
// List for all active nodes on a port
|
|||
|
struct _ATALK_NODE * an_Next;
|
|||
|
|
|||
|
ULONG an_RefCount;
|
|||
|
|
|||
|
// Backpointer to the port for this node
|
|||
|
struct _PORT_DESCRIPTOR *an_Port;
|
|||
|
|
|||
|
// State of the node
|
|||
|
BYTE an_Flags;
|
|||
|
|
|||
|
// Next dynamic socket number to create on this node.
|
|||
|
BYTE an_NextDynSkt;
|
|||
|
|
|||
|
// Nbp Id & Enumerator to use on the next NbpAction
|
|||
|
BYTE an_NextNbpId;
|
|||
|
BYTE an_NextNbpEnum;
|
|||
|
|
|||
|
// Hash List of ddp address objects (accessed by the
|
|||
|
// Appletalk socket address) on this node
|
|||
|
struct _DDP_ADDROBJ * an_DdpAoHash[NODE_DDPAO_HASH_SIZE];
|
|||
|
|
|||
|
// Address of this node
|
|||
|
ATALK_NODEADDR an_NodeAddr;
|
|||
|
|
|||
|
// Lock
|
|||
|
ATALK_SPIN_LOCK an_Lock;
|
|||
|
} ATALK_NODE, *PATALK_NODE;
|
|||
|
|
|||
|
// Exports
|
|||
|
|
|||
|
VOID
|
|||
|
AtalkNodeRefByAddr(
|
|||
|
IN PPORT_DESCRIPTOR pPortDesc,
|
|||
|
IN PATALK_NODEADDR pNodeAddr,
|
|||
|
OUT PATALK_NODE * pNode,
|
|||
|
OUT PATALK_ERROR pErr
|
|||
|
);
|
|||
|
|
|||
|
// VOID
|
|||
|
// AtalkNodeRefByPtr(
|
|||
|
// IN OUT PATALK_NODE Node,
|
|||
|
// OUT PATALK_ERROR pErr
|
|||
|
// );
|
|||
|
#define AtalkNodeRefByPtr(_pNode, _pErr) \
|
|||
|
{ \
|
|||
|
KIRQL OldIrql; \
|
|||
|
\
|
|||
|
ASSERT(VALID_ATALK_NODE(_pNode)); \
|
|||
|
\
|
|||
|
ACQUIRE_SPIN_LOCK(&(_pNode)->an_Lock, &OldIrql);\
|
|||
|
AtalkNodeRefByPtrNonInterlock(_pNode, _pErr); \
|
|||
|
RELEASE_SPIN_LOCK(&(_pNode)->an_Lock, OldIrql); \
|
|||
|
}
|
|||
|
|
|||
|
// VOID
|
|||
|
// AtalkNodeRefByPtrNonInterlock(
|
|||
|
// IN OUT PATALK_NODE Node,
|
|||
|
// OUT PATALK_ERROR pErr
|
|||
|
// );
|
|||
|
|
|||
|
#define AtalkNodeRefByPtrNonInterlock(_pNode, _pErr) \
|
|||
|
{ \
|
|||
|
ASSERT(VALID_ATALK_NODE(_pNode)); \
|
|||
|
\
|
|||
|
if (((_pNode)->an_Flags & AN_CLOSING) == 0) \
|
|||
|
{ \
|
|||
|
(_pNode)->an_RefCount++; \
|
|||
|
*(_pErr) = ATALK_NO_ERROR; \
|
|||
|
} \
|
|||
|
else \
|
|||
|
{ \
|
|||
|
*(_pErr) = ATALK_NODE_CLOSING; \
|
|||
|
DBGPRINT(DBG_COMP_NODE, DBG_LEVEL_WARN, \
|
|||
|
("AtalkNodeRefByPtrNonInterlock: Attempt to ref a closing node %lx (%x.%x)\n",\
|
|||
|
_pNode, (_pNode)->an_NodeAddr.atn_Network, (_pNode)->an_NodeAddr.atn_Node));\
|
|||
|
} \
|
|||
|
}
|
|||
|
|
|||
|
VOID
|
|||
|
AtalkNodeRefNextNc(
|
|||
|
IN PATALK_NODE pNode,
|
|||
|
IN PATALK_NODE * ppNode,
|
|||
|
OUT PATALK_ERROR pErr
|
|||
|
);
|
|||
|
|
|||
|
VOID
|
|||
|
AtalkNodeDeref(
|
|||
|
IN OUT PATALK_NODE pNode
|
|||
|
);
|
|||
|
|
|||
|
ATALK_ERROR
|
|||
|
AtalkInitNodeCreateOnPort(
|
|||
|
IN PPORT_DESCRIPTOR pPortDesc,
|
|||
|
IN BOOLEAN AllowStartupRange,
|
|||
|
IN BOOLEAN RouterNode,
|
|||
|
IN PATALK_NODEADDR pNodeAddr
|
|||
|
);
|
|||
|
|
|||
|
ATALK_ERROR
|
|||
|
AtalkNodeReleaseOnPort(
|
|||
|
IN PPORT_DESCRIPTOR pPortDesc,
|
|||
|
IN PATALK_NODE pNode
|
|||
|
);
|
|||
|
|
|||
|
BOOLEAN
|
|||
|
AtalkNodeExistsOnPort(
|
|||
|
IN PPORT_DESCRIPTOR pPortDesc,
|
|||
|
IN PATALK_NODEADDR pNodeAddr
|
|||
|
);
|
|||
|
|
|||
|
ATALK_ERROR
|
|||
|
AtalkInitNodeAllocate(
|
|||
|
IN PPORT_DESCRIPTOR pPortDesc,
|
|||
|
OUT PATALK_NODE * ppNode
|
|||
|
);
|
|||
|
|
|||
|
// MACROS
|
|||
|
|
|||
|
#if DBG
|
|||
|
#define AtalkNodeReferenceByAddr(pPortDesc,NodeAddr,Node, pErr) \
|
|||
|
{ \
|
|||
|
AtalkNodeRefByAddr(pPortDesc,NodeAddr,Node, pErr); \
|
|||
|
if (ATALK_SUCCESS(*pErr)) \
|
|||
|
{ \
|
|||
|
DBGPRINT(DBG_COMP_NODE, DBG_LEVEL_REFNODE, \
|
|||
|
("AtalkNodeRefByAddr : %s %d PostCount %d\n", \
|
|||
|
__FILE__, __LINE__,(*Node)->an_RefCount)); \
|
|||
|
} \
|
|||
|
}
|
|||
|
|
|||
|
#define AtalkNodeReferenceByPtr(Node, pErr) \
|
|||
|
{ \
|
|||
|
AtalkNodeRefByPtr(Node, pErr); \
|
|||
|
DBGPRINT(DBG_COMP_NODE, DBG_LEVEL_REFNODE, \
|
|||
|
("AtalkNodeRefByPtr : %s %d PostCount %d\n", \
|
|||
|
__FILE__, __LINE__, Node->an_RefCount)) \
|
|||
|
}
|
|||
|
|
|||
|
#define AtalkNodeReferenceByPtrNonInterlock(Node, pErr) \
|
|||
|
{ \
|
|||
|
AtalkNodeRefByPtrNonInterlock(Node, pErr); \
|
|||
|
DBGPRINT(DBG_COMP_NODE, DBG_LEVEL_REFNODE, \
|
|||
|
("AtalkNodeRefByPtrNi : %s %d PostCount %d\n", \
|
|||
|
__FILE__, __LINE__,Node->an_RefCount)); \
|
|||
|
}
|
|||
|
|
|||
|
#define AtalkNodeReferenceNextNc(pNode, ppNode, pErr) \
|
|||
|
{ \
|
|||
|
AtalkNodeRefNextNc(pNode, ppNode, pErr); \
|
|||
|
if (ATALK_SUCCESS(*pErr)) \
|
|||
|
{ \
|
|||
|
DBGPRINT(DBG_COMP_NODE, DBG_LEVEL_REFNODE, \
|
|||
|
("AtalkNodeRefByPtrNc : %s %d PostCount %d\n", \
|
|||
|
__FILE__, __LINE__, (*ppNode)->an_RefCount)); \
|
|||
|
} \
|
|||
|
}
|
|||
|
|
|||
|
#define AtalkNodeDereference(Node) \
|
|||
|
{ \
|
|||
|
DBGPRINT(DBG_COMP_NODE, DBG_LEVEL_REFNODE, \
|
|||
|
("AtalkNodeDerefByPtr : %s %d PreCount %d\n", \
|
|||
|
__FILE__, __LINE__,Node->an_RefCount)); \
|
|||
|
AtalkNodeDeref(Node); \
|
|||
|
}
|
|||
|
|
|||
|
#else
|
|||
|
#define AtalkNodeReferenceByAddr(pPortDesc,NodeAddr,Node, pErr) \
|
|||
|
AtalkNodeRefByAddr(pPortDesc,NodeAddr,Node, pErr)
|
|||
|
|
|||
|
#define AtalkNodeReferenceByPtr(Node, pErr) \
|
|||
|
AtalkNodeRefByPtr(Node, pErr)
|
|||
|
|
|||
|
#define AtalkNodeReferenceByPtrNonInterlock(Node, pErr) \
|
|||
|
AtalkNodeRefByPtrNonInterlock(Node, pErr)
|
|||
|
|
|||
|
#define AtalkNodeReferenceNextNcNonInterlock(pNode, ppNode, pErr)\
|
|||
|
AtalkNodeRefNextNcNonInterlock(pNode, ppNode, pErr)
|
|||
|
|
|||
|
#define AtalkNodeReferenceNextNc(pNode, ppNode, pErr) \
|
|||
|
AtalkNodeRefNextNc(pNode, ppNode, pErr);
|
|||
|
|
|||
|
#define AtalkNodeDereference(Node) AtalkNodeDeref(Node)
|
|||
|
#endif
|
|||
|
|
|||
|
|
|||
|
VOID
|
|||
|
AtalkInitNodeSavePramAddr(
|
|||
|
IN PPORT_DESCRIPTOR pPortDesc,
|
|||
|
IN PWSTR RegValue,
|
|||
|
IN PATALK_NODEADDR Node
|
|||
|
);
|
|||
|
|
|||
|
VOID
|
|||
|
AtalkInitNodeGetPramAddr(
|
|||
|
IN PPORT_DESCRIPTOR pPortDesc,
|
|||
|
IN PWSTR RegValue,
|
|||
|
OUT PATALK_NODEADDR Node
|
|||
|
);
|
|||
|
|
|||
|
|
|||
|
VOID
|
|||
|
AtalkZapPramValue(
|
|||
|
IN PPORT_DESCRIPTOR pPortDesc,
|
|||
|
IN PWSTR RegValue
|
|||
|
);
|
|||
|
|
|||
|
#endif // _NODE_
|
|||
|
|
|||
|
|