[0.4.7][AFD] Port back 2 fixes CORE-18328 (#4972) and CORE-13067 (#440)

fix CORE-18328 'FileZilla 3.8 unable to list content of a remote directory due to undue ECONNRESET'
I tested to list the contents of ftp.heise.de and downloaded some files from its pub.

by porting back:
0.4.15-dev-5870-g 9f9b81e396 [AFD] ReceiveActivity: Don't return STATUS_FILE_CLOSED in case of FCB overread CORE-18328 (#4972)
-------------
fix CORE-13067 'wget can not download'
I tested to wget.exe http://download.microsoft.com/download/vc60pro/update/2/w9xnt4/en-us/vc6redistsetup_deu.exe

by porting back:
0.4.9-dev-349-g 9168226378 [AFD] Respond to FileFsDeviceInformation. CORE-13067 (#440)
0.4.9-dev-350-g 8b84b1c6b3 [AFD] Mark the socket as named pipe, so NtWriteFile actually knows what to do with it. CORE-13067 (#440)
-------------
also port back unrelated:
0.4.8-dev-233-g 44e36b616a [AFD] Zap unused TaCopyAddress() and TaCopyAddressInPlace().
partially 0.4.8-dev-589-g a2f7de7ee8 [AFD] just pick the main.c one-liner with the %p format-string
and a few whitespace improvements from 0.4.8-dev'ing
This commit is contained in:
Joachim Henze 2023-06-14 23:52:06 +02:00
parent e4f0ba5cae
commit 03fe564d33
13 changed files with 119 additions and 104 deletions

View file

@ -305,8 +305,8 @@ PAFD_HANDLE LockHandles( PAFD_HANDLE HandleArray, UINT HandleCount ) {
UINT i; UINT i;
NTSTATUS Status = STATUS_SUCCESS; NTSTATUS Status = STATUS_SUCCESS;
PAFD_HANDLE FileObjects = ExAllocatePool PAFD_HANDLE FileObjects = ExAllocatePool(NonPagedPool,
( NonPagedPool, HandleCount * sizeof(AFD_HANDLE) ); HandleCount * sizeof(AFD_HANDLE));
for( i = 0; FileObjects && i < HandleCount; i++ ) { for( i = 0; FileObjects && i < HandleCount; i++ ) {
FileObjects[i].Status = 0; FileObjects[i].Status = 0;

View file

@ -27,7 +27,7 @@ void OskitDumpBuffer( PCHAR Data, UINT Len ) {
for( i = 0; i < Len; i++ ) { for( i = 0; i < Len; i++ ) {
if( i && !(i & 0xf) ) DbgPrint( "\n" ); if( i && !(i & 0xf) ) DbgPrint( "\n" );
if( !(i & 0xf) ) DbgPrint( "%08x: ", (UINT)(Data + i) ); if( !(i & 0xf) ) DbgPrint( "%p: ", (Data + i) );
DbgPrint( " %02x", Data[i] & 0xff ); DbgPrint( " %02x", Data[i] & 0xff );
} }
DbgPrint("\n"); DbgPrint("\n");
@ -301,6 +301,7 @@ AfdCreateSocket(PDEVICE_OBJECT DeviceObject, PIRP Irp,
DeviceExt = DeviceObject->DeviceExtension; DeviceExt = DeviceObject->DeviceExtension;
FileObject = IrpSp->FileObject; FileObject = IrpSp->FileObject;
FileObject->Flags |= FO_NAMED_PIPE;
//Disposition = (IrpSp->Parameters.Create.Options >> 24) & 0xff; //Disposition = (IrpSp->Parameters.Create.Options >> 24) & 0xff;
Irp->IoStatus.Information = 0; Irp->IoStatus.Information = 0;
@ -726,9 +727,6 @@ AfdDisconnect(PDEVICE_OBJECT DeviceObject, PIRP Irp,
FCB->Recv.Content = 0; FCB->Recv.Content = 0;
FCB->Recv.BytesUsed = 0; FCB->Recv.BytesUsed = 0;
/* Mark us as overread to complete future reads with an error */
FCB->Overread = TRUE;
/* Set a successful receive status to indicate a shutdown on overread */ /* Set a successful receive status to indicate a shutdown on overread */
FCB->LastReceiveStatus = STATUS_SUCCESS; FCB->LastReceiveStatus = STATUS_SUCCESS;
@ -829,6 +827,50 @@ AfdDisconnect(PDEVICE_OBJECT DeviceObject, PIRP Irp,
return UnlockAndMaybeComplete( FCB, Status, Irp, 0 ); return UnlockAndMaybeComplete( FCB, Status, Irp, 0 );
} }
NTSTATUS
AfdQueryFsDeviceInfo(PDEVICE_OBJECT DeviceObject, PFILE_FS_DEVICE_INFORMATION Buffer, PULONG Length)
{
if (*Length >= sizeof(FILE_FS_DEVICE_INFORMATION))
{
Buffer->Characteristics = 0;
Buffer->DeviceType = FILE_DEVICE_NAMED_PIPE;
*Length -= sizeof(FILE_FS_DEVICE_INFORMATION);
return STATUS_SUCCESS;
}
else
return STATUS_INFO_LENGTH_MISMATCH;
}
static NTSTATUS NTAPI
AfdQueryVolumeInformation(PDEVICE_OBJECT DeviceObject, PIRP Irp, PIO_STACK_LOCATION IrpSp)
{
FS_INFORMATION_CLASS InfoClass;
PVOID Buffer;
ULONG Length;
NTSTATUS Status = STATUS_INVALID_INFO_CLASS;
Buffer = Irp->AssociatedIrp.SystemBuffer;
Length = IrpSp->Parameters.QueryVolume.Length;
InfoClass = IrpSp->Parameters.QueryVolume.FsInformationClass;
switch (InfoClass)
{
case FileFsDeviceInformation:
Status = AfdQueryFsDeviceInfo(DeviceObject, Buffer, &Length);
break;
default:
break;
}
Irp->IoStatus.Status = Status;
Irp->IoStatus.Information = IrpSp->Parameters.QueryVolume.Length - Length;
IoCompleteRequest(Irp, IO_NETWORK_INCREMENT);
return Status;
}
static DRIVER_DISPATCH AfdDispatch; static DRIVER_DISPATCH AfdDispatch;
static NTSTATUS NTAPI static NTSTATUS NTAPI
AfdDispatch(PDEVICE_OBJECT DeviceObject, PIRP Irp) AfdDispatch(PDEVICE_OBJECT DeviceObject, PIRP Irp)
@ -870,6 +912,9 @@ AfdDispatch(PDEVICE_OBJECT DeviceObject, PIRP Irp)
case IRP_MJ_READ: case IRP_MJ_READ:
return AfdConnectedSocketReadData( DeviceObject, Irp, IrpSp, TRUE ); return AfdConnectedSocketReadData( DeviceObject, Irp, IrpSp, TRUE );
case IRP_MJ_QUERY_VOLUME_INFORMATION:
return AfdQueryVolumeInformation(DeviceObject, Irp, IrpSp);
case IRP_MJ_DEVICE_CONTROL: case IRP_MJ_DEVICE_CONTROL:
{ {
switch( IrpSp->Parameters.DeviceIoControl.IoControlCode ) { switch( IrpSp->Parameters.DeviceIoControl.IoControlCode ) {
@ -1247,6 +1292,7 @@ DriverEntry(PDRIVER_OBJECT DriverObject, PUNICODE_STRING RegistryPath)
DriverObject->MajorFunction[IRP_MJ_WRITE] = AfdDispatch; DriverObject->MajorFunction[IRP_MJ_WRITE] = AfdDispatch;
DriverObject->MajorFunction[IRP_MJ_READ] = AfdDispatch; DriverObject->MajorFunction[IRP_MJ_READ] = AfdDispatch;
DriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL] = AfdDispatch; DriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL] = AfdDispatch;
DriverObject->MajorFunction[IRP_MJ_QUERY_VOLUME_INFORMATION] = AfdDispatch;
DriverObject->DriverUnload = AfdUnload; DriverObject->DriverUnload = AfdUnload;
Status = IoCreateDevice(DriverObject, Status = IoCreateDevice(DriverObject,

View file

@ -175,23 +175,15 @@ static NTSTATUS ReceiveActivity( PAFD_FCB FCB, PIRP Irp ) {
TotalBytesCopied)); TotalBytesCopied));
UnlockBuffers( RecvReq->BufferArray, UnlockBuffers( RecvReq->BufferArray,
RecvReq->BufferCount, FALSE ); RecvReq->BufferCount, FALSE );
if (FCB->Overread && FCB->LastReceiveStatus == STATUS_SUCCESS)
{
/* Overread after a graceful disconnect so complete with an error */
Status = STATUS_FILE_CLOSED;
}
else
{
/* Unexpected disconnect by the remote host or initial read after a graceful disconnect */
Status = FCB->LastReceiveStatus; Status = FCB->LastReceiveStatus;
}
NextIrp->IoStatus.Status = Status; NextIrp->IoStatus.Status = Status;
NextIrp->IoStatus.Information = 0; NextIrp->IoStatus.Information = 0;
if( NextIrp == Irp ) RetStatus = Status; if( NextIrp == Irp ) RetStatus = Status;
if( NextIrp->MdlAddress ) UnlockRequest( NextIrp, IoGetCurrentIrpStackLocation( NextIrp ) ); if( NextIrp->MdlAddress ) UnlockRequest( NextIrp, IoGetCurrentIrpStackLocation( NextIrp ) );
(void)IoSetCancelRoutine(NextIrp, NULL); (void)IoSetCancelRoutine(NextIrp, NULL);
IoCompleteRequest( NextIrp, IO_NETWORK_INCREMENT ); IoCompleteRequest( NextIrp, IO_NETWORK_INCREMENT );
FCB->Overread = TRUE;
} }
} else { } else {
/* Kick the user that receive would be possible now */ /* Kick the user that receive would be possible now */

View file

@ -71,26 +71,6 @@ UINT TaLengthOfTransportAddressByType(UINT AddressType)
return AddrLen; return AddrLen;
} }
VOID TaCopyAddressInPlace( PTA_ADDRESS Target,
PTA_ADDRESS Source ) {
UINT AddrLen = TaLengthOfAddress( Source );
RtlCopyMemory( Target, Source, AddrLen );
}
PTA_ADDRESS TaCopyAddress( PTA_ADDRESS Source ) {
UINT AddrLen = TaLengthOfAddress( Source );
PVOID Buffer;
if (!AddrLen)
return NULL;
Buffer = ExAllocatePool( NonPagedPool, AddrLen );
if (Buffer)
RtlCopyMemory( Buffer, Source, AddrLen );
return Buffer;
}
VOID TaCopyTransportAddressInPlace( PTRANSPORT_ADDRESS Target, VOID TaCopyTransportAddressInPlace( PTRANSPORT_ADDRESS Target,
PTRANSPORT_ADDRESS Source ) { PTRANSPORT_ADDRESS Source ) {
UINT AddrLen = TaLengthOfTransportAddress( Source ); UINT AddrLen = TaLengthOfTransportAddress( Source );
@ -211,8 +191,7 @@ NTSTATUS TdiBuildNullConnectionInfo
ConnInfo = (PTDI_CONNECTION_INFORMATION) ConnInfo = (PTDI_CONNECTION_INFORMATION)
ExAllocatePool(NonPagedPool, ExAllocatePool(NonPagedPool,
sizeof(TDI_CONNECTION_INFORMATION) + sizeof(TDI_CONNECTION_INFORMATION) + TdiAddressSize);
TdiAddressSize);
if (!ConnInfo) { if (!ConnInfo) {
*ConnectionInfo = NULL; *ConnectionInfo = NULL;
return STATUS_INSUFFICIENT_RESOURCES; return STATUS_INSUFFICIENT_RESOURCES;

View file

@ -141,7 +141,7 @@ typedef struct _AFD_STORED_DATAGRAM {
} AFD_STORED_DATAGRAM, *PAFD_STORED_DATAGRAM; } AFD_STORED_DATAGRAM, *PAFD_STORED_DATAGRAM;
typedef struct _AFD_FCB { typedef struct _AFD_FCB {
BOOLEAN Locked, Critical, Overread, NonBlocking, OobInline, TdiReceiveClosed, SendClosed; BOOLEAN Locked, Critical, NonBlocking, OobInline, TdiReceiveClosed, SendClosed;
UINT State, Flags, GroupID, GroupType; UINT State, Flags, GroupID, GroupType;
KIRQL OldIrql; KIRQL OldIrql;
UINT LockCount; UINT LockCount;

View file

@ -6,8 +6,6 @@ PTRANSPORT_ADDRESS TaCopyTransportAddress( PTRANSPORT_ADDRESS OtherAddress );
PTRANSPORT_ADDRESS TaBuildNullTransportAddress(UINT AddressType); PTRANSPORT_ADDRESS TaBuildNullTransportAddress(UINT AddressType);
UINT TaLengthOfAddress( PTA_ADDRESS Addr ); UINT TaLengthOfAddress( PTA_ADDRESS Addr );
UINT TaLengthOfTransportAddress( PTRANSPORT_ADDRESS Addr ); UINT TaLengthOfTransportAddress( PTRANSPORT_ADDRESS Addr );
VOID TaCopyAddressInPlace( PTA_ADDRESS Target, PTA_ADDRESS Source );
PTA_ADDRESS TaCopyAddress( PTA_ADDRESS Source );
VOID TaCopyTransportAddressInPlace( PTRANSPORT_ADDRESS Target, VOID TaCopyTransportAddressInPlace( PTRANSPORT_ADDRESS Target,
PTRANSPORT_ADDRESS Source ); PTRANSPORT_ADDRESS Source );
UINT TdiAddressSizeFromType( UINT Type ); UINT TdiAddressSizeFromType( UINT Type );