721 lines
20 KiB
C
721 lines
20 KiB
C
|
/**********************************************************************/
|
||
|
/** Microsoft Windows/NT **/
|
||
|
/** Copyright(c) Microsoft Corporation, 1997 - 1999 **/
|
||
|
/**********************************************************************/
|
||
|
|
||
|
/*
|
||
|
general.h
|
||
|
Header file for the general DHCP snapin admin classes
|
||
|
|
||
|
FILE HISTORY:
|
||
|
|
||
|
*/
|
||
|
|
||
|
#ifndef _GENERAL_H
|
||
|
#define _GENERAL_H
|
||
|
|
||
|
extern const TCHAR g_szDefaultHelpTopic[];
|
||
|
|
||
|
#define SCOPE_DFAULT_LEASE_DAYS 8
|
||
|
#define SCOPE_DFAULT_LEASE_HOURS 0
|
||
|
#define SCOPE_DFAULT_LEASE_MINUTES 0
|
||
|
|
||
|
#define MSCOPE_DFAULT_LEASE_DAYS 30
|
||
|
#define MSCOPE_DFAULT_LEASE_HOURS 0
|
||
|
#define MSCOPE_DFAULT_LEASE_MINUTES 0
|
||
|
|
||
|
#define DYN_BOOTP_DFAULT_LEASE_DAYS 30
|
||
|
#define DYN_BOOTP_DFAULT_LEASE_HOURS 0
|
||
|
#define DYN_BOOTP_DFAULT_LEASE_MINUTES 0
|
||
|
|
||
|
#define DHCP_IP_ADDRESS_INVALID ((DHCP_IP_ADDRESS)0)
|
||
|
|
||
|
#define DHCP_OPTION_ID_CSR 249
|
||
|
|
||
|
class CDhcpServer;
|
||
|
|
||
|
class CTimerDesc
|
||
|
{
|
||
|
public:
|
||
|
SPITFSNode spNode;
|
||
|
CDhcpServer * pServer;
|
||
|
UINT_PTR uTimer;
|
||
|
TIMERPROC timerProc;
|
||
|
};
|
||
|
|
||
|
typedef CArray<CTimerDesc *, CTimerDesc *> CTimerArrayBase;
|
||
|
|
||
|
class CTimerMgr : CTimerArrayBase
|
||
|
{
|
||
|
public:
|
||
|
CTimerMgr();
|
||
|
~CTimerMgr();
|
||
|
|
||
|
public:
|
||
|
int AllocateTimer(ITFSNode * pNode, CDhcpServer * pServer, UINT uTimerValue, TIMERPROC TimerProc);
|
||
|
void FreeTimer(UINT_PTR uEventId);
|
||
|
void ChangeInterval(UINT_PTR uEventId, UINT uNewInterval);
|
||
|
CTimerDesc * GetTimerDesc(UINT_PTR uEventId);
|
||
|
CCriticalSection m_csTimerMgr;
|
||
|
};
|
||
|
|
||
|
typedef CArray<DWORD_DWORD, DWORD_DWORD> CDWordDWordArray;
|
||
|
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
//
|
||
|
// CDhcpIpRange prototype
|
||
|
//
|
||
|
// Simple wrapper for a DHCP_IP_RANGE
|
||
|
//
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
class CDhcpClient
|
||
|
{
|
||
|
public:
|
||
|
CDhcpClient ( const DHCP_CLIENT_INFO * pdhcClientInfo ) ;
|
||
|
CDhcpClient ( const DHCP_CLIENT_INFO_V4 * pdhcClientInfo ) ;
|
||
|
CDhcpClient () ;
|
||
|
~ CDhcpClient () ;
|
||
|
|
||
|
const CString & QueryName () const
|
||
|
{ return m_strName ; }
|
||
|
const CString & QueryComment () const
|
||
|
{ return m_strComment ; }
|
||
|
const CString & QueryHostName ( BOOL bNetbios = FALSE ) const
|
||
|
{ return bNetbios ? m_strHostNetbiosName : m_strHostName ; }
|
||
|
DHCP_IP_ADDRESS QueryIpAddress () const
|
||
|
{ return m_dhcpIpAddress ; }
|
||
|
DHCP_IP_MASK QuerySubnet () const
|
||
|
{ return m_dhcpIpMask ; }
|
||
|
DHCP_IP_ADDRESS QueryHostAddress () const
|
||
|
{ return m_dhcpIpHost ; }
|
||
|
const DATE_TIME & QueryExpiryDateTime () const
|
||
|
{ return m_dtExpires ; }
|
||
|
const CByteArray & QueryHardwareAddress () const
|
||
|
{ return m_baHardwareAddress ; }
|
||
|
BYTE QueryClientType() const
|
||
|
{ return m_bClientType; }
|
||
|
|
||
|
BOOL IsReservation () const
|
||
|
{ return m_bReservation ; }
|
||
|
void SetReservation ( BOOL bReservation = TRUE )
|
||
|
{ m_bReservation = bReservation ; }
|
||
|
|
||
|
// Data change accessors: SOME OF THESE THROW EXCEPTIONS
|
||
|
void SetIpAddress ( DHCP_IP_ADDRESS dhipa )
|
||
|
{ m_dhcpIpAddress = dhipa ; }
|
||
|
void SetIpMask ( DHCP_IP_ADDRESS dhipa )
|
||
|
{ m_dhcpIpMask = dhipa ; }
|
||
|
void SetName ( const CString & cName )
|
||
|
{ m_strName = cName ; }
|
||
|
void SetComment( const CString & cComment )
|
||
|
{ m_strComment = cComment ; }
|
||
|
void SetHostName ( const CString & cHostName )
|
||
|
{ m_strHostName = cHostName ; }
|
||
|
void SetHostNetbiosName ( const CString & cHostNbName )
|
||
|
{ m_strHostNetbiosName = cHostNbName ; }
|
||
|
void SetHostIpAddress ( DHCP_IP_ADDRESS dhipa )
|
||
|
{ m_dhcpIpHost = dhipa ; }
|
||
|
void SetExpiryDateTime ( DATE_TIME dt )
|
||
|
{ m_dtExpires = dt ; }
|
||
|
void SetHardwareAddress ( const CByteArray & caByte ) ;
|
||
|
void SetClientType(BYTE bClientType)
|
||
|
{ m_bClientType = bClientType; }
|
||
|
|
||
|
protected:
|
||
|
void InitializeData(const DHCP_CLIENT_INFO * pdhcClientInfo);
|
||
|
|
||
|
protected:
|
||
|
DHCP_IP_ADDRESS m_dhcpIpAddress; // Client's IP address
|
||
|
DHCP_IP_MASK m_dhcpIpMask; // Client's subnet
|
||
|
CByteArray m_baHardwareAddress; // hardware addresss
|
||
|
CString m_strName; // Client name
|
||
|
CString m_strComment; // Client comment
|
||
|
DATE_TIME m_dtExpires; // date/time lease expires
|
||
|
BOOL m_bReservation; // This is a reservation
|
||
|
BYTE m_bClientType; // Client Type V4 and above only
|
||
|
// Host information
|
||
|
CString m_strHostName;
|
||
|
CString m_strHostNetbiosName;
|
||
|
DHCP_IP_ADDRESS m_dhcpIpHost;
|
||
|
};
|
||
|
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
//
|
||
|
// CDhcpIpRange prototype
|
||
|
//
|
||
|
// Simple wrapper for a DHCP_IP_RANGE
|
||
|
//
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
class CDhcpIpRange
|
||
|
{
|
||
|
protected:
|
||
|
DHCP_IP_RANGE m_dhcpIpRange;
|
||
|
UINT m_RangeType;
|
||
|
|
||
|
public:
|
||
|
CDhcpIpRange (DHCP_IP_RANGE dhcpIpRange);
|
||
|
CDhcpIpRange ();
|
||
|
virtual ~CDhcpIpRange();
|
||
|
|
||
|
operator DHCP_IP_RANGE ()
|
||
|
{ return m_dhcpIpRange; }
|
||
|
|
||
|
operator DHCP_IP_RANGE () const
|
||
|
{ return m_dhcpIpRange; }
|
||
|
|
||
|
// Return TRUE if both addresses are generally OK
|
||
|
operator BOOL ()
|
||
|
{ return m_dhcpIpRange.StartAddress != DHCP_IP_ADDRESS_INVALID
|
||
|
&& m_dhcpIpRange.EndAddress != DHCP_IP_ADDRESS_INVALID
|
||
|
&& m_dhcpIpRange.StartAddress <= m_dhcpIpRange.EndAddress; }
|
||
|
|
||
|
CDhcpIpRange & operator = (const DHCP_IP_RANGE dhcpIpRange);
|
||
|
|
||
|
DHCP_IP_ADDRESS QueryAddr (BOOL bStart) const
|
||
|
{ return bStart ? m_dhcpIpRange.StartAddress : m_dhcpIpRange.EndAddress; }
|
||
|
|
||
|
DHCP_IP_ADDRESS SetAddr (DHCP_IP_ADDRESS dhcpIpAddress, BOOL bStart);
|
||
|
|
||
|
// Return TRUE if this range overlaps the given range.
|
||
|
BOOL IsOverlap (DHCP_IP_RANGE dhcpIpRange);
|
||
|
|
||
|
// Return TRUE if this range is a subset of the given range.
|
||
|
BOOL IsSubset (DHCP_IP_RANGE dhcpIpRange);
|
||
|
|
||
|
// Return TRUE if this range is a superset of the given range.
|
||
|
BOOL IsSuperset (DHCP_IP_RANGE dhcpIpRange);
|
||
|
|
||
|
// Sort helper function
|
||
|
//int OrderByAddress ( const CObjectPlus * pobIpRange ) const;
|
||
|
|
||
|
void SetRangeType(UINT uRangeType);
|
||
|
UINT GetRangeType();
|
||
|
};
|
||
|
|
||
|
typedef CList<CDhcpIpRange *, CDhcpIpRange *> CExclusionList;
|
||
|
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
//
|
||
|
// CDhcpOptionValue prototype
|
||
|
//
|
||
|
// Simple wrapper for DHCP_OPTION_DATA
|
||
|
//
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
class CDhcpOptionValue
|
||
|
{
|
||
|
public:
|
||
|
CDhcpOptionValue ( const DHCP_OPTION & dhcpOption );
|
||
|
CDhcpOptionValue ( const DHCP_OPTION_VALUE & dhcpOptionValue );
|
||
|
CDhcpOptionValue ( DHCP_OPTION_DATA_TYPE dhcDataType, INT cUpperBound = 0);
|
||
|
|
||
|
// Copy constructor.
|
||
|
CDhcpOptionValue ( const CDhcpOptionValue & cOptionValue );
|
||
|
CDhcpOptionValue ( const CDhcpOptionValue * dhcpOption );
|
||
|
|
||
|
// Assignment operator: assign a new value to this one.
|
||
|
CDhcpOptionValue & operator = ( const CDhcpOptionValue & dhcpValue );
|
||
|
|
||
|
CDhcpOptionValue () { };
|
||
|
~CDhcpOptionValue ();
|
||
|
|
||
|
//
|
||
|
// Query functions
|
||
|
//
|
||
|
DHCP_OPTION_DATA_TYPE QueryDataType () const
|
||
|
{
|
||
|
return m_dhcpOptionDataType;
|
||
|
}
|
||
|
|
||
|
int QueryUpperBound () const
|
||
|
{
|
||
|
return m_nUpperBound;
|
||
|
}
|
||
|
void SetUpperBound ( int nNewBound = 1 );
|
||
|
|
||
|
long QueryNumber ( INT index = 0 ) const;
|
||
|
DHCP_IP_ADDRESS QueryIpAddr ( INT index = 0 ) const;
|
||
|
LPCTSTR QueryString ( INT index = 0 ) const;
|
||
|
INT QueryBinary ( INT index = 0 ) const;
|
||
|
const CByteArray * QueryBinaryArray () const;
|
||
|
DWORD_DWORD QueryDwordDword ( INT index = 0 ) const;
|
||
|
|
||
|
//
|
||
|
// Return a string representation of the current value.
|
||
|
//
|
||
|
LONG QueryDisplayString ( CString & strResult, BOOL fLineFeed = FALSE ) const;
|
||
|
LONG QueryRouteArrayDisplayString( CString & strResult) const;
|
||
|
|
||
|
//
|
||
|
// Modifiers: SetString accepts any string representation;
|
||
|
// others are specific.
|
||
|
//
|
||
|
LONG SetData ( const DHCP_OPTION_DATA * podData );
|
||
|
LONG SetData ( const CDhcpOptionValue * pOptionValue );
|
||
|
BOOL SetDataType ( DHCP_OPTION_DATA_TYPE dhcpType, INT cUpperBound = 0 );
|
||
|
LONG SetString ( LPCTSTR pszNewValue, INT index = 0 );
|
||
|
LONG SetNumber ( INT nValue, INT nIndex = 0 );
|
||
|
LONG SetIpAddr ( DHCP_IP_ADDRESS dhcpIpAddress, INT index = 0 );
|
||
|
LONG SetDwordDword ( DWORD_DWORD dwdwValue, INT index = 0 );
|
||
|
|
||
|
LONG RemoveString ( INT index = 0);
|
||
|
LONG RemoveNumber ( INT index = 0);
|
||
|
LONG RemoveIpAddr ( INT index = 0);
|
||
|
LONG RemoveDwordDword ( INT index = 0);
|
||
|
|
||
|
BOOL IsValid () const;
|
||
|
|
||
|
LONG CreateOptionDataStruct(//const CDhcpOptionValue * pdhcpOptionValue,
|
||
|
LPDHCP_OPTION_DATA * ppOptionData,
|
||
|
BOOL bForceType = FALSE);
|
||
|
LONG FreeOptionDataStruct();
|
||
|
|
||
|
// implementation
|
||
|
private:
|
||
|
//
|
||
|
// Release the value union data
|
||
|
//
|
||
|
void FreeValue ();
|
||
|
|
||
|
//
|
||
|
// Initialize the value union data
|
||
|
//
|
||
|
LONG InitValue ( DHCP_OPTION_DATA_TYPE dhcDataType,
|
||
|
INT cUpperBound,
|
||
|
BOOL bProvideDefaultValue = TRUE );
|
||
|
|
||
|
BOOL CreateBinaryData ( const DHCP_BINARY_DATA * podBin, DHCP_BINARY_DATA * pobData ) ;
|
||
|
BOOL CreateBinaryData ( const CByteArray * paByte, DHCP_BINARY_DATA * pobData ) ;
|
||
|
|
||
|
// Attributes
|
||
|
private:
|
||
|
DHCP_OPTION_DATA_TYPE m_dhcpOptionDataType;
|
||
|
DHCP_OPTION_DATA * m_pdhcpOptionDataStruct;
|
||
|
INT m_nUpperBound ;
|
||
|
|
||
|
union
|
||
|
{
|
||
|
CObject * pCObj; // Generic pointer
|
||
|
CDWordArray * paDword; // 8-, 16-, 32-bit data.
|
||
|
CStringArray * paString; // String data
|
||
|
CByteArray * paBinary; // Binary and encapsulated data
|
||
|
CDWordDWordArray * paDwordDword;// 62-bit data.
|
||
|
} m_dhcpOptionValue;
|
||
|
};
|
||
|
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
//
|
||
|
// CDhcpOption prototype
|
||
|
//
|
||
|
// Simple wrapper for DHCP_OPTION
|
||
|
//
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
class CDhcpOption
|
||
|
{
|
||
|
public:
|
||
|
// Standard constructor uses API data
|
||
|
CDhcpOption ( const DHCP_OPTION & dhpOption );
|
||
|
|
||
|
// Constructor that must get info about option id referenced by the given value.
|
||
|
CDhcpOption ( const DHCP_OPTION_VALUE & dhcpOptionValue,
|
||
|
LPCTSTR pszVendor,
|
||
|
LPCTSTR pszClass );
|
||
|
|
||
|
// Constructor with overriding value.
|
||
|
CDhcpOption ( const CDhcpOption & dhpType,
|
||
|
const DHCP_OPTION_VALUE & dhcOptionValue );
|
||
|
|
||
|
// Constructor for dynamic instances
|
||
|
CDhcpOption ( DHCP_OPTION_ID nId,
|
||
|
DHCP_OPTION_DATA_TYPE dhcType,
|
||
|
LPCTSTR pszOptionName,
|
||
|
LPCTSTR pszComment,
|
||
|
DHCP_OPTION_TYPE dhcOptType = DhcpUnaryElementTypeOption );
|
||
|
|
||
|
// Copy constructor
|
||
|
CDhcpOption ( const CDhcpOption & dhpType );
|
||
|
|
||
|
~CDhcpOption ();
|
||
|
|
||
|
CDhcpOptionValue & QueryValue ()
|
||
|
{
|
||
|
return m_dhcpOptionValue ;
|
||
|
}
|
||
|
|
||
|
const CDhcpOptionValue & QueryValue () const
|
||
|
{
|
||
|
return m_dhcpOptionValue ;
|
||
|
}
|
||
|
|
||
|
DHCP_OPTION_DATA_TYPE QueryDataType () const
|
||
|
{
|
||
|
return m_dhcpOptionValue.QueryDataType() ;
|
||
|
}
|
||
|
|
||
|
DHCP_OPTION_ID QueryId () const
|
||
|
{
|
||
|
return m_dhcpOptionId ;
|
||
|
}
|
||
|
|
||
|
LPCTSTR QueryName () const
|
||
|
{
|
||
|
return m_strName ;
|
||
|
}
|
||
|
|
||
|
LPCTSTR QueryComment () const
|
||
|
{
|
||
|
return m_strComment ;
|
||
|
}
|
||
|
|
||
|
void SetOptType ( DHCP_OPTION_TYPE dhcOptType ) ;
|
||
|
|
||
|
DHCP_OPTION_TYPE QueryOptType() const
|
||
|
{
|
||
|
return m_dhcpOptionType ;
|
||
|
}
|
||
|
|
||
|
// Return TRUE if the option type is an array.
|
||
|
BOOL IsArray () const
|
||
|
{
|
||
|
return QueryOptType() == DhcpArrayTypeOption ;
|
||
|
}
|
||
|
|
||
|
// Fill the given string with a displayable representation of the item.
|
||
|
void QueryDisplayName ( CString & cStr ) const ;
|
||
|
|
||
|
BOOL SetName ( LPCTSTR pszName ) ;
|
||
|
BOOL SetComment ( LPCTSTR pszComment ) ;
|
||
|
|
||
|
LONG Update ( const CDhcpOptionValue & dhcpOptionValue ) ;
|
||
|
static INT MaxSizeOfType ( DHCP_OPTION_DATA_TYPE dhcType ) ;
|
||
|
|
||
|
BOOL SetDirty(BOOL bDirty = TRUE)
|
||
|
{
|
||
|
BOOL bOldFlag = m_bDirty;
|
||
|
m_bDirty = bDirty;
|
||
|
return bOldFlag;
|
||
|
}
|
||
|
|
||
|
// vendor specifc option stuff
|
||
|
void SetVendor(LPCTSTR pszVendor) { m_strVendor = pszVendor; }
|
||
|
BOOL IsVendor() { return !m_strVendor.IsEmpty(); }
|
||
|
LPCTSTR GetVendor() { return m_strVendor.IsEmpty() ? NULL : (LPCTSTR) m_strVendor; }
|
||
|
|
||
|
BOOL IsDirty() { return m_bDirty; }
|
||
|
|
||
|
// class ID methods
|
||
|
LPCTSTR GetClassName() { return m_strClassName; }
|
||
|
void SetClassName(LPCTSTR pClassName) { m_strClassName = pClassName; }
|
||
|
BOOL IsClassOption() { return m_strClassName.IsEmpty() ? FALSE : TRUE; }
|
||
|
|
||
|
DWORD SetApiErr(DWORD dwErr)
|
||
|
{
|
||
|
DWORD dwOldErr = m_dwErr;
|
||
|
m_dwErr = dwErr;
|
||
|
return dwOldErr;
|
||
|
}
|
||
|
|
||
|
DWORD QueryApiErr() { return m_dwErr; }
|
||
|
|
||
|
protected:
|
||
|
DHCP_OPTION_ID m_dhcpOptionId; // Option identifier
|
||
|
DHCP_OPTION_TYPE m_dhcpOptionType; // Option type
|
||
|
CDhcpOptionValue m_dhcpOptionValue; // Default value info
|
||
|
CString m_strName; // Name of option
|
||
|
CString m_strComment; // Comment for option
|
||
|
CString m_strVendor; // Vendor Name for this option
|
||
|
BOOL m_bDirty;
|
||
|
DWORD m_dwErr; // stored err for later display
|
||
|
CString m_strClassName;
|
||
|
};
|
||
|
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
//
|
||
|
// COptionList
|
||
|
//
|
||
|
// Object contains a list of options. Can be iterated.
|
||
|
//
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
typedef CList<CDhcpOption*, CDhcpOption*> COptionListBase;
|
||
|
|
||
|
class COptionList : public COptionListBase
|
||
|
{
|
||
|
public:
|
||
|
COptionList()
|
||
|
: m_pos(NULL), m_bDirty(FALSE) {}
|
||
|
~COptionList()
|
||
|
{
|
||
|
DeleteAll();
|
||
|
}
|
||
|
|
||
|
public:
|
||
|
void DeleteAll()
|
||
|
{
|
||
|
while (!IsEmpty())
|
||
|
{
|
||
|
delete RemoveHead();
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// removes an option from the list
|
||
|
void Remove(CDhcpOption * pOption)
|
||
|
{
|
||
|
POSITION pos = Find(pOption);
|
||
|
if (pos)
|
||
|
RemoveAt(pos);
|
||
|
}
|
||
|
|
||
|
void Reset() { m_pos = GetHeadPosition(); }
|
||
|
|
||
|
CDhcpOption * Next()
|
||
|
{
|
||
|
if (m_pos)
|
||
|
return GetNext(m_pos);
|
||
|
else
|
||
|
return NULL;
|
||
|
}
|
||
|
|
||
|
CDhcpOption * FindId(DWORD dwId, LPCTSTR pszVendor)
|
||
|
{
|
||
|
CDhcpOption * pOpt = NULL;
|
||
|
CString strVendor = pszVendor;
|
||
|
|
||
|
POSITION pos = GetHeadPosition();
|
||
|
while (pos)
|
||
|
{
|
||
|
CDhcpOption * pCurOpt = GetNext(pos);
|
||
|
if ( (pCurOpt->QueryId() == dwId) &&
|
||
|
( (!pszVendor && !pCurOpt->GetVendor()) ||
|
||
|
(pCurOpt->GetVendor() && (strVendor.CompareNoCase(pCurOpt->GetVendor()) == 0) ) ) )
|
||
|
{
|
||
|
pOpt = pCurOpt;
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
return pOpt;
|
||
|
}
|
||
|
|
||
|
BOOL SetAll(BOOL bDirty)
|
||
|
{
|
||
|
BOOL bWasDirty = FALSE;
|
||
|
POSITION pos = GetHeadPosition();
|
||
|
while (pos)
|
||
|
{
|
||
|
CDhcpOption * pCurOpt = GetNext(pos);
|
||
|
if (pCurOpt->SetDirty(bDirty))
|
||
|
bWasDirty = TRUE;
|
||
|
}
|
||
|
return bWasDirty;
|
||
|
}
|
||
|
|
||
|
BOOL SetDirty(BOOL bDirty = TRUE)
|
||
|
{
|
||
|
BOOL bOldFlag = m_bDirty;
|
||
|
m_bDirty = bDirty;
|
||
|
return bOldFlag;
|
||
|
}
|
||
|
|
||
|
static int __cdecl SortByIdHelper(const void * pa, const void * pb)
|
||
|
{
|
||
|
CDhcpOption ** ppOpt1 = (CDhcpOption **) pa;
|
||
|
CDhcpOption ** ppOpt2 = (CDhcpOption **) pb;
|
||
|
|
||
|
if ((*ppOpt1)->QueryId() < (*ppOpt2)->QueryId())
|
||
|
return -1;
|
||
|
else
|
||
|
if ((*ppOpt1)->QueryId() > (*ppOpt2)->QueryId())
|
||
|
return 1;
|
||
|
else
|
||
|
{
|
||
|
// options have equal IDs, but standard options come first
|
||
|
if ((*ppOpt1)->IsVendor() && !(*ppOpt2)->IsVendor())
|
||
|
return 1;
|
||
|
else
|
||
|
if (!(*ppOpt1)->IsVendor() && (*ppOpt2)->IsVendor())
|
||
|
return -1;
|
||
|
else
|
||
|
return 0; // they are either both standard or both vendor -- equal
|
||
|
}
|
||
|
}
|
||
|
|
||
|
LONG SortById()
|
||
|
{
|
||
|
LONG err = 0;
|
||
|
CDhcpOption * pOpt;
|
||
|
int cItems = (int) GetCount();
|
||
|
|
||
|
if ( cItems < 2 )
|
||
|
return NO_ERROR;
|
||
|
|
||
|
CATCH_MEM_EXCEPTION
|
||
|
{
|
||
|
// Allocate the array
|
||
|
CDhcpOption ** paOpt = (CDhcpOption **) alloca(sizeof(CDhcpOption *) * cItems);
|
||
|
|
||
|
/// Fill the helper array.
|
||
|
POSITION pos = GetHeadPosition();
|
||
|
for (UINT i = 0; pos != NULL; i++ )
|
||
|
{
|
||
|
pOpt = GetNext(pos);
|
||
|
paOpt[i] = pOpt;
|
||
|
}
|
||
|
|
||
|
RemoveAll();
|
||
|
|
||
|
ASSERT( GetCount() == 0 );
|
||
|
|
||
|
// Sort the helper array
|
||
|
::qsort( paOpt,
|
||
|
cItems,
|
||
|
sizeof(paOpt[0]),
|
||
|
SortByIdHelper ) ;
|
||
|
|
||
|
// Refill the list from the helper array.
|
||
|
for ( i = 0 ; i < (UINT) cItems ; i++ )
|
||
|
{
|
||
|
AddTail( paOpt[i] );
|
||
|
}
|
||
|
|
||
|
ASSERT( GetCount() == cItems ) ;
|
||
|
}
|
||
|
END_MEM_EXCEPTION(err)
|
||
|
|
||
|
return err ;
|
||
|
}
|
||
|
|
||
|
private:
|
||
|
POSITION m_pos;
|
||
|
BOOL m_bDirty;
|
||
|
};
|
||
|
|
||
|
/*---------------------------------------------------------------------------
|
||
|
Class: COptionValueEnum
|
||
|
---------------------------------------------------------------------------*/
|
||
|
class COptionValueEnum : public COptionList
|
||
|
{
|
||
|
public:
|
||
|
COptionValueEnum();
|
||
|
|
||
|
DWORD Init(LPCTSTR pServer, LARGE_INTEGER & liVersion, DHCP_OPTION_SCOPE_INFO & dhcpOptionScopeInfo);
|
||
|
DWORD Enum();
|
||
|
void Copy(COptionValueEnum * pEnum);
|
||
|
void Remove(DHCP_OPTION_ID optionId, LPCTSTR pszVendor, LPCTSTR pszClass);
|
||
|
|
||
|
protected:
|
||
|
DWORD EnumOptions();
|
||
|
DWORD EnumOptionsV5();
|
||
|
|
||
|
// V5 Helper
|
||
|
HRESULT CreateOptions(LPDHCP_OPTION_VALUE_ARRAY pOptionValues, LPCTSTR pClassName, LPCTSTR pszVendor);
|
||
|
|
||
|
public:
|
||
|
DHCP_OPTION_SCOPE_INFO m_dhcpOptionScopeInfo;
|
||
|
LARGE_INTEGER m_liVersion;
|
||
|
CString m_strServer;
|
||
|
CString m_strDynBootpClassName;
|
||
|
};
|
||
|
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
//
|
||
|
// CDhcpDefaultOptionsOnServer prototype
|
||
|
//
|
||
|
// Object contains a list of default options on a DHCP server
|
||
|
//
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
class CDhcpDefaultOptionsOnServer
|
||
|
{
|
||
|
// constructors
|
||
|
public:
|
||
|
CDhcpDefaultOptionsOnServer();
|
||
|
~CDhcpDefaultOptionsOnServer();
|
||
|
|
||
|
// exposed functions
|
||
|
public:
|
||
|
LONG Enumerate(LPCWSTR pServer, LARGE_INTEGER liVersion);
|
||
|
CDhcpOption * Find(DHCP_OPTION_ID dhcpOptionId, LPCTSTR pszVendor);
|
||
|
BOOL IsEmpty() { return m_listOptions.IsEmpty(); }
|
||
|
int GetCount() { return (int) m_listOptions.GetCount(); }
|
||
|
|
||
|
CDhcpOption * First();
|
||
|
CDhcpOption * Next();
|
||
|
void Reset();
|
||
|
|
||
|
LONG SortById();
|
||
|
|
||
|
COptionList & GetOptionList() { return m_listOptions; }
|
||
|
|
||
|
// implementation
|
||
|
private:
|
||
|
LONG RemoveAll();
|
||
|
LONG EnumerateV4(LPCWSTR pServer);
|
||
|
LONG EnumerateV5(LPCWSTR pServer);
|
||
|
|
||
|
// attributes
|
||
|
private:
|
||
|
COptionList m_listOptions;
|
||
|
|
||
|
DWORD m_dwLastUpdate;
|
||
|
DWORD m_dwOptionsTotal;
|
||
|
POSITION m_pos;
|
||
|
};
|
||
|
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
//
|
||
|
// CDhcpDefaultOptionsMasterList prototype
|
||
|
//
|
||
|
// Object contains master list of known options
|
||
|
//
|
||
|
/////////////////////////////////////////////////////////////////////
|
||
|
enum OPT_FIELD
|
||
|
{
|
||
|
OPTF_OPTION,
|
||
|
OPTF_NAME,
|
||
|
OPTF_TYPE,
|
||
|
OPTF_ARRAY_FLAG,
|
||
|
OPTF_LENGTH,
|
||
|
OPTF_DESCRIPTION,
|
||
|
OPTF_REMARK,
|
||
|
OPTF_MAX
|
||
|
};
|
||
|
|
||
|
typedef struct
|
||
|
{
|
||
|
int eOptType ;
|
||
|
LPCTSTR pszOptTypeName ;
|
||
|
} OPT_TOKEN ;
|
||
|
|
||
|
class CDhcpDefaultOptionsMasterList
|
||
|
{
|
||
|
// constructors
|
||
|
public:
|
||
|
CDhcpDefaultOptionsMasterList();
|
||
|
~CDhcpDefaultOptionsMasterList();
|
||
|
|
||
|
// exposed functions
|
||
|
public:
|
||
|
LONG BuildList();
|
||
|
|
||
|
CDhcpOption * First();
|
||
|
CDhcpOption * Next();
|
||
|
void Reset();
|
||
|
|
||
|
int GetCount();
|
||
|
|
||
|
// implementation
|
||
|
private:
|
||
|
BOOL scanNextParamType(LPCTSTR * ppszText, CDhcpOption * * ppParamType);
|
||
|
LPCTSTR scanNextField(LPCTSTR pszLine, LPTSTR pszOut, int cFieldSize);
|
||
|
BOOL allDigits(LPCTSTR psz);
|
||
|
int recognizeToken(OPT_TOKEN * apToken, LPCTSTR pszToken);
|
||
|
LPCTSTR skipToNextLine(LPCTSTR pszLine);
|
||
|
BOOL skipWs(LPCTSTR * ppszLine);
|
||
|
|
||
|
|
||
|
// attributes
|
||
|
private:
|
||
|
COptionList m_listOptions;
|
||
|
POSITION m_pos;
|
||
|
};
|
||
|
|
||
|
#endif _GENERAL_H
|