Открытие объекта в Kernel Mode

Тема в разделе "WASM.NT.KERNEL", создана пользователем ov4inka, 23 ноя 2009.

  1. ov4inka

    ov4inka New Member

    Публикаций:
    0
    Регистрация:
    1 дек 2008
    Сообщения:
    37
    есть два драйвера. При загрузке первый создает устройство \Device\MyObject1. Вот код:

    Код (Text):
    1. NTSTATUS CreateMainDevice(IN PDRIVER_OBJECT DriverObject)
    2. {
    3.      UNICODE_STRING                    device_name;
    4.      ANSI_STRING                       Ansidevice_name;
    5.      UNICODE_STRING                    device_link;
    6.      ANSI_STRING                       Ansidevice_link;
    7.      NTSTATUS            status;
    8.      PDEVICE_OBJECT      device_object;
    9.      PMYDEVICE_EXTENSION   device_extension;
    10.      HANDLE              thread_handle;
    11.  
    12.      RtlInitAnsiString( &Ansidevice_name, NTDEVICE_STRING);
    13.      RtlAnsiStringToUnicodeString( &device_name, &Ansidevice_name, TRUE);
    14.      RtlInitAnsiString( &Ansidevice_link, LINKNAME_STRING);
    15.      RtlAnsiStringToUnicodeString( &device_link, &Ansidevice_link, TRUE);
    16.  
    17.      
    18.      status = IoCreateDevice(
    19.         DriverObject,
    20.         sizeof(MYDEVICE_EXTENSION),
    21.         &device_name,
    22.         FILE_DEVICE_UNKNOWN,
    23.         0,
    24.         FALSE,
    25.         &device_object
    26.         );
    27.      
    28.      
    29.      if (!NT_SUCCESS(status))
    30.      {
    31.         return status;
    32.      }
    33.      status = IoCreateSymbolicLink( &device_link, &device_name );
    34.      if (!NT_SUCCESS(status) )
    35.      {
    36.         IoDeleteDevice(device_object);
    37.         return status;
    38.      }
    39.      
    40.      device_object->Flags |= DO_DIRECT_IO;
    41.      device_object->Flags &= ~DO_DEVICE_INITIALIZING;
    42.      
    43.      device_extension = (PMYDEVICE_EXTENSION) device_object->DeviceExtension;
    44.      InitializeListHead(&device_extension->list_head);
    45.      
    46.      KeInitializeSpinLock(&device_extension->list_lock);
    47.      KeInitializeEvent( &device_extension->request_event,
    48.                         SynchronizationEvent,
    49.                         FALSE );
    50.      
    51.      device_extension->terminate_thread = FALSE;
    52.      status = PsCreateSystemThread(
    53.         &thread_handle,
    54.         (ACCESS_MASK) 0L,
    55.         NULL,
    56.         NULL,
    57.         NULL,
    58.         FileDiskThread,
    59.         device_object
    60.         );
    61.      
    62.      if (!NT_SUCCESS(status))
    63.      {
    64.         IoDeleteSymbolicLink( &device_link );
    65.         IoDeleteDevice(device_object);
    66.         return status;
    67.      }
    68.      
    69.      status = ObReferenceObjectByHandle(
    70.         thread_handle,
    71.         THREAD_ALL_ACCESS,
    72.         NULL,
    73.         KernelMode,
    74.         &device_extension->thread_pointer,
    75.         NULL
    76.         );
    77.      
    78.      if (!NT_SUCCESS(status))
    79.      {
    80.         ZwClose(thread_handle);
    81.         device_extension->terminate_thread = TRUE;
    82.         KeSetEvent(
    83.             &device_extension->request_event,
    84.             (KPRIORITY) 0,
    85.             FALSE
    86.             );
    87.         IoDeleteSymbolicLink( &device_link );
    88.         IoDeleteDevice(device_object);
    89.         return status;
    90.      }
    91.      
    92.      ZwClose(thread_handle);
    93.  
    94.      return status;
    95. }
    Второй, также при загрузке, пытается открыть это устройство. Вот код:
    Код (Text):
    1. VOID OpenDevice ( IN PUCHAR Buffer, IN ACCESS_MASK AccessMask, IN ULONG ShareAccess, OUT HANDLE  *handle )
    2. {
    3.     UNICODE_STRING                    ufile_name;
    4.     ANSI_STRING                       AnsiString;
    5.     NTSTATUS                          status = STATUS_SUCCESS;
    6.     IO_STATUS_BLOCK                   FileStatus;
    7.     OBJECT_ATTRIBUTES                 object_attributes;
    8.    
    9.     RtlInitAnsiString( &AnsiString, Buffer);
    10.     RtlAnsiStringToUnicodeString( &ufile_name, &AnsiString, TRUE);
    11.    
    12.     InitializeObjectAttributes(
    13.         &object_attributes,
    14.         &ufile_name,
    15.         OBJ_CASE_INSENSITIVE,
    16.         NULL,
    17.         NULL
    18.         );
    19.  
    20.     status = ZwOpenFile( handle,
    21.         AccessMask,
    22.         &object_attributes,
    23.         &FileStatus,
    24.         ShareAccess,
    25.         FILE_NON_DIRECTORY_FILE |
    26.         FILE_RANDOM_ACCESS |
    27.         FILE_NO_INTERMEDIATE_BUFFERING |
    28.         FILE_SYNCHRONOUS_IO_NONALERT );
    29.        
    30.      RtlFreeUnicodeString( &ufile_name );
    31.        
    32.      if (!NT_SUCCESS(status))
    33.      {
    34.         *handle = NULL;
    35.         return;
    36.      }
    37.      
    38.      return;
    39. }
    Но система зависает! Да, система - Windows Vista 32bit. Стоит мне закомментировать ZwOpenFile и все работает! Иначе - зависает! Подскажите, в чем кривость моих рук? Спасибо!
     
  2. Forever

    Forever Виталий

    Публикаций:
    0
    Регистрация:
    12 апр 2008
    Сообщения:
    244
    А где обработчики IRP_MJ_CREATE и IRP_MJ_CLOSE для устройства?
     
  3. ov4inka

    ov4inka New Member

    Публикаций:
    0
    Регистрация:
    1 дек 2008
    Сообщения:
    37
    В DriverEntry
    Код (Text):
    1.     for (ulIndex = 0, dispatch = DriverObject->MajorFunction;
    2.          ulIndex <= IRP_MJ_MAXIMUM_FUNCTION;
    3.          ulIndex++, dispatch++) {
    4.  
    5.         *dispatch = DiskPerfFilterProc;
    6.     }
    Функция-обработчик всех IRP
    Код (Text):
    1. NTSTATUS DiskPerfFilterProc( IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp )
    2. {
    3.     PMYDEVICE_EXTENSION  MydeviceExtension   = DeviceObject->DeviceExtension;
    4.     IoMarkIrpPending(Irp);
    5.        
    6.     ExInterlockedInsertTailList(
    7.         &(MydeviceExtension->list_head),
    8.         &(Irp->Tail.Overlay.ListEntry),
    9.         &(MydeviceExtension->list_lock)
    10.         );
    11.        
    12.      KeSetEvent(
    13.         &(MydeviceExtension->request_event),
    14.         (KPRIORITY) 0,
    15.         FALSE
    16.         );
    17.        
    18.      return STATUS_PENDING;
    19. }
    Ну и собственно обработка в отдельном потоке
    Код (Text):
    1. VOID FileDiskThread ( IN PVOID Context )
    2. {
    3.     PDEVICE_OBJECT      device_object;
    4.     PMYDEVICE_EXTENSION   device_extension;
    5.     PIRP                irp;
    6.     PIO_STACK_LOCATION  io_stack;
    7.     NTSTATUS            status;
    8.    
    9.     ASSERT(Context != NULL);
    10.  
    11.     device_object = (PDEVICE_OBJECT) Context;
    12.  
    13.     device_extension = (PMYDEVICE_EXTENSION) device_object->DeviceExtension;
    14.  
    15.     for (;;)
    16.     {
    17.         KeWaitForSingleObject(
    18.             &device_extension->request_event,
    19.             Executive,
    20.             KernelMode,
    21.             FALSE,
    22.             NULL
    23.             );
    24.  
    25.         if (device_extension->terminate_thread)
    26.         {
    27.             PsTerminateSystemThread(STATUS_SUCCESS);
    28.         }
    29.  
    30.         while (request = ExInterlockedRemoveHeadList( &device_extension->list_head,
    31.                                                       &device_extension->list_lock ))
    32.         {
    33.             irp = CONTAINING_RECORD(request, IRP, Tail.Overlay.ListEntry);
    34.             io_stack = IoGetCurrentIrpStackLocation(irp);
    35.            
    36.             irp->IoStatus.Status = STATUS_SUCCESS;
    37.             switch (io_stack->MajorFunction)
    38.             {
    39.             case IRP_MJ_WRITE:
    40.                  DebugPrint((2, "DiskFilter: I am successful WRITE!!!\n"));
    41.                  irp->IoStatus.Status = STATUS_SUCCESS;
    42.                  break;
    43.             case IRP_MJ_CREATE:
    44.             case IRP_MJ_CLOSE:
    45.                  DebugPrint((2, "DiskFilter: I am successful opened!!!\n"));                
    46.                  irp->IoStatus.Status = STATUS_SUCCESS;
    47.                  irp->IoStatus.Information = FILE_OPENED;
    48.                  break;
    49.             default:
    50.                 irp->IoStatus.Status = STATUS_DRIVER_INTERNAL_ERROR;
    51.             }
    52.             IoCompleteRequest( irp, IO_NO_INCREMENT );
    53.         } // End of while
    54.        
    55.     }//End ForEver
    56. }
     
  4. ov4inka

    ov4inka New Member

    Публикаций:
    0
    Регистрация:
    1 дек 2008
    Сообщения:
    37
    x64 ну где же ты?????? подскажи)
     
  5. xssww2

    xssww2 New Member

    Публикаций:
    0
    Регистрация:
    11 апр 2009
    Сообщения:
    84
    я так тоже люблю звать на помощь))))
     
  6. x64

    x64 New Member

    Публикаций:
    0
    Регистрация:
    29 июл 2008
    Сообщения:
    1.370
    Адрес:
    Россия
    Во-первых, все эти флаги в ZwOpenFile() обычно не нужны при открытии собственных девайсов неизвестного типа:

    Во-вторых, если ты указываешь флаг FILE_SYNCHRONOUS_IO_NONALERT, то маска доступа должна содержать флаг SYNCHRONIZE. Вообще, было бы неплохо уточнить, как и когда вызывается функция OpenDevice().

    В-третьих, ты уверен, что поток действительно работает и занимается выборкой запросов? Я бы поставил здесь побольше отладочных сообщений и убедился, что запрос на открытие действительно завершается вызовом IoCompleteRequest().

    Особых проблем в коде не вижу, за исключением мелких недочётов типа этих:

    1. Забыл последнее break; в ветке default: в switch.
    2. Зачем перегонять строки из ANSI в Unicode, вообще не понятно. Обычно используют сразу Unicode.