[ros-diffs] [cgutman] 54819: [NDISUIO] - Handle IOCTL_NDISUIO_OPEN_WRITE_DEVICE and IOCTL_NDISUIO_OPEN_DEVICE properly with regard to current open handles - Check that we have read permissions (opened by IOCTL...

cgutman at svn.reactos.org cgutman at svn.reactos.org
Tue Jan 3 18:12:30 UTC 2012


Author: cgutman
Date: Tue Jan  3 18:12:29 2012
New Revision: 54819

URL: http://svn.reactos.org/svn/reactos?rev=54819&view=rev
Log:
[NDISUIO]
- Handle IOCTL_NDISUIO_OPEN_WRITE_DEVICE and IOCTL_NDISUIO_OPEN_DEVICE properly with regard to current open handles
- Check that we have read permissions (opened by IOCTL_NDISUIO_OPEN_DEVICE) before allowing queries or reads

Modified:
    branches/wlan-bringup/drivers/network/ndisuio/ioctl.c
    branches/wlan-bringup/drivers/network/ndisuio/ndisuio.h
    branches/wlan-bringup/drivers/network/ndisuio/readwrite.c

Modified: branches/wlan-bringup/drivers/network/ndisuio/ioctl.c
URL: http://svn.reactos.org/svn/reactos/branches/wlan-bringup/drivers/network/ndisuio/ioctl.c?rev=54819&r1=54818&r2=54819&view=diff
==============================================================================
--- branches/wlan-bringup/drivers/network/ndisuio/ioctl.c [iso-8859-1] (original)
+++ branches/wlan-bringup/drivers/network/ndisuio/ioctl.c [iso-8859-1] Tue Jan  3 18:12:29 2012
@@ -174,8 +174,19 @@
         {
             /* Reference the adapter context */
             KeAcquireSpinLock(&AdapterContext->Spinlock, &OldIrql);
-            ReferenceAdapterContext(AdapterContext);
-            Status = STATUS_SUCCESS;
+            if (AdapterContext->OpenCount != 0)
+            {
+                /* An open for read-write is exclusive,
+                 * so we can't have any other open handles */
+                KeReleaseSpinLock(&AdapterContext->Spinlock, OldIrql);
+                Status = STATUS_INVALID_PARAMETER;
+            }
+            else
+            {
+                /* Add a reference */
+                ReferenceAdapterContext(AdapterContext);
+                Status = STATUS_SUCCESS;
+            }
         }
         else
         {
@@ -191,6 +202,9 @@
             {
                 /* Set the file object pointer */
                 OpenEntry->FileObject = FileObject;
+                
+                /* Set the permissions */
+                OpenEntry->WriteOnly = FALSE;
 
                 /* Associate this FO with the adapter */
                 FileObject->FsContext = AdapterContext;
@@ -230,8 +244,80 @@
 NTSTATUS
 OpenDeviceWrite(PIRP Irp, PIO_STACK_LOCATION IrpSp)
 {
-    /* FIXME: Handle this correctly */
-    return OpenDeviceReadWrite(Irp, IrpSp);
+    PFILE_OBJECT FileObject = IrpSp->FileObject;
+    UNICODE_STRING DeviceName;
+    ULONG NameLength;
+    NTSTATUS Status;
+    PNDISUIO_ADAPTER_CONTEXT AdapterContext;
+    PNDISUIO_OPEN_ENTRY OpenEntry;
+    KIRQL OldIrql;
+    
+    NameLength = IrpSp->Parameters.DeviceIoControl.InputBufferLength;
+    if (NameLength != 0)
+    {
+        DeviceName.MaximumLength = DeviceName.Length = NameLength;
+        DeviceName.Buffer = IrpSp->Parameters.DeviceIoControl.Type3InputBuffer;
+        
+        /* Check if this already has a context */
+        AdapterContext = FindAdapterContextByName(&DeviceName);
+        if (AdapterContext != NULL)
+        {
+            /* Reference the adapter context */
+            KeAcquireSpinLock(&AdapterContext->Spinlock, &OldIrql);
+            ReferenceAdapterContext(AdapterContext);
+            Status = STATUS_SUCCESS;
+        }
+        else
+        {
+            /* Invalid device name */
+            Status = STATUS_INVALID_PARAMETER;
+        }
+        
+        /* Check that the bind succeeded */
+        if (NT_SUCCESS(Status))
+        {
+            OpenEntry = ExAllocatePool(NonPagedPool, sizeof(*OpenEntry));
+            if (OpenEntry)
+            {
+                /* Set the file object pointer */
+                OpenEntry->FileObject = FileObject;
+                
+                /* Associate this FO with the adapter */
+                FileObject->FsContext = AdapterContext;
+                FileObject->FsContext2 = OpenEntry;
+                
+                /* Set permissions */
+                OpenEntry->WriteOnly = TRUE;
+                
+                /* Add it to the adapter's list */
+                InsertTailList(&AdapterContext->OpenEntryList,
+                               &OpenEntry->ListEntry);
+                
+                /* Success */
+                KeReleaseSpinLock(&AdapterContext->Spinlock, OldIrql);
+                Status = STATUS_SUCCESS;
+            }
+            else
+            {
+                /* Remove the reference we added */
+                KeReleaseSpinLock(&AdapterContext->Spinlock, OldIrql);
+                DereferenceAdapterContext(AdapterContext, NULL);
+                Status = STATUS_NO_MEMORY;
+            }
+        }
+    }
+    else
+    {
+        /* Invalid device name */
+        Status = STATUS_INVALID_PARAMETER;
+    }
+    
+    Irp->IoStatus.Status = Status;
+    Irp->IoStatus.Information = 0;
+    
+    IoCompleteRequest(Irp, IO_NO_INCREMENT);
+    
+    return Status;
 }
 
 NTSTATUS
@@ -240,6 +326,7 @@
                          PIRP Irp)
 {
     PIO_STACK_LOCATION IrpSp = IoGetCurrentIrpStackLocation(Irp);
+    PNDISUIO_OPEN_ENTRY OpenEntry;
     
     ASSERT(DeviceObject == GlobalDeviceObject);
 
@@ -263,24 +350,39 @@
                 return STATUS_INVALID_PARAMETER;
             }
 
-            /* Now handle other IOCTLs */
+            /* Now handle write IOCTLs */
             switch (IrpSp->Parameters.DeviceIoControl.IoControlCode)
             {
-                case IOCTL_CANCEL_READ:
-                    return CancelPacketRead(Irp, IrpSp);
-
-                case IOCTL_NDISUIO_QUERY_OID_VALUE:
-                    return QueryAdapterOid(Irp, IrpSp);
-
                 case IOCTL_NDISUIO_SET_OID_VALUE:
                     return SetAdapterOid(Irp, IrpSp);
 
                 default:
-                    DPRINT1("Unimplemented\n");
-                    Irp->IoStatus.Status = STATUS_NOT_IMPLEMENTED;
-                    Irp->IoStatus.Information = 0;
-                    IoCompleteRequest(Irp, IO_NO_INCREMENT);
-                    break;
+                    /* Check that we have read permissions */
+                    OpenEntry = IrpSp->FileObject->FsContext2;
+                    if (OpenEntry->WriteOnly)
+                    {
+                        Irp->IoStatus.Status = STATUS_INVALID_PARAMETER;
+                        Irp->IoStatus.Information = 0;
+                        IoCompleteRequest(Irp, IO_NO_INCREMENT);
+                        
+                        return STATUS_INVALID_PARAMETER;
+                    }
+
+                    switch (IrpSp->Parameters.DeviceIoControl.IoControlCode)
+                    {
+                        case IOCTL_CANCEL_READ:
+                            return CancelPacketRead(Irp, IrpSp);
+                        
+                        case IOCTL_NDISUIO_QUERY_OID_VALUE:
+                            return QueryAdapterOid(Irp, IrpSp);
+                        
+                        default:
+                            DPRINT1("Unimplemented\n");
+                            Irp->IoStatus.Status = STATUS_NOT_IMPLEMENTED;
+                            Irp->IoStatus.Information = 0;
+                            IoCompleteRequest(Irp, IO_NO_INCREMENT);
+                            break;
+                    }
             }
             break;
     }

Modified: branches/wlan-bringup/drivers/network/ndisuio/ndisuio.h
URL: http://svn.reactos.org/svn/reactos/branches/wlan-bringup/drivers/network/ndisuio/ndisuio.h?rev=54819&r1=54818&r2=54819&view=diff
==============================================================================
--- branches/wlan-bringup/drivers/network/ndisuio/ndisuio.h [iso-8859-1] (original)
+++ branches/wlan-bringup/drivers/network/ndisuio/ndisuio.h [iso-8859-1] Tue Jan  3 18:12:29 2012
@@ -42,9 +42,24 @@
     /* File object */
     PFILE_OBJECT FileObject;
     
+    /* Tracks how this adapter was opened (write-only or read-write) */
+    BOOLEAN WriteOnly;
+    
     /* List entry */
     LIST_ENTRY ListEntry;
 } NDISUIO_OPEN_ENTRY, *PNDISUIO_OPEN_ENTRY;
+
+struct _NDISUIO_PACKET_ENTRY
+{
+    /* Length of data at the end of the struct */
+    ULONG PacketLength;
+    
+    /* Entry on the packet list */
+    LIST_ENTRY ListEntry;
+
+    /* Packet data */
+    UCHAR PacketData[1];
+} NDISUIO_PACKET_ENTRY, *PNDISUIO_PACKET_ENTRY;
 
 /* NDIS version info */
 #define NDIS_MAJOR_VERISON 5

Modified: branches/wlan-bringup/drivers/network/ndisuio/readwrite.c
URL: http://svn.reactos.org/svn/reactos/branches/wlan-bringup/drivers/network/ndisuio/readwrite.c?rev=54819&r1=54818&r2=54819&view=diff
==============================================================================
--- branches/wlan-bringup/drivers/network/ndisuio/readwrite.c [iso-8859-1] (original)
+++ branches/wlan-bringup/drivers/network/ndisuio/readwrite.c [iso-8859-1] Tue Jan  3 18:12:29 2012
@@ -18,6 +18,7 @@
 {
     PIO_STACK_LOCATION IrpSp = IoGetCurrentIrpStackLocation(Irp);
     PNDISUIO_ADAPTER_CONTEXT AdapterContext = IrpSp->FileObject->FsContext;
+    PNDISUIO_OPEN_ENTRY OpenEntry = IrpSp->FileObject->FsContext2;
     KIRQL OldIrql;
     NTSTATUS Status;
     PLIST_ENTRY ListEntry;
@@ -25,6 +26,15 @@
     ULONG BytesCopied = 0;
 
     ASSERT(DeviceObject == GlobalDeviceObject);
+
+    if (OpenEntry->WriteOnly)
+    {
+        Irp->IoStatus.Status = STATUS_INVALID_PARAMETER;
+        Irp->IoStatus.Information = 0;
+        IoCompleteRequest(Irp, IO_NO_INCREMENT);
+        
+        return STATUS_INVALID_PARAMETER;
+    }
 
     while (TRUE)
     {




More information about the Ros-diffs mailing list