Как передать данные из драйвера в "пользовательское" приложение?

Тема в разделе "WASM.BEGINNERS", создана пользователем Inkognito, 15 май 2008.

  1. Inkognito

    Inkognito New Member

    Публикаций:
    0
    Регистрация:
    21 мар 2008
    Сообщения:
    25
    Изучив примеры ioctl и event я сделал вывод, что мне они не помогут так как у меня Filter-Hook Driver (надо было наверное сразу об этом сказать) и мне необходимо передавать информацию из пакета (его размер) после поступления соответствующего пакета по сети. Я также посмотрел статью http://www.wasm.ru/article.php?article=drvw2k14 и у меня возник такой вопрос: "Недостаточно ли в моём случае вместо процедуры ProcessNotifyRoutine, указывать PF_FORWARD_ACTION hook_proc() - callback функцию для обработки пакетов, в PsSetCreateProcessNotifyRoutine?" Если этого недостаточно, то как же заставить следить драйвер за поступлением пакетов?
    P.S.
    Данный вопрос уже задавал 9ine в 2004 году, но как он это сделал там не указано. Если кто-то делал нечто похожее, поделитесь опытом.
     
  2. Inkognito

    Inkognito New Member

    Публикаций:
    0
    Регистрация:
    21 мар 2008
    Сообщения:
    25
    По примеру указанной ранее статьи делаю следующее:
    1) в приложении
    Код (Text):
    1. ...
    2. hHandle = CreateFile("\\\\.\\ipfilterr",
    3.             GENERIC_READ | GENERIC_WRITE,
    4.             FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE,
    5.             NULL,
    6.             CREATE_ALWAYS,
    7.             FILE_ATTRIBUTE_NORMAL,
    8.             NULL );
    9.     if(hHandle == INVALID_HANDLE_VALUE)
    10.     {    
    11.         printf("ERR: can not access driver ipfilterr.sys!! (%d)\n", GetLastError());
    12.         goto done;
    13.     }
    14. hEvent = CreateEvent(NULL, FALSE, FALSE, NULL);
    15.     g_fbExitNow = FALSE;
    16.  
    17.     if( hEvent == NULL )
    18.      printf("error in CreateEvent(%d)\n",GetLastError());
    19.  
    20.   hThread = CreateThread(NULL, 0, WaitForProcessData, hEvent, 0, NULL);
    21.     if(hThread == NULL)
    22.    {
    23.        printf("error in CreateThread (%d)\n",GetLastError());
    24.    }
    25.    CloseHandle(hThread);
    26.  
    27.      bl = DeviceIoControl(hHandle,
    28.                     (DWORD)IOCTL_SET_NOTIFY,
    29.                     &hEvent, sizeof(hEvent),                  
    30.                      NULL, 0,  
    31.                     &BytesReturned,
    32.                     (LPVOID)NULL );
    33.     if(!bl)
    34.    {
    35.     printf( "Error in IOCTL_SET_NOTIFY! Can not set notify (%d)\n", GetLastError() );
    36.     goto done;
    37.    }
    38. ...
    GetLastError() возвращает 6
    2) в драйвере
    Код (Text):
    1. ...
    2.   case IOCTL_SET_NOTIFY:        
    3.                 ...
    4.    status = ObReferenceObjectByHandle(inBuf, EVENT_MODIFY_STATE,
    5.                                     &ExEventObjectType,
    6.                                 UserMode,  
    7.                                                       &pEvent, NULL);
    8.         if( status == STATUS_SUCCESS )
    9.             {
    10.                ...
    11.             }
    12.    DbgPrint("-IPFILT- Could not reference user event object. Status: %08X\n",status);
    status = C0000008
    Как исправить сложившуюся ситуацию?
     
  3. Inkognito

    Inkognito New Member

    Публикаций:
    0
    Регистрация:
    21 мар 2008
    Сообщения:
    25
    У меня ещё такой вопрос: "Как при помощи ZwWriteFile записать число в файл?" Сразу, как я понял, число записать нельзя, поэтому можно ли зделать что-то вроде этого:
    Код (Text):
    1. ULONG            chislo = 256987;//к примеру
    2. UNICODE_STRING      peremen;
    3. ANSI_STRING           str_ans;
    4. IO_STATUS_BLOCK    isb;
    5. HANDLE                   hFile;
    6.  
    7. RtlIntegerToUnicodeString(chislo, 0, &peremen);
    8. RtlUnicodeStringToAnsiString(&str_ans, &peremen, TRUE);
    9. ...
    10. status = ZwWriteFile(hFile, 0, NULL, NULL, &isb,
    11.                          &str_ans, strlen(&str_ans), NULL, NULL);
    12. ...
     
  4. z0mailbox

    z0mailbox z0

    Публикаций:
    0
    Регистрация:
    3 фев 2005
    Сообщения:
    635
    Адрес:
    Russia СПБ
    извращение
    _snwprintf
     
  5. Inkognito

    Inkognito New Member

    Публикаций:
    0
    Регистрация:
    21 мар 2008
    Сообщения:
    25
    Спасибо за _snwprintf (правда к этому моменту она мне уже не нужна, но на будущее может пригодиться).
    А правда, что функция GetUserNameEx может вернуть имя "текущего" пользователя системы? Как её использовать в смысле, что и где нужно подключать в VS2005, что бы она заработала, а то студия ругается (error C2065: 'NameDisplay' : undeclared identifier, error C3861: 'GetUserNameEx': identifier not found). Мне нужно определить (в User mode или Kernel mode, неважно, где проще, но лучше конечно всё-таки в User mode) login текущего пользователя Windows XP.
    P.S.
    Вопрос может быть не совсем по "стартовой теме", но у меня сейчас в сущности одна тема - Filter-Hook Driver и "связанное" с ним приложение.
     
  6. n0name

    n0name New Member

    Публикаций:
    0
    Регистрация:
    5 июн 2004
    Сообщения:
    4.336
    Адрес:
    Russia
    Покажи код.
    Линковать надо Secur32.lib.
    Инклудить - Security.h.
    Все это есть в MSDN'e.
     
  7. Inkognito

    Inkognito New Member

    Публикаций:
    0
    Регистрация:
    21 мар 2008
    Сообщения:
    25
    кода у меня немного, прямо скажем.
    Код (Text):
    1. char               *buf;
    2. DWORD            size;
    3.  GetUserNameEx(NameDisplay, buf, &size);
    4. printf("name is %s \n",buf);//я наивно полагаю, что теперь в buf должен быть login
    я там не правильно сказал я компилирую не в VS2005, а build'ом из DDk, но в общем и DDK VS2005 сейчас (после подключения Security.h и sspi.h) ругаются одинаково (d:\visual studio 2005\vc\platformsdk\include\sspi.h(59) : fatal error C1189: #error : You must define one of SECURITY_WIN32, SECURITY_KERNEL, or). Как мне эту Secur32.lib "залинковать" в DDk, надо как-то в sources файле прописывать?
     
  8. n0name

    n0name New Member

    Публикаций:
    0
    Регистрация:
    5 июн 2004
    Сообщения:
    4.336
    Адрес:
    Russia
    у тебя даже до линковки не доходит дело, а так да - в sources.
    #define SECURITY_WIN32 перед инклудами.
     
  9. Inkognito

    Inkognito New Member

    Публикаций:
    0
    Регистрация:
    21 мар 2008
    Сообщения:
    25
    всё скомпилировалось без ошибок и без ворнингов и в результате получилось name is <null> Это так должно быть или я чего-то не так сделал?
     
  10. n0name

    n0name New Member

    Публикаций:
    0
    Регистрация:
    5 июн 2004
    Сообщения:
    4.336
    Адрес:
    Russia
    читай MSDN, особенно про третий аргумент.
     
  11. Inkognito

    Inkognito New Member

    Публикаций:
    0
    Регистрация:
    21 мар 2008
    Сообщения:
    25
    У меня ещё вопрос (я ведь никому этим не мешаю, задаю себе и задаю, в смысле ни себе, а ... в общем каламбурчик) нарисовался.
    Как можно передать массив или структуру в драйвер из приложения? У меня 4 варианта:
    1) передавать весь массив (структуру) сразу, как обычную переменную?
    2) передавать в цикле каждое значение массива (поле структуры)?
    3) запихиавть массив (структуру) в строку, передавать строку, а потом выковыривать обратно каждое значение (поле)?
    4) для каждого значения создавать свой IOCTL - какой-то совсем дурной (если массив из 100 чисел?) вариант, зато, наверное работать точно будет?
    Какой выбрать?
    По 1) делаю так
    Код (Text):
    1. /*в приложении*/
    2. ULONG       IPmas[5];
    3. IPmas[0] = 1; //к примеру
    4. IPmas[1] = 2;
    5. IPmas[2] = 3;
    6. IPmas[3] = 4;
    7. IPmas[4] = 5;
    8. ...
    9. DeviceIoControl(hHandle, (DWORD)IOCTL_SET_NOTIFY, &IPmas, sizeof(IPmas),          
    10.              NULL, 0, &BytesReturned, (LPVOID)NULL );
    11. ...
    12. /*в драйвере*/
    13. ULONG         int_in_data, znach;
    14. PULONG        inBuff;
    15. case IOCTL_SET_NOTIFY:  
    16.          inBuff = Irp->AssociatedIrp.SystemBuffer;   
    17.     DbgPrint("-IPFILT- inBuf = %u %u %u\n",inBuff, &inBuff, *inBuff);
    18.     int_in_data = *inBuff;
    19.      _asm{
    20.           mov esi, 0
    21.           mov ebx, int_in_data[esi]
    22.           mov znach, ebx
    23.            }
    24.    
    25. DbgPrint("IPmas_Kernel = %u\n",znach);  //в znach почему-то последнее число переданного массива
    26.        _asm{
    27.           mov esi, 0
    28.           mov ebx, int_in_data[esi+2]; (mov ebx, int_in_data[esi-2])
    29.           mov znach, ebx
    30.            }
    31. DbgPrint("IPmas_Kernel = %u\n",znach);//в zhach хрен знает что за число, если [esi-4] или [esi+4], то в zhach 0
    Что я сделал не так, как достать переданный массив, если он конечно вообще передан (размер массива передаётся верно)?
    2)
    Код (Text):
    1. /*в приложении*/
    2. int i = 0, count = 5;
    3. ...
    4. do
    5. {        
    6.  DeviceIoControl(hHandle, (DWORD)IOCTL_SET_NOTIFY, &IPmas[i], sizeof(IPmas[i]),                             NULL, 0, &BytesReturned, (LPVOID)NULL );
    7.  i++;
    8.  count--;    
    9. }
    10.  while(count == 0);
    11. ...
    Происходит только один вызов DeviceIoControl. Что не так (подозреваю, что всё не так)?
    3) и 4) я ещё не пробовал
     
  12. n0name

    n0name New Member

    Публикаций:
    0
    Регистрация:
    5 июн 2004
    Сообщения:
    4.336
    Адрес:
    Russia
    Код (Text):
    1. mov ebx, int_in_data[esi]
    2. ...
    3. mov eax, [inBuff]
    4. mov ebx, [eax + esi * 4]
    выполняется цекл до тех пор пока count==0

    советую все таки сесть почитать умные книжки по ассемблеру и Си.
     
  13. Inkognito

    Inkognito New Member

    Публикаций:
    0
    Регистрация:
    21 мар 2008
    Сообщения:
    25
    Вот это я И.... Массив передался, спасибо!
    На крупномасштабное изучение у меня уже не осталось времени, делаю всё в торопях, но в книжки всё-таки заглядываю, перед тем как спросить, правда выясняется, что невнимательно смотрю.
    Вот на счёт GetUserNameEx ещё буду смотреть, чуть-чуть попозже, особенно про 3 параметр, а пока GetLastError(): 1332.
     
  14. Inkognito

    Inkognito New Member

    Публикаций:
    0
    Регистрация:
    21 мар 2008
    Сообщения:
    25
    Подключаю #include <iostream> для динамического создания массива. Компилирую в VS2005 - всё работает, компилирую этот же код в DDk - ругается следующим образом:
    Код (Text):
    1. 1>zappp.obj() : error LNK2019: unresolved external symbol "public: __thiscall std::ios_base::Init::Init(void)" (??0Init@ios_base@std@@QAE@XZ) referenced in function _$E1
    2. 1>zappp.obj() : error LNK2019: unresolved external symbol "public: __thiscall std::ios_base::Init::~Init(void)" (??1Init@ios_base@std@@QAE@XZ) referenced in function _$E2
    3. 1>zappp.obj() : error LNK2019: unresolved external symbol "public: __thiscall std::_Winit::_Winit(void)" (??0_Winit@std@@QAE@XZ) referenced in function _$E4
    4. 1>zappp.obj() : error LNK2019: unresolved external symbol "public: __thiscall std::_Winit::~_Winit(void)" (??1_Winit@std@@QAE@XZ) referenced in function _$E5
    5. 1>objchk\i386\zap.exe() : error LNK1120: 4 unresolved externals
    И там ещё 16 ворнингов, я их не стал показывать. Кто нибудь может объяснить, что происходит и как это исправить?
     
  15. Inkognito

    Inkognito New Member

    Публикаций:
    0
    Регистрация:
    21 мар 2008
    Сообщения:
    25
    Написано, не помню где, что в поле "транспорт" IP-заголовка число 6 идентифицирует протокол TCP.
    В DDK есть следующий пример
    Код (Text):
    1. #define PROT_TCP   6
    2.  
    3. // Drop all TCP packets
    4.  
    5. PF_FORWARD_ACTION
    6. DropTcpPackets(
    7.         unsigned char   *PacketHeader,
    8.         unsigned char   *Packet,
    9.         unsigned int    PacketLength,
    10.         unsigned int    RecvInterfaceIndex,
    11.         unsigned int    SendInterfaceIndex,
    12.         IPAddr          RecvLinkNextHop,
    13.         IPAddr          SendLinkNextHop
    14.         )
    15. {
    16.     if (PacketHeader->iph_protocol == PROT_TCP)
    17.     {
    18.         return PF_DROP;
    19.     }
    20.     return PF_FORWARD;
    21. }
    У меня
    Код (Text):
    1. typedef struct IPHeader {
    2.   UCHAR  iph_verlen;  // Version and length
    3.   UCHAR  iph_tos;         // Type of service
    4.   USHORT  iph_length;    // Total datagram length
    5.   USHORT  iph_id;         // Identification
    6.   USHORT  iph_offset;    // Flags, fragment offset
    7.   USHORT  iph_ttl;         // Time to live
    8.   UCHAR  iph_protocol;  // Protocol
    9.   USHORT  iph_xsum;  // Header checksum
    10.   ULONG  iph_src;     // Source address
    11.   ULONG  iph_dest;  // Destination address
    12. } IPHeader;
    13. ...
    14. PF_FORWARD_ACTION
    15. hook_proc(unsigned char *PacketHeader, unsigned char *Packet, unsigned int PacketLength, unsigned int RecvInterfaceIndex, unsigned int SendInterfaceIndex, IPAddr RecvLinkNextHop, IPAddr SendLinkNextHop)
    16. {
    17. IPHeader *ipp;
    18. ipp=(IPHeader*)PacketHeader;
    19. DbgPrint("protocol = %d",ipp->iph_protocol);
    20. ...
    21. }
    22. ...
    Запускаю свой Filter-Hook Driver, подключаюсь к интернет. Выводит какие-угодно (0...255) значения, кроме 6. Почему? Не подскажите где можно что-нибудь узнать по этому поводу?
     
  16. Clerk

    Clerk Забанен

    Публикаций:
    0
    Регистрация:
    4 янв 2008
    Сообщения:
    6.689
    Адрес:
    РБ, Могилёв
    Inkognito
    Не знаю что ты там курил :)
    Создать разделяемую память.
     
  17. Inkognito

    Inkognito New Member

    Публикаций:
    0
    Регистрация:
    21 мар 2008
    Сообщения:
    25
    Это я так понимаю по поводу сообщения #31, так с этим разобрался.
    А вот, что на счёт #35 или #34??
     
  18. akaGK

    akaGK New Member

    Публикаций:
    0
    Регистрация:
    9 июл 2008
    Сообщения:
    1
    подскажите как реализовать самым простым способом передачу... Нужно чтобы при нажатии клавиши драйвер-фильтр передавал в приложение код этой клавиши.
    Пробовал как то так:
    в приложении
    Код (Text):
    1. HANDLE hHandle = CreateFile( "\\\\.\\kbfiltr",GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
    2.  
    3.           DWORD RL, Status = 1;
    4.  
    5.           int Direction = 0;
    6.           int err;
    7.  
    8.           int Ret;
    9.           char *buf = NULL;
    10.           buf = new char;
    11.  
    12.           Ret = ReadFile(hHandle,buf,1,NULL,NULL);
    в драйвере
    Код (Text):
    1. NTSTATUS KbFilter_Callback(IN PDEVICE_OBJECT DeviceObject,IN PIRP IRP,IN PVOID Context)
    2. {
    3.     PIO_STACK_LOCATION      IRPStack;
    4.     PKEYBOARD_INPUT_DATA    KeyData;
    5.    
    6.     DbgPrint(("Callback"));
    7.    
    8.     IRPStack = IoGetCurrentIrpStackLocation(IRP);
    9.     if (NT_SUCCESS(IRP->IoStatus.Status))
    10.     {
    11.         KeyData=IRP->AssociatedIrp.SystemBuffer;   
    12.  
    13.         if (KeyData[0].MakeCode == 18)
    14.         {
    15.             NTSTATUS ntStatus = STATUS_SUCCESS;
    16.  
    17.             ntStatus = 1;
    18.  
    19.             // Завершение запроса
    20.             IRP->IoStatus.Status = ntStatus;
    21.             IRP->IoStatus.Information = 1;
    22.  
    23.             IoCompleteRequest(IRP,IO_NO_INCREMENT);
    24.             return ntStatus;
    25.         }
    26.     }
    27.  
    28.     if (IRP->PendingReturned) IoMarkIrpPending(IRP);
    29.     return IRP->IoStatus.Status;
    30. }
    31.  
    32. NTSTATUS KbFilter_Read(IN PDEVICE_OBJECT DeviceObject,IN PIRP IRP)
    33. {
    34.     PDEVICE_EXTENSION   DeviceExtension;
    35.     PIO_STACK_LOCATION  CurrentIRPStack;
    36.     PIO_STACK_LOCATION  NextIRPStack;
    37.  
    38.     DbgPrint(("Read"));
    39.  
    40.     DeviceExtension=(PDEVICE_EXTENSION)DeviceObject->DeviceExtension;
    41.     CurrentIRPStack=IoGetCurrentIrpStackLocation(IRP);
    42.     NextIRPStack=IoGetNextIrpStackLocation(IRP);    
    43.  
    44.     *NextIRPStack=*CurrentIRPStack;
    45.     IoSetCompletionRoutine(IRP,KbFilter_Callback,DeviceObject,TRUE,TRUE,TRUE);
    46.  
    47.     return IoCallDriver(DeviceExtension->TopOfStack,IRP);
    48. }
    CreateFile вроде проходит, на ReadFile бсод
     
  19. Four-F

    Four-F New Member

    Публикаций:
    0
    Регистрация:
    31 авг 2002
    Сообщения:
    1.237
    http://www.wasm.ru/article.php?article=drvw2k16
     
  20. FoxB

    FoxB Member

    Публикаций:
    0
    Регистрация:
    10 июл 2003
    Сообщения:
    117
    Кто может поделиться старым IFS Kit или сцыль может есть, где он лежит?
    На сайте М$ его убрали...