c ++ CreateFile () возвращает 1 (недопустимая функция) при попытке открыть устройство в win 10 - PullRequest
0 голосов
/ 04 июля 2018

Я пытаюсь реализовать простой драйвер режима ядра для мониторинга процесса создания. Когда я пытаюсь открыть устройство с помощью CreateFile (), он возвращает код ошибки 1 (недопустимая функция). Я добавил код драйвера и пользовательского режима ниже. Пожалуйста, посмотрите и скажите мне, что мне не хватает.

UserModeController.cpp:

#include "stdafx.h"
#include <iostream>
#include <string>
#include <Windows.h>
#include <winioctl.h>

using namespace std;

#define MILLISEC 1000

#define IOCTL_ADD_BLAPP CTL_CODE(FILE_DEVICE_UNKNOWN, 0x801, METHOD_BUFFERED, FILE_READ_DATA)
#define IOCTL_REM_BLAPP CTL_CODE(FILE_DEVICE_UNKNOWN, 0x802, METHOD_BUFFERED, FILE_READ_DATA)

#define MAX_PATH 255

#define CMD_INSTALL     L"/install"
#define CMD_UNINSTALL   L"/uninstall"
#define CMD_START       L"/start"
#define CMD_STOP        L"/stop"
#define CMD_ADD         L"/add"
#define CMD_REMOVE      L"/remove"

#define BL_SERVICE_NAME L"BLDrv"
#define BL_BINARY_PATH  L"c:\\DriverTest\\BLDrv.sys"

#define SYMBOLIC_LINK   L"\\\\.\\BLDev"

HANDLE g_hDeviceHandle  = INVALID_HANDLE_VALUE;

SC_HANDLE g_schSCManager    = NULL;
SC_HANDLE g_schBLDrv        = NULL;

SERVICE_STATUS g_ssBLServStatus;

void PrintHelpMessage();

void InstallDriver();

void UninstallDriver();

void StartDriver();

void StopDriver();

void AddBlacklistApp(WCHAR* inparam);

void RemoveBlacklistApp(WCHAR* inparam);

int wmain(int argc, wchar_t* argv[])
{

    if (argc < 2)
        PrintHelpMessage();

    if (!wcscmp(argv[1], CMD_INSTALL))
    {
        InstallDriver();
    }
    else if (!wcscmp(argv[1], CMD_UNINSTALL))
    {
        UninstallDriver();
    }
    else if (!wcscmp(argv[1], CMD_START))
    {
        StartDriver();
    }
    else if (!wcscmp(argv[1], CMD_STOP))
    {
        StopDriver();
    }
    else if (!wcscmp(argv[1], CMD_ADD))
    {
        if (argv[2] != L"")
            AddBlacklistApp(argv[2]);
    }
    else if (!wcscmp(argv[1], CMD_REMOVE))
    {
        if (argv[2] != L"")
            RemoveBlacklistApp(argv[2]);
    }
    else
    {
        cout << endl << "Invalid argument." << endl << endl;
        PrintHelpMessage();
    }

    return 0;
}

void PrintHelpMessage()
{
    wcout << CMD_INSTALL << L" - Install blacklist driver." << endl;
    wcout << CMD_UNINSTALL << L" - Uninstall blacklist driver." << endl;
    wcout << CMD_START << L" - Start blacklist driver service." << endl;
    wcout << CMD_STOP << L" - Stop blacklist driver service." << endl;
    wcout << CMD_ADD << L" - Add program to blacklist." << endl;
    wcout << CMD_REMOVE << L" - Remove program from blacklist." << endl;
}

BOOL OpenSCM()
{
    g_schSCManager = OpenSCManager(
        NULL,
        NULL,
        SC_MANAGER_ALL_ACCESS
    );
    if (g_schSCManager == NULL)
    {
        cout << "Failed to open SCManager : " << GetLastError() << endl;
        return FALSE;
    }   
    else
        return TRUE;
}

BOOL OpenBLServ()
{
    g_schBLDrv = OpenService(
        g_schSCManager,
        BL_SERVICE_NAME,
        SERVICE_ALL_ACCESS
    );
    if (g_schBLDrv == NULL)
    {
        cout << "Failed to open BLDrv service : " << GetLastError() << endl;
        return FALSE;
    }
    else
        return TRUE;
}

BOOL OpenDeviceHandle()
{
    g_hDeviceHandle = CreateFile(
        L"\\\\.\\BLDev",
        GENERIC_ALL,
        NULL,
        NULL,
        OPEN_EXISTING,
        FILE_ATTRIBUTE_SYSTEM,
        NULL
    );
    if (g_hDeviceHandle == INVALID_HANDLE_VALUE)
    {
        cout << "Failed to create file : " << GetLastError() << endl;
        return FALSE;
    }
    else
        return TRUE;
}

void InstallDriver()
{
    if (g_schSCManager == NULL)
        if (!OpenSCM())
            return;

    g_schBLDrv = CreateService(
        g_schSCManager,
        BL_SERVICE_NAME,
        BL_SERVICE_NAME,
        SERVICE_ALL_ACCESS,
        SERVICE_KERNEL_DRIVER,
        SERVICE_DEMAND_START,
        SERVICE_ERROR_NORMAL,
        BL_BINARY_PATH,
        NULL,
        NULL,
        NULL,
        NULL,
        NULL
    );
    if (g_schBLDrv == NULL)
        cout << "Failed to install driver service : " << GetLastError() << endl;
    else
        cout << "BLDrv installed successfully." << endl;
}

void UninstallDriver()
{
    if (g_schSCManager == NULL)
        if (!OpenSCM())
            return;

    if (g_schBLDrv == NULL)
        if (!OpenBLServ())
            return;

    StopDriver();

    if (DeleteService(g_schBLDrv))
        cout << "BLDrv removed successfully." << endl;
    else
        cout << "Failed to remove BLDrv : " << GetLastError() << endl;  
}

void StartDriver()
{
    if (g_schSCManager == NULL)
        if (!OpenSCM())
            return;

    if (g_schBLDrv == NULL)
        if (!OpenBLServ())
            return;

    if (StartService(g_schBLDrv, 0, NULL))
    {
        cout << "Starting BLDrv..." << endl;

        while (QueryServiceStatus(g_schBLDrv, &g_ssBLServStatus))
        {
            if (g_ssBLServStatus.dwCurrentState == SERVICE_RUNNING)
                break;
            Sleep(2 * MILLISEC);
        }
        cout << "BLDrv started." << endl;
    }
    else
    {
        cout << "Failed to start BLDrv : " << GetLastError() << endl;
    }
}

void StopDriver()
{
    if (g_schSCManager == NULL)
        if (!OpenSCM())
            return;

    if (g_schBLDrv == NULL)
        if (!OpenBLServ())
            return;

    if (ControlService(g_schBLDrv, SERVICE_CONTROL_STOP, &g_ssBLServStatus))
    {
        cout << "Stopping BLDrv..." << endl;
        while (QueryServiceStatus(g_schBLDrv, &g_ssBLServStatus))
        {
            if (g_ssBLServStatus.dwCurrentState == SERVICE_STOPPED)
                break;
            Sleep(2 * MILLISEC);
        }
        cout << "BLDrv stopped." << endl;
    }
}

void AddBlacklistApp(WCHAR* inparam)
{
    if (g_hDeviceHandle == NULL || g_hDeviceHandle == INVALID_HANDLE_VALUE)
        if (!OpenDeviceHandle())
            return;

    ULONG returnLength = 0;

    if (DeviceIoControl(
        g_hDeviceHandle,
        IOCTL_ADD_BLAPP,
        inparam,
        (wcslen(inparam) + 1) * 2,
        NULL,
        0,
        &returnLength,
        0
    ))
        wcout << "Add Blacklist request sent..." << endl;
    else
        wcout << "Failed to send add blacklist request : " << GetLastError << endl;
}

void RemoveBlacklistApp(WCHAR* inparam)
{
    if (g_hDeviceHandle == NULL)
        if (!OpenDeviceHandle())
            return;

    ULONG returnLength = 0;

    if (DeviceIoControl(
        g_hDeviceHandle,
        IOCTL_REM_BLAPP,
        inparam,
        (wcslen(inparam) + 1) * 2,
        NULL,
        0,
        &returnLength,
        0
    ))
        wcout << "Add Blacklist request sent..." << endl;
    else
        wcout << "Failed to send add blacklist request : " << GetLastError << endl;
}

driver.c:

#include<ntddk.h>
#include<ntstrsafe.h>

#define IOCTL_ADD_BLAPP CTL_CODE(FILE_DEVICE_UNKNOWN, 0x801, METHOD_BUFFERED, FILE_READ_DATA)
#define IOCTL_REM_BLAPP CTL_CODE(FILE_DEVICE_UNKNOWN, 0x802, METHOD_BUFFERED, FILE_READ_DATA)

#define MAX_PATH 255

ULONG g_NotifyRegistered = FALSE;

PDEVICE_OBJECT g_pDeviceObject;

UNICODE_STRING g_usDeviceName = RTL_CONSTANT_STRING(L"\\Device\\BLDev");
UNICODE_STRING g_usSymbolicLink = RTL_CONSTANT_STRING(L"\\DosDevices\\BLDev");


VOID OnProcessCreation(
    PEPROCESS Process,
    HANDLE ProcessId,
    PPS_CREATE_NOTIFY_INFO CreateInfo
)
{
    UNREFERENCED_PARAMETER(Process);
    UNREFERENCED_PARAMETER(ProcessId);

    if (CreateInfo == NULL)
        return;
    if (CreateInfo->ImageFileName == NULL || CreateInfo->CommandLine == NULL)
        return;
    if (CreateInfo->ImageFileName->Buffer == NULL || CreateInfo->CommandLine->Buffer == NULL)
        return;

    DbgPrint("ImageFileName : %wZ \n", CreateInfo->ImageFileName);
    DbgPrint("Commandline   : %wZ \n", CreateInfo->CommandLine);
}


VOID Unload(PDRIVER_OBJECT pDriverObject)
{
    UNREFERENCED_PARAMETER(pDriverObject);

    if (g_NotifyRegistered)
    {
        NTSTATUS status = PsSetCreateProcessNotifyRoutineEx(
            OnProcessCreation,
            TRUE
        );
        switch (status)
        {
        case STATUS_SUCCESS:
            DbgPrint("Process creation notification successfully unregistered.\n");
            break;
        case STATUS_INVALID_PARAMETER:
            DbgPrint("Invalid parameters.\nFailed to unregister for process creation notification.\n");
            status = STATUS_UNSUCCESSFUL;
            break;
        case STATUS_ACCESS_DENIED:
            DbgPrint("Access denied.\nFailed to unregister for process creation notification.\n");
            status = STATUS_UNSUCCESSFUL;
            break;
        }
    }

    IoDeleteSymbolicLink(&g_usSymbolicLink);
    IoDeleteDevice(g_pDeviceObject);
    DbgPrint("Driver unloaded.\n");
}


NTSTATUS DispatchDeviceControl(
    PDEVICE_OBJECT pDeviceObject,
    PIRP pIrp
)
{
    UNREFERENCED_PARAMETER(pDeviceObject);
    NTSTATUS status = STATUS_SUCCESS;

    PIO_STACK_LOCATION pIOStackLoc = IoGetCurrentIrpStackLocation(pIrp);

    size_t returnLength = 0;
    WCHAR wzInParam[MAX_PATH] = L"";
    PVOID buffer = pIrp->AssociatedIrp.SystemBuffer;

    switch (pIOStackLoc->Parameters.DeviceIoControl.IoControlCode)
    {
    case IOCTL_ADD_BLAPP:
        wcsncpy(buffer, wzInParam, MAX_PATH);
        returnLength = (wcsnlen(buffer, MAX_PATH) + 1) * 2;
        DbgPrint("Adding : %wZ\n", wzInParam);
        break;
    case IOCTL_REM_BLAPP:
        wcsncpy(buffer, wzInParam, MAX_PATH);
        returnLength = (wcsnlen(buffer, MAX_PATH) + 1) * 2;
        DbgPrint("Removing : %wZ\n", wzInParam);
        break;
    default:
        status = STATUS_INVALID_PARAMETER;
    }

    pIrp->IoStatus.Status = status;
    pIrp->IoStatus.Information = returnLength;
    IoCompleteRequest(
        pIrp,
        IO_NO_INCREMENT
    );

    return status;
}

VOID OnProcessCreation(
    PEPROCESS Process,
    HANDLE ProcessId,
    PPS_CREATE_NOTIFY_INFO CreateInfo
);

NTSTATUS DriverEntry(
    PDRIVER_OBJECT pDriverObject,
    PUNICODE_STRING pusRegistryPath
)
{
    UNREFERENCED_PARAMETER(pusRegistryPath);

    NTSTATUS status = STATUS_SUCCESS;

    pDriverObject->DriverUnload = Unload;
    pDriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL] = DispatchDeviceControl;

    status = IoCreateDevice(
        pDriverObject,
        0,
        &g_usDeviceName,
        FILE_DEVICE_UNKNOWN,
        FILE_DEVICE_SECURE_OPEN,
        FALSE,
        &g_pDeviceObject
    );
    if (!NT_SUCCESS(status))
    {
        DbgPrint("Failed to createDevice.\n");
        return STATUS_UNSUCCESSFUL;
    }
    else
        DbgPrint("Device created successfully.\n");

    status = IoCreateSymbolicLink(
        &g_usSymbolicLink,
        &g_usDeviceName
    );
    if (!NT_SUCCESS(status))
    {
        DbgPrint("Failed to create symbolic link.\n");
        IoDeleteDevice(g_pDeviceObject);
        return STATUS_UNSUCCESSFUL;
    }
    else
        DbgPrint("Symbolic link created successfully.\n");

    status = PsSetCreateProcessNotifyRoutineEx(
        OnProcessCreation,
        FALSE
    );
    switch (status)
    {
    case STATUS_SUCCESS:
        DbgPrint("Process creation notification successfully registered.\n");
        g_NotifyRegistered = TRUE;
        break;
    case STATUS_INVALID_PARAMETER:
        DbgPrint("Invalid parameters.\nFailed to register for process creation notification.\n");
        status = STATUS_UNSUCCESSFUL;
        break;
    case STATUS_ACCESS_DENIED:
        DbgPrint("Access denied.\nFailed to register for process creation notification.\n");
        status = STATUS_UNSUCCESSFUL;
        break;
    }

    DbgPrint("Driver loaded.\n");
    return STATUS_SUCCESS;
}

1 Ответ

0 голосов
/ 04 июля 2018

вы не инициатор IRP_MJ_CREATE обработчик. вы только делаете

 pDriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL] = DispatchDeviceControl;

и все. как результат был обработчик по умолчанию на IRP_MJ_CREATE, который безоговорочно возвращает STATUS_INVALID_DEVICE_REQUEST. этот код и вернулся в режим пользователя. подсистема win32 преобразует его в ERROR_INVALID_FUNCTION

...