# encoding: ascii
# api: powershell
# title: Get-DhcpClient
# description: More C# than PowerShell. A script to return DHCP client leases from a DHCP server.
# version: 0.1
# type: script
# license: CC0
# x-poshcode-id: 2310
# x-archived: 2010-10-21T23:39:15
#
#
<#
.Description
A C# P/Invoke wrapper for DhcpEnumSubnetClients from the DHCP API
.Parameter Server
A DHCP server to query
.Parameter Scope
The IP address representing the scope to query
#>
[CmdLetBinding()]
Param(
[Parameter(Mandatory = $True)]
[Net.IPAddress]$Server,
[Parameter(Mandatory = $True)]
[Net.IPAddress]$Scope
)
#
# Add the namespace
#
Try { [Void][Dhcp.DhcpClient] } Catch { }
If (!$?) {
Add-Type @"
using System;
using System.Collections;
using System.Net;
using System.Runtime.InteropServices;
using Dhcp;
namespace Dhcp
{
public class ConvertTo {
public static IPAddress IP(UInt32 Value)
{
Byte[] IPArray = new Byte[4];
for (int i = 3; i > -1; i--) {
Double Remainder = Value % Math.Pow(256, i);
IPArray[3 - i] = (Byte)((Value - Remainder) / Math.Pow(256, i));
Value = (UInt32)Remainder;
}
return IPAddress.Parse(String.Format("{0}.{1}.{2}.{3}",
IPArray[0],
IPArray[1],
IPArray[2],
IPArray[3]));
}
public static UInt32 UInt32(IPAddress IP)
{
UInt32 Value = 0;
Byte[] Bytes = IP.GetAddressBytes();
for (int i = 0; i < 4; i++) {
Value = Value | (UInt32)(Bytes[i] << (8 * (3 - i)));
}
return Value;
}
}
public class Functions {
[DllImport("dhcpsapi.dll")]
public static extern UInt32 DhcpEnumSubnetClients(
[MarshalAs(UnmanagedType.LPWStr)]
String ServerIpAddress,
uint SubnetAddress,
ref uint ResumeHandle,
uint PreferredMaximum,
out IntPtr ClientInfo,
out uint ClientsRead,
out uint ClientsTotal
);
}
public class Structures {
[StructLayout(LayoutKind.Sequential)]
public struct DATE_TIME
{
public UInt32 dwLowDateTime;
public UInt32 dwHighDateTime;
public DateTime ToDateTime()
{
if (dwHighDateTime == 0 && dwLowDateTime == 0)
{
return DateTime.MinValue;
}
if (dwHighDateTime == int.MaxValue && dwLowDateTime == UInt32.MaxValue)
{
return DateTime.MaxValue;
}
return DateTime.FromFileTime((((long)dwHighDateTime) << 32) | dwLowDateTime);
}
}
[StructLayout(LayoutKind.Sequential)]
public struct DHCP_BINARY_DATA
{
public uint DataLength;
public IntPtr Data;
public override String ToString()
{
return String.Format("{0:X2}:{1:X2}:{2:X2}:{3:X2}:{4:X2}:{5:X2}",
Marshal.ReadByte(this.Data),
Marshal.ReadByte(this.Data, 1),
Marshal.ReadByte(this.Data, 2),
Marshal.ReadByte(this.Data, 3),
Marshal.ReadByte(this.Data, 4),
Marshal.ReadByte(this.Data, 5));
}
};
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]
public struct DHCP_CLIENT_INFO_ARRAY
{
public uint NumElements;
public IntPtr Clients;
}
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]
public struct DHCP_CLIENT_INFO
{
public uint ClientIpAddress;
public uint SubnetMask;
public DHCP_BINARY_DATA ClientHardwareAddress;
[MarshalAs(UnmanagedType.LPWStr)]
public string ClientName;
[MarshalAs(UnmanagedType.LPWStr)]
public string ClientComment;
public DATE_TIME ClientLeaseExpires;
public DHCP_HOST_INFO OwnerHost;
}
[StructLayout(LayoutKind.Sequential)]
public struct DHCP_HOST_INFO
{
uint IpAddress;
[MarshalAs(UnmanagedType.LPWStr)]
String NetBiosName;
[MarshalAs(UnmanagedType.LPWStr)]
String HostName;
}
}
public class DhcpClient
{
public String Name;
public String MACAddress;
public IPAddress IpAddress;
public IPAddress SubnetMask;
public String Description;
public DateTime LeaseExpires;
internal DhcpClient(Structures.DHCP_CLIENT_INFO RawReservation)
{
this.IpAddress = ConvertTo.IP(RawReservation.ClientIpAddress);
this.SubnetMask = ConvertTo.IP(RawReservation.SubnetMask);
this.MACAddress = RawReservation.ClientHardwareAddress.ToString();
this.Name = RawReservation.ClientName;
this.Description = RawReservation.ClientComment;
this.LeaseExpires = RawReservation.ClientLeaseExpires.ToDateTime();
}
public static DhcpClient[] Get(IPAddress ServerIP, IPAddress ScopeIP) {
ArrayList Clients = new ArrayList();
uint resumeHandle = 0;
IntPtr info_array_ptr;
uint numClientsRead = 0;
uint totalClients = 0;
String Server = ServerIP.ToString();
UInt32 Scope = ConvertTo.UInt32(ScopeIP);
UInt32 ReturnCode = Functions.DhcpEnumSubnetClients(
Server,
Scope,
ref resumeHandle,
65536,
out info_array_ptr,
out numClientsRead,
out totalClients
);
Structures.DHCP_CLIENT_INFO_ARRAY rawClients =
(Structures.DHCP_CLIENT_INFO_ARRAY)Marshal.PtrToStructure(info_array_ptr, typeof(Structures.DHCP_CLIENT_INFO_ARRAY));
IntPtr current = rawClients.Clients;
for (int i = 0; i < (int)rawClients.NumElements; i++) {
Structures.DHCP_CLIENT_INFO rawMachine =
(Structures.DHCP_CLIENT_INFO)Marshal.PtrToStructure(Marshal.ReadIntPtr(current), typeof(Structures.DHCP_CLIENT_INFO));
Clients.Add(new DhcpClient(rawMachine));
current = (IntPtr)((int)current + (int)Marshal.SizeOf(typeof(IntPtr)));
}
return (DhcpClient[])Clients.ToArray(typeof(DhcpClient));
}
}
}
"@
}
#
# Execute Get()
#
[Dhcp.DhcpClient]::Get($Server, $Scope)