Windows NT 4.0 source code leak
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.
 
 
 
 
 
 

402 lines
10 KiB

/*++
Copyright (c) 1994 Microsoft Corporation
Copyright (c) 1993 Micro Computer Systems, Inc.
Module Name:
net\svcdlls\nwsap\server\bindlib.c
Abstract:
This routine handles the BindLib API for the SAP Agent
Author:
Brian Walker (MCS) 06-15-1993
Revision History:
--*/
#include "precomp.h"
#pragma hdrstop
#define BINDLIB_BITS 0xC0000000
#define BINDLIB_MASK 0x1FFFFFFF
/*++
*******************************************************************
S a p G e t O b j e c t N a m e I n t e r n a l
Routine Description:
This routine converts an Object ID into an Object Name
and Type.
Arguments:
ObjectID = Object ID to convert
ObjectName = Ptr to where to store 48 byte object name
ObjectType = Ptr to where to store the object type
ObjectAddr = Ptr to where to store NET_ADDRESS (12 bytes)
ObjectName, ObjectType, ObjectAddr can be NULL.
Return Value:
SAPRETURN_SUCCESS = OK - name and type are filled in
SAPRETURN_NOTEXIST = Invalid object id.
*******************************************************************
--*/
INT
SapGetObjectNameInternal(
IN ULONG ObjectID,
IN PUCHAR ObjectName,
IN PUSHORT ObjectType,
IN PUCHAR ObjectAddr)
{
PSAP_RECORD Entry;
/** Make sure the object ID is valid **/
if ((ObjectID & BINDLIB_BITS) != BINDLIB_BITS)
return SAPRETURN_NOTEXIST;
/** Convert the Object ID into an index number **/
ObjectID &= BINDLIB_MASK;
/** Make sure the index number is valid **/
if (ObjectID >= (ULONG)SapNumArrayEntries)
return SAPRETURN_NOTEXIST;
/** Get a ptr to the entry **/
ACQUIRE_READERS_LOCK("SapGetObjectName");
Entry = GETPTRFROMINDEX(ObjectID);
if (Entry == NULL) {
RELEASE_READERS_LOCK("SapGetObjectName X1");
return SAPRETURN_NOTEXIST;
}
/** If in free list - return error **/
if ((Entry->ServType == 0xFFFF) ||
(Entry->HeadIndex == SDMD_ENDOFLIST) ||
(Entry->HopCount == 16)) {
RELEASE_READERS_LOCK("SapGetObjectName X2");
return SAPRETURN_NOTEXIST;
}
/** Return the entry **/
if (ObjectType)
*ObjectType = Entry->ServType;
if (ObjectName)
SAP_COPY_SERVNAME(ObjectName, Entry->ServName);
if (ObjectAddr)
SAP_COPY_ADDRESS(ObjectAddr, Entry->ServAddress);
/** All Done OK **/
RELEASE_READERS_LOCK("SapGetObjectName X3");
return SAPRETURN_SUCCESS;
}
/*++
*******************************************************************
S a p G e t O b j e c t I D I n t e r n a l
Routine Description:
This routine converts a name and type into an object ID.
Arguments:
ObjectName = Ptr to 48 byte object name (Must be uppercase)
ObjectType = Object type to look for
ObjectID = Ptr to where to store the object ID.
Return Value:
SAPRETURN_SUCCESS = OK - Object ID is filled in
SAPRETURN_NOTEXIST = Name/Type not found
*******************************************************************
--*/
INT
SapGetObjectIDInternal(
IN PUCHAR ObjectName,
IN USHORT ObjectType,
IN PULONG ObjectID)
{
PSAP_RECORD Entry;
PSDMD_LIST_ENTRY ListHead;
INT HashIndex;
INT rc;
/** Cannot have wildcard **/
if (ObjectType == 0xFFFF)
return SAPRETURN_NOTEXIST;
/** Lock the database **/
ACQUIRE_READERS_LOCK("SapGetObjectId");
/** Get the name from the hash table **/
HashIndex = SdmdCalcHash(ObjectName);
/** Get ptr to the list head for the hash index **/
ListHead = SdmdNameHashTable + HashIndex;
/** Find the name in the list **/
Entry = GETPTRFROMINDEX(ListHead->Flink);
while (Entry) {
/**
Make sure the Object Type is correct and that this entry
is not marked for deletion.
**/
if ((Entry->ServType == ObjectType) && (Entry->HopCount != 16)) {
/** Check if this is the name **/
rc = SAP_NAMECMP(Entry->ServName, ObjectName);
/** If this is it - return it **/
if (!rc) {
/** Build the object ID and return it **/
*ObjectID = (ULONG)(Entry->Index | BINDLIB_BITS);
RELEASE_READERS_LOCK("SapGetObjectId X2");
return SAPRETURN_SUCCESS;
}
/**
Since the names are stored in alphabetical order, if we
get past the name we are looking for, then we can just
give up now instead of having to search the whole list.
**/
if (rc > 0)
break;
}
/** Goto the next entry **/
Entry = GETPTRFROMINDEX(Entry->Links[SAP_HASHLIST_INDEX].Flink);
}
/** There is not an entry for that name/type **/
RELEASE_READERS_LOCK("SapGetObjectId X3");
return SAPRETURN_NOTEXIST;
}
/*++
*******************************************************************
S a p S c a n O b j e c t I n t e r n a l
Routine Description:
This routine is used to scan thru the database list.
Arguments:
ObjectID = Ptr to last Object ID we saw. On first call
this should point to a 0xFFFFFFFF.
ObjectName = Ptr to where to store 48 byte object name
ObjectType = Ptr to where to store the object type
ScanType = Object Type that we are scanning for
(0xFFFF = All)
ObjectName, ObjectType can be NULL.
Return Value:
SAPRETURN_SUCCESS = OK - name and type are filled in
ObjectID has the object ID of this entry.
SAPRETURN_NOTEXIST = Invalid object id.
*******************************************************************
--*/
INT
SapScanObjectInternal(
IN PULONG ObjectID,
IN PUCHAR ObjectName,
IN PUSHORT ObjectType,
IN USHORT ScanType)
{
PSAP_RECORD Entry;
PSAP_RECORD HeadEntry;
ULONG id;
/** Get the readers lock **/
ACQUIRE_READERS_LOCK("SapScanObject Entry");
/**
Get the ID and validate it. If the ID is 0xFFFFFFFF, then
we start with the first entry in the type list.
If it is not 0xFFFFFFFF - then we get that entry and
get it's fwd pointer in the type list as the next one to return.
**/
id = *ObjectID;
if (id == 0xFFFFFFFF) {
/** Get ptr to entry at head of the type list **/
HeadEntry = GETPTRFROMINDEX(SdmdLists[SAP_TYPELIST_INDEX].Flink);
if (ScanType != 0xFFFF) {
while (HeadEntry && (HeadEntry->ServType < ScanType)) {
HeadEntry = GETPTRFROMINDEX(HeadEntry->Links[SAP_TYPELIST_INDEX].Flink);
}
}
/** If no type found - return error **/
if ((HeadEntry == NULL) || (HeadEntry->ServType == 0xFFFF)) {
RELEASE_READERS_LOCK("SapScanObject X1");
return SAPRETURN_NOTEXIST;
}
/** If not wildcard - make sure it matches type we want **/
if (ScanType != 0xFFFF) {
if (HeadEntry->ServType != ScanType) {
RELEASE_READERS_LOCK("SapScanObject X2");
return SAPRETURN_NOTEXIST;
}
}
/** Get ptr to first entry in this sublist **/
Entry = GETPTRFROMINDEX(HeadEntry->Links[SAP_SUBLIST_INDEX].Flink);
}
else {
/**
This is a SCAN NEXT type call. Take the object ID and
get the forward pointer to it and verify that it is for
the same object type as before.
**/
if ((id & BINDLIB_BITS) != BINDLIB_BITS) {
RELEASE_READERS_LOCK("SapScanObject X4");
return SAPRETURN_NOTEXIST;
}
id &= BINDLIB_MASK; /* Convert to an index */
/** Make sure the index number is valid **/
if (id >= (ULONG)SapNumArrayEntries) {
RELEASE_READERS_LOCK("SapGetObjectName X5");
return SAPRETURN_NOTEXIST;
}
/**
Get ptr to the entry. If the ptr is bad or the entry
is on the free list - then we should return an error.
**/
Entry = GETPTRFROMINDEX(id);
if ((Entry == NULL) || (Entry->ServType == 0xFFFF) || (Entry->HeadIndex == SDMD_ENDOFLIST)) {
RELEASE_READERS_LOCK("SapGetObjectName X6");
return SAPRETURN_NOTEXIST;
}
/** Get the head entry for this entry **/
HeadEntry = GETPTRFROMINDEX(Entry->HeadIndex);
SS_ASSERT(HeadEntry);
/**
Now we get the ptr to the next entry in the sub list.
This is the entry we will return (If there is one).
**/
Entry = GETPTRFROMINDEX(Entry->Links[SAP_SUBLIST_INDEX].Flink);
}
/**
Entry is the entry we start with. This could be NULL.
Entry and HeadEntry are set here. HeadEntry must be non-NULL.
**/
while (1) {
/**
If we hit the end of this sublist - then we can go to the next
sublist if the scan type is for wildcard.
**/
if (Entry == NULL) {
/** If not wildcard - return error **/
if (ScanType != 0xFFFF) {
RELEASE_READERS_LOCK("SapGetObjectName X7");
return SAPRETURN_NOTEXIST;
}
/** This is for wildcard - get next HeadEntry **/
HeadEntry = GETPTRFROMINDEX(HeadEntry->Links[SAP_TYPELIST_INDEX].Flink);
if ((HeadEntry == NULL) || (HeadEntry->ServType == 0xFFFF)) {
RELEASE_READERS_LOCK("SapGetObjectName X8");
return SAPRETURN_NOTEXIST;
}
/** Get ptr to first entry in this list **/
Entry = GETPTRFROMINDEX(HeadEntry->Links[SAP_SUBLIST_INDEX].Flink);
}
/** If we got one - return it **/
if (Entry) {
/** If valid entry - return it **/
if (Entry->HopCount != 16)
break;
/** Get ptr to next entry in the list **/
Entry = GETPTRFROMINDEX(Entry->Links[SAP_SUBLIST_INDEX].Flink);
}
/** We go back up to try again **/
}
/** Return the entry **/
*ObjectID = (ULONG)(Entry->Index | BINDLIB_BITS);
if (ObjectType)
*ObjectType = Entry->ServType;
if (ObjectName)
SAP_COPY_SERVNAME(ObjectName, Entry->ServName);
/** All Done OK **/
RELEASE_READERS_LOCK("SapGetObjectName X9");
return SAPRETURN_SUCCESS;
}