Базовое управление процессами в ядре Windows

Я изучаю программирование ядра Windows и сосредотачиваюсь на написании чистого кода C, который правильно обрабатывает и распространяет ошибки. Следующий фрагмент кода довольно прост, но я хотел бы получить отзывы о нем, прежде чем применять этот интерфейс и стиль кодирования к остальной части кода.

Приведенный ниже код отвечает за инициализацию объектов процесса, чтение и запись в их памяти и их очистку.

process.h:

#pragma once

#include <ntdef.h>
#include <ntifs.h>

typedef enum  {
    EProcessSuccess,
    EProcessInvalid, 
    EProcessInvalidArgs,
    EProcessAccessDenied,
    EProcessFail
} EProcessStatus;

#define PROCESS_STATUS_SUCCESS(EValue) (EValue == EProcessSuccess)

typedef struct _Process {
    HANDLE id;
    PEPROCESS process;
    BOOLEAN initialized;
} Process;

EProcessStatus processInit(HANDLE processId, Process* process);
EProcessStatus processDestroy(Process* process);
EProcessStatus processReadMemory(Process* process, PVOID sourceAddress, PVOID targetAddress, SIZE_T size);
EProcessStatus processWriteMemory(Process* process, PVOID sourceAddress, PVOID targetAddress, SIZE_T size);
EProcessStatus processGetId(Process* process, HANDLE* id);

process.c

#include "process.h"

#include "log.h"

NTSTATUS NTAPI MmCopyVirtualMemory(
    PEPROCESS SourceProcess,
    PVOID sourceAddress,
    PEPROCESS TargetProcess,
    PVOID targetAddress,
    SIZE_T BufferSize,
    KPROCESSOR_MODE PreviousMode,
    PSIZE_T ReturnSize
);

void printErrorRW(char* msg, HANDLE id, NTSTATUS status, PVOID address, SIZE_T size) {
    DEBUG_LOG("[ERROR] %s - %x n", msg, status);
    DEBUG_LOG("ttProcess: %pn", id);
    DEBUG_LOG("ttSourceAddress: %pn", address);
    DEBUG_LOG("ttBytes: %pn", size);
}

BOOLEAN isValid(Process* process) {
    return process && process->initialized;
}

EProcessStatus processInit(HANDLE processId, Process* process) {
    DEBUG_VERBOSE("Create process with PID %dn", processId);

    if (process == NULL) {
        DEBUG_LOG("[ERROR] Can't initialize NULL Process.n");
        return EProcessInvalid;
    }

    process->id = processId;
    process->initialized = NT_SUCCESS(PsLookupProcessByProcessId(processId, &process->process));

    if (!process->initialized) {
        DEBUG_LOG("[ERROR] Unable to initialize process with PID %dn", processId);
        return EProcessInvalid;
    }
    return EProcessSuccess;
}

EProcessStatus processDestroy(Process* process) {
    if (isValid(process) && process->initialized) {
        ObDereferenceObject(process->process);
    }
    
    return EProcessSuccess;
}

EProcessStatus processReadMemory(Process* process, PVOID sourceAddress, PVOID targetAddress, SIZE_T size) {

    if (!isValid(process)) {
        DEBUG_LOG("[ERROR] Can't read memory from invalid processn");
        return EProcessInvalid;
    }

    DEBUG_VERBOSE("Read memory from process %d at address %pn", process->id, sourceAddress);

    SIZE_T Bytes = 0;
    NTSTATUS Status = STATUS_SUCCESS;

    __try
    {
        Status = MmCopyVirtualMemory(process->process, sourceAddress, PsGetCurrentProcess(), targetAddress, size, KernelMode, &Bytes);

        if (!NT_SUCCESS(Status))
        {
            printErrorRW("readMemory", process->id, Status, sourceAddress, Bytes);
            return EProcessFail;
        }
        return EProcessSuccess;
    }
    __except (EXCEPTION_EXECUTE_HANDLER)
    {
        printErrorRW("readMemory exception", process->id, Status, sourceAddress, Bytes);
        return EProcessAccessDenied;
    }
}

EProcessStatus processWriteMemory(Process* process, PVOID sourceAddress, PVOID targetAddress, SIZE_T size) {
    if (!isValid(process)) {
        DEBUG_LOG("[ERROR] Can't write memory from invalid processn");
        return EProcessInvalid;
    }

    DEBUG_VERBOSE("Write memory from process %d at address %pn", process->id, sourceAddress);

    SIZE_T Bytes = 0;
    NTSTATUS Status = STATUS_SUCCESS;

    __try
    {
        Status = MmCopyVirtualMemory(PsGetCurrentProcess(), sourceAddress, process->process, targetAddress, size, KernelMode, &Bytes);

        if (!NT_SUCCESS(Status))
        {
            printErrorRW("writeMemory", process->id, Status, sourceAddress, Bytes);
            return EProcessFail;
        }
        return EProcessSuccess;
    }
    __except (EXCEPTION_EXECUTE_HANDLER)
    {
        printErrorRW("writeMemory exception", process->id, Status, sourceAddress, Bytes);
        return EProcessAccessDenied;
    }
}

EProcessStatus processGetId(Process* process, HANDLE* id) {
    if (process == NULL) {
        DEBUG_LOG("[ERROR] Can't get PID of invalid processn");
        return EProcessInvalid;
    }
    if (id == NULL) {
        DEBUG_LOG("[ERROR] processGetId - NULL id pointern");
        return EProcessInvalidArgs;
    }
    *id = process->id;
    return EProcessSuccess;
}

Спасибо за ваше время.

0

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *