This is change 1 of 2.

AddIPAddress and DeleteIPAddress are now implemented all the way down.
Next we need the dhcp service live enough to assign the address from userland,
then we can remove the IP address setting from the kernel.

svn path=/trunk/; revision=14298
This commit is contained in:
Art Yerkes 2005-03-24 10:46:52 +00:00
parent 632a47580b
commit 0ecfffa8a0
11 changed files with 188 additions and 9 deletions

View file

@ -244,13 +244,29 @@ BOOLEAN IPRegisterInterface(
*/
{
KIRQL OldIrql;
UINT ChosenIndex = 1;
BOOLEAN IndexHasBeenChosen;
IP_ADDRESS NetworkAddress;
PNEIGHBOR_CACHE_ENTRY NCE;
IF_LIST_ITER(Interface);
TI_DbgPrint(MID_TRACE, ("Called. IF (0x%X).\n", IF));
TcpipAcquireSpinLock(&IF->Lock, &OldIrql);
/* Choose an index */
do {
IndexHasBeenChosen = TRUE;
ForEachInterface(Interface) {
if( Interface->Index == ChosenIndex ) {
ChosenIndex++;
IndexHasBeenChosen = FALSE;
}
} EndFor(Interface);
} while( !IndexHasBeenChosen );
IF->Index = ChosenIndex;
/* Add a permanent neighbor for this NTE */
NCE = NBAddNeighbor(IF, &IF->Unicast,
IF->Address, IF->AddressLength,

View file

@ -56,6 +56,14 @@ NTSTATUS DispTdiSetInformationEx(
PIRP Irp,
PIO_STACK_LOCATION IrpSp);
NTSTATUS DispTdiSetIPAddress(
PIRP Irp,
PIO_STACK_LOCATION IrpSp);
NTSTATUS DispTdiDeleteIPAddress(
PIRP Irp,
PIO_STACK_LOCATION IrpSp);
#endif /* __DISPATCH_H */
/* EOF */

View file

@ -153,10 +153,16 @@ typedef struct _IP_INTERFACE {
UNICODE_STRING Name; /* Adapter name */
PUCHAR Address; /* Pointer to interface address */
UINT AddressLength; /* Length of address in bytes */
UINT Index; /* Index of adapter (used to add ip addr) */
LL_TRANSMIT_ROUTINE Transmit; /* Pointer to transmit function */
PVOID TCPContext; /* TCP Content for this interface */
} IP_INTERFACE, *PIP_INTERFACE;
typedef struct _IP_SET_ADDRESS {
ULONG NteIndex;
IPv4_RAW_ADDRESS Address;
IPv4_RAW_ADDRESS Netmask;
} IP_SET_ADDRESS, *PIP_SET_ADDRESS;
#define IP_PROTOCOL_TABLE_SIZE 0x100

View file

@ -45,6 +45,12 @@
#define IOCTL_TCP_SET_INFORMATION_EX \
_TCP_CTL_CODE(1, METHOD_BUFFERED, FILE_WRITE_ACCESS)
#define IOCTL_SET_IP_ADDRESS \
_TCP_CTL_CODE(14, METHOD_BUFFERED, FILE_WRITE_ACCESS)
#define IOCTL_DELETE_IP_ADDRESS \
_TCP_CTL_CODE(16, METHOD_BUFFERED, FILE_WRITE_ACCESS)
/* Unique error values for log entries */
#define TI_ERROR_DRIVERENTRY 0

View file

@ -1465,4 +1465,56 @@ NTSTATUS DispTdiSetInformationEx(
return Status;
}
/* TODO: Support multiple addresses per interface.
* For now just set the nte context to the interface index.
*
* Later on, create an NTE context and NTE instance
*/
NTSTATUS DispTdiSetIPAddress( PIRP Irp, PIO_STACK_LOCATION IrpSp ) {
NTSTATUS Status = STATUS_DEVICE_DOES_NOT_EXIST;
PIP_SET_ADDRESS IpAddrChange =
(PIP_SET_ADDRESS)Irp->AssociatedIrp.SystemBuffer;
IF_LIST_ITER(IF);
ForEachInterface(IF) {
if( IF->Unicast.Address.IPv4Address == IpAddrChange->Address ) {
Status = STATUS_DUPLICATE_OBJECTID;
break;
}
if( IF->Index == IpAddrChange->NteIndex ) {
IF->Unicast.Type = IP_ADDRESS_V4;
IF->Unicast.Address.IPv4Address = IpAddrChange->Address;
IF->Netmask.Type = IP_ADDRESS_V4;
IF->Netmask.Address.IPv4Address = IpAddrChange->Netmask;
IpAddrChange->Address = IF->Index;
Status = STATUS_SUCCESS;
Irp->IoStatus.Information = IF->Index;
break;
}
} EndFor(IF);
Irp->IoStatus.Status = Status;
return Status;
}
NTSTATUS DispTdiDeleteIPAddress( PIRP Irp, PIO_STACK_LOCATION IrpSp ) {
NTSTATUS Status = STATUS_UNSUCCESSFUL;
PUSHORT NteIndex = Irp->AssociatedIrp.SystemBuffer;
IF_LIST_ITER(IF);
ForEachInterface(IF) {
if( IF->Index == *NteIndex ) {
IF->Unicast.Type = IP_ADDRESS_V4;
IF->Unicast.Address.IPv4Address = 0;
IF->Netmask.Type = IP_ADDRESS_V4;
IF->Netmask.Address.IPv4Address = 0;
Status = STATUS_SUCCESS;
}
} EndFor(IF);
Irp->IoStatus.Status = Status;
return Status;
}
/* EOF */

View file

@ -33,7 +33,7 @@ TDI_STATUS InfoTdiQueryGetInterfaceMIB(TDIEntityID *ID,
RtlZeroMemory( OutData, sizeof(IFENTRY) + MAX_IFDESCR_LEN );
OutData->Index = ID->tei_instance + 1;
OutData->Index = Interface->Index;
/* viz: tcpip keeps those indices */
OutData->Type = Interface ==
Loopback ? MIB_IF_TYPE_LOOPBACK : MIB_IF_TYPE_ETHERNET;
@ -104,5 +104,7 @@ TDI_STATUS InfoInterfaceTdiSetEx( UINT InfoClass,
TDIEntityID *id,
PCHAR Buffer,
UINT BufferSize ) {
TI_DbgPrint("Got Request: Class %x Type %x Id %x, EntityID %x:%x\n",
InfoClass, InfoId, id->tei_entity, id->tei_instance);
return TDI_INVALID_REQUEST;
}

View file

@ -9,7 +9,7 @@
*/
#include "precomp.h"
#define NDEBUG
//#define NDEBUG
#ifndef NDEBUG
DWORD DebugTraceLevel = DEBUG_ULTRA & ~(DEBUG_LOCK | DEBUG_PBUFFER);
@ -578,6 +578,16 @@ TiDispatch(
Status = DispTdiSetInformationEx(Irp, IrpSp);
break;
case IOCTL_SET_IP_ADDRESS:
TI_DbgPrint(MIN_TRACE, ("SET_IP_ADDRESS\n"));
Status = DispTdiSetIPAddress(Irp, IrpSp);
break;
case IOCTL_DELETE_IP_ADDRESS:
TI_DbgPrint(MIN_TRACE, ("DELETE_IP_ADDRESS\n"));
Status = DispTdiDeleteIPAddress(Irp, IrpSp);
break;
default:
TI_DbgPrint(MIN_TRACE, ("Unknown IOCTL 0x%X\n",
IrpSp->Parameters.DeviceIoControl.IoControlCode));

View file

@ -37,4 +37,10 @@
#define IOCTL_TCP_SET_INFORMATION_EX \
_TCP_CTL_CODE(1, METHOD_BUFFERED, FILE_WRITE_ACCESS)
#define IOCTL_SET_IP_ADDRESS \
_TCP_CTL_CODE(14, METHOD_BUFFERED, FILE_WRITE_ACCESS)
#define IOCTL_DELETE_IP_ADDRESS \
_TCP_CTL_CODE(16, METHOD_BUFFERED, FILE_WRITE_ACCESS)
#endif/*_TCPIOCTL_H*/

View file

@ -754,6 +754,8 @@ DWORD getInterfaceEntryByName(const char *name, PMIB_IFROW entry)
sizeof(info.if_info) );
}
DPRINT1("entry->bDescr = %s\n", entry->bDescr);
closeTcpFile( tcpFile );
}
@ -795,3 +797,72 @@ char *toIPAddressString(unsigned int addr, char string[16])
}
return string;
}
NTSTATUS addIPAddress( IPAddr Address, IPMask Mask, DWORD IfIndex,
PULONG NteContext, PULONG NteInstance )
{
HANDLE tcpFile;
NTSTATUS status = openTcpFile( &tcpFile );
IP_SET_DATA Data;
IO_STATUS_BLOCK Iosb;
DPRINT("Called.\n");
if( !NT_SUCCESS(status) ) return status;
Data.NteContext = IfIndex;
Data.NewAddress = Address;
Data.NewNetmask = Mask;
status = NtDeviceIoControlFile( tcpFile,
NULL,
NULL,
NULL,
&Iosb,
IOCTL_SET_IP_ADDRESS,
&Data,
sizeof(Data),
&Data,
sizeof(Data) );
closeTcpFile( tcpFile );
if( NT_SUCCESS(status) ) {
*NteContext = Iosb.Information;
*NteInstance = Data.NewAddress;
}
switch( status ) {
case STATUS_SUCCESS: return ERROR_SUCCESS;
case STATUS_DEVICE_DOES_NOT_EXIST: return ERROR_DEV_NOT_EXIST;
default: return status;
}
}
NTSTATUS deleteIpAddress( ULONG NteContext )
{
HANDLE tcpFile;
NTSTATUS status = openTcpFile( &tcpFile );
USHORT TheNteContext = NteContext;
IO_STATUS_BLOCK Iosb;
DPRINT("Called.\n");
if( !NT_SUCCESS(status) ) return status;
status = NtDeviceIoControlFile( tcpFile,
NULL,
NULL,
NULL,
&Iosb,
IOCTL_DELETE_IP_ADDRESS,
&NteContext,
sizeof(USHORT),
NULL,
0 );
closeTcpFile( tcpFile );
if( NT_SUCCESS(status) ) return ERROR_SUCCESS;
else return ERROR_GEN_FAILURE;
}

View file

@ -82,11 +82,9 @@ BOOL WINAPI DllMain (HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
* DWORD
*
*/
DWORD WINAPI AddIPAddress(IPAddr Address, IPMask IpMask, DWORD IfIndex, PULONG NTEContext, PULONG NTEInstance)
DWORD WINAPI AddIPAddress(IPAddr Address, IPMask Netmask, DWORD IfIndex, PULONG NteContext, PULONG NteInstance)
{
FIXME(":stub\n");
/* marking Win2K+ functions not supported */
return ERROR_NOT_SUPPORTED;
return addIPAddress( Address, Netmask, IfIndex, NteContext, NteInstance );
}
@ -404,9 +402,7 @@ DWORD WINAPI CreateProxyArpEntry(DWORD dwAddress, DWORD dwMask, DWORD dwIfIndex)
DWORD WINAPI DeleteIPAddress(ULONG NTEContext)
{
TRACE("NTEContext %ld\n", NTEContext);
FIXME(":stub\n");
/* marking Win2K+ functions not supported */
return ERROR_NOT_SUPPORTED;
return deleteIpAddress( NTEContext );
}

View file

@ -82,6 +82,12 @@ typedef struct _IFInfo {
IPAddrEntry ip_addr;
} IFInfo;
typedef struct _IP_SET_DATA {
ULONG NteContext;
ULONG NewAddress;
ULONG NewNetmask;
} IP_SET_DATA, *PIP_SET_DATA;
typedef enum _IPHLPAddrType {
IPAAddr, IPABcast, IPAMask, IFMtu, IFStatus
} IPHLPAddrType;