когдапроцессодеялоЗащищать
的时候 比如无法获取其процессручка Разрешения
(OpenProcess
) Или, когда вы не можете получить права доступа на чтение и запись в память, вы можете использовать этот метод для повышения привилегий.
необходимые знания,Понимание структуры системы Windows. Ручка стола.
。
Вы можете просмотреть ссылку на этот блог:
Обработка структуры записи таблицы HANDLE_TABLE_ENTRY
В нем записан участник Права доступа, необходимые для текущего дескриптора.
Структура следующая:
//0x8 bytes (sizeof)
union _HANDLE_TABLE_ENTRY
{
volatile LONG VolatileLowValue; //0x0
LONG LowValue; //0x0
struct
{
struct _HANDLE_TABLE_ENTRY_INFO* volatile InfoTable; //0x0
LONG HighValue; //0x4
union _HANDLE_TABLE_ENTRY* NextFreeHandleEntry; //0x4
struct _EXHANDLE LeafHandleValue; //0x4
};
ULONG Unlocked:1; //0x0
ULONG Attributes:2; //0x0
struct
{
ULONG ObjectPointerBits:29; //0x0
LONG RefCountField; //0x4
ULONG GrantedAccessBits:25; //0x4
ULONG ProtectFromClose:1; //0x4
ULONG NoRightsUpgrade:1; //0x4
};
ULONG RefCnt:5; //0x4
};
Большинство из них состоят из консорциумов, и их основными областями деятельности являются GrantedAccessBits
Поэтому наш подход заключается в том, чтобы сначала получить пониженный в должности дескриптор, а затем изменить разрешения этого дескриптора на
Полные разрешения, то есть 0x1fffff
. После завершения модификации мы можем использовать дескриптор с повышенными правами для выполнения наших операций.
Код основного драйвера очень прост.
следующее:
#include <ntifs.h>
#include <ntddk.h>
typedef union _EXHANDLE
{
struct
{
int TagBits : 2;
int Index : 30;
} u;
void* GenericHandleOverlay;
ULONG_PTR Value;
} EXHANDLE, *PEXHANDLE;
typedef struct _HANDLE_TABLE_ENTRY // Size=16
{
union
{
ULONG_PTR VolatileLowValue; // Size=8 Offset=0
ULONG_PTR LowValue; // Size=8 Offset=0
struct _HANDLE_TABLE_ENTRY_INFO* InfoTable; // Size=8 Offset=0
struct
{
ULONG_PTR Unlocked : 1; // Size=8 Offset=0 BitOffset=0 BitCount=1
ULONG_PTR RefCnt : 16; // Size=8 Offset=0 BitOffset=1 BitCount=16
ULONG_PTR Attributes : 3; // Size=8 Offset=0 BitOffset=17 BitCount=3
ULONG_PTR ObjectPointerBits : 44; // Size=8 Offset=0 BitOffset=20 BitCount=44
};
};
union
{
ULONG_PTR HighValue; // Size=8 Offset=8
struct _HANDLE_TABLE_ENTRY* NextFreeHandleEntry; // Size=8 Offset=8
union _EXHANDLE LeafHandleValue; // Size=8 Offset=8
struct
{
ULONG GrantedAccessBits : 25; // Size=4 Offset=8 BitOffset=0 BitCount=25
ULONG NoRightsUpgrade : 1; // Size=4 Offset=8 BitOffset=25 BitCount=1
ULONG Spare : 6; // Size=4 Offset=8 BitOffset=26 BitCount=6
};
};
ULONG TypeInfo; // Size=4 Offset=12
} HANDLE_TABLE_ENTRY, *PHANDLE_TABLE_ENTRY;
typedef struct _HANDLE_TABLE
{
ULONG NextHandleNeedingPool;
long ExtraInfoPages;
LONG_PTR TableCode;
PEPROCESS QuotaProcess;
LIST_ENTRY HandleTableList;
ULONG UniqueProcessId;
ULONG Flags;
EX_PUSH_LOCK HandleContentionEvent;
EX_PUSH_LOCK HandleTableLock;
// More fields here...
} HANDLE_TABLE, *PHANDLE_TABLE;
typedef BOOLEAN(*EX_ENUMERATE_HANDLE_ROUTINE)(
IN PHANDLE_TABLE HandleTable,
IN PHANDLE_TABLE_ENTRY HandleTableEntry,
IN HANDLE Handle,
IN PVOID EnumParameter
);
#ifdef __cplusplus
extern "C"
{
#endif
BOOLEAN NTAPI ExEnumHandleTable(
IN PHANDLE_TABLE HandleTable,
IN EX_ENUMERATE_HANDLE_ROUTINE EnumHandleProcedure,
IN PVOID EnumParameter,
OUT PHANDLE Handle);
VOID FASTCALL ExfUnblockPushLock(
IN OUT PEX_PUSH_LOCK PushLock,
IN OUT PVOID WaitBlock
);
#ifdef __cplusplus
}
#endif
typedef struct _HANDLE_INFO
{
unsigned long process_id;
unsigned long access;
unsigned long long handle;
}HANDLE_INFO, *PHANDLE_INFO;
unsigned char callback(
PHANDLE_TABLE pHandleTableAddress,
PHANDLE_TABLE_ENTRY pHandleTableEntryInfo,
HANDLE Handle,
PVOID pContext)
{
#define ExpIsValidObjectEntry(Entry) ( (Entry) && (Entry->LowValue != 0) && (Entry->HighValue != -2) )
unsigned char result = 0;
if (MmIsAddressValid(pContext))
{
PHANDLE_INFO info = (PHANDLE_INFO)pContext;
if (info->handle == (unsigned long long)Handle
&& MmIsAddressValid(pHandleTableEntryInfo)
&& ExpIsValidObjectEntry(pHandleTableEntryInfo)
&& pHandleTableEntryInfo->GrantedAccessBits != info->access)
{
pHandleTableEntryInfo->GrantedAccessBits = info->access;
result = 1;
}
}
if (pHandleTableEntryInfo) _InterlockedExchangeAdd8((char*)&pHandleTableEntryInfo->VolatileLowValue, 1);
if (pHandleTableAddress && pHandleTableAddress->HandleContentionEvent) ExfUnblockPushLock(&pHandleTableAddress->HandleContentionEvent, NULL);
return result;
}
void handleUpdateAccess(HANDLE_INFO info)
{
PEPROCESS process{ 0 };
NTSTATUS status = PsLookupProcessByProcessId((HANDLE)info.process_id, &process);
if (NT_SUCCESS(status))
{
//dt _EPROCESS find ObjectTable offset replace ox418 of offset
PHANDLE_TABLE table_ptr = *(PHANDLE_TABLE*)((PUCHAR)process + 0x418);
if (MmIsAddressValid(table_ptr)) ExEnumHandleTable(table_ptr, &callback, &info, NULL);
ObDereferenceObject(process);
}
}
VOID DriverUnload(PDRIVER_OBJECT)
{
}
EXTERN_C
NTSTATUS
DriverEntry(
PDRIVER_OBJECT driver,
PUNICODE_STRING)
{
driver->DriverUnload = DriverUnload;
HANDLE_INFO info{ 0 };
info.process_id = 6288; //PID процесса, который необходимо повысить
info.access = 0x1fffff; //Установить все разрешения
info.handle = 0xA4; //Повышаем права процесса, чтобы получить дескриптор Разрешения
handleUpdateAccess(info);
return STATUS_SUCCESS;
}
Демонстрационный пример на уровне пользователя:
// ShutDownProtectProcess.cpp : Этот файл содержит "main" функция. Выполнение программы начнется и закончится здесь.
//
#include <windows.h>
#include <iostream>
using namespace std;
int main()
{
//Вы можете получить более низкий уровень Разрешения Например: PROCESS_QUERY_INFORMATION.
HANDLE hProcess = OpenProcess(PROCESS_TERMINATE, FALSE, 7652);
BOOL bRet = FALSE;
cout << "HANDLE = " << hex << hProcess << endl;
cout << "Start Terminate Process " << endl;
bRet = TerminateProcess(hProcess,0);
if (bRet == FALSE)
{
cout << "TerminateProcess Error try two Terminate" << endl;
system("pause"); //Подождите, пока будет установлен файл Ядро для обновления Разрешения, затем нажмите любую клавишу, чтобы продолжить
bRet = TerminateProcess(hProcess, 0);
if (bRet == FALSE)
{
cout << "Two TerminateProcess Error " << endl;
system("pause");
return 0;
}
{
cout << "Two TerminateProcess Success " << endl;
system("pause");
return 0;
}
}
else
{
cout << "one TerminateProcess Success " << endl;
system("pause");
return 0;
}
system("pause");
return 0;
}
Потому что я не инкапсулировал связь с ядром. Поэтому после запуска программы USER она будет ждать, пока пользователь вручную установит драйвер.
PID в драйвере необходимо изменить на идентификатор программы USER, а HANDLE, полученный пользователем, необходимо распечатать и изменить в драйвере.
Затем перекомпилируйте драйвер и установите его. После установки ручка будет поднята. В это время пользовательская программа продолжает работать, завершая работу защищенной программы блокнота.
#include <ntifs.h>
#include <ntstrsafe.h>
#define PROCESS_TERMINATE (0x0001) // winnt
#define PROCESS_CREATE_THREAD (0x0002) // winnt
#define PROCESS_SET_SESSIONID (0x0004) // winnt
#define PROCESS_VM_OPERATION (0x0008) // winnt
#define PROCESS_VM_READ (0x0010) // winnt
#define PROCESS_VM_WRITE (0x0020) // winnt
// begin_ntddk begin_wdm begin_ntifs
#define PROCESS_DUP_HANDLE (0x0040) // winnt
// end_ntddk end_wdm end_ntifs
#define PROCESS_CREATE_PROCESS (0x0080) // winnt
#define PROCESS_SET_QUOTA (0x0100) // winnt
#define PROCESS_SET_INFORMATION (0x0200) // winnt
#define PROCESS_QUERY_INFORMATION (0x0400) // winnt
#define PROCESS_SET_PORT (0x0800)
#define PROCESS_SUSPEND_RESUME (0x0800) // winnt
PVOID g_ObjHandle;
extern "C" NTKERNELAPI
UCHAR * PsGetProcessImageFileName(__in PEPROCESS Process);
OB_PREOP_CALLBACK_STATUS MyObjectCallBack(
PVOID RegistrationContext,
POB_PRE_OPERATION_INFORMATION OperationInformation
)
{
UNREFERENCED_PARAMETER(RegistrationContext);
PEPROCESS pProcess = NULL;
CHAR *pszName = NULL;
pProcess = (PEPROCESS)OperationInformation->Object;
pszName = (CHAR*)PsGetProcessImageFileName(pProcess);
//Определяем, следует ли открывать флаг процесса
if (OperationInformation->Operation == OB_OPERATION_HANDLE_CREATE)
{
//Получаем совпадение имен
if (strstr(pszName, (CHAR*)"notepad"))
{
KdPrint(("%s \r\n", pszName));
//Определяем, закончилось ли это
if ((OperationInformation->Parameters->CreateHandleInformation.OriginalDesiredAccess
& PROCESS_TERMINATE) == 1)
{
//Если оно наше, ставим DesiredAccess Разрешения. Убираем конец Разрешения.
OperationInformation->Parameters->CreateHandleInformation.DesiredAccess
= (ULONG)~PROCESS_TERMINATE;
return OB_PREOP_SUCCESS;
}
}
}
return OB_PREOP_SUCCESS;
}
VOID InitHook()
{
//Выполняем КРЮК Как написать перехватчики обратного вызова.
OB_OPERATION_REGISTRATION oper; //Ваша функция обратного вызова и ее тип помещаются в эту структуру, которая может представлять собой массив структур.
OB_CALLBACK_REGISTRATION CallbackRegistration;
CallbackRegistration.Version = OB_FLT_REGISTRATION_VERSION; //номер версии
CallbackRegistration.OperationRegistrationCount = 1;//Следующие несколько перехватчиков, то есть количество массивов структур
RtlUnicodeStringInit(&CallbackRegistration.Altitude, L"600000");//Укажите строку UNICODE, чтобы указать, что вы делаете
CallbackRegistration.RegistrationContext = NULL; //Каковы параметры при поступлении вашей функции обратного вызова? Здесь указано.
CallbackRegistration.OperationRegistration = &oper; //Настройка типа структуры крючка.
//Присвоение значения структуре перехвата
oper.ObjectType = PsProcessType; //Тип процессной операции. Когда процессная операция возвращается. PsThreadType — операция потока.
oper.Operations = OB_OPERATION_HANDLE_CREATE; //Тип операции должен быть открыт и повторен.
oper.PreOperation = MyObjectCallBack; //Есть два указателя: передний указатель и задний указатель. Значения такие. Будете ли вы проинформированы до или после создания процесса?
oper.PostOperation = NULL;
ObRegisterCallbacks(&CallbackRegistration, &g_ObjHandle);
}
VOID UnHook()
{
ObUnRegisterCallbacks(g_ObjHandle);
}
VOID
DriverUnLoad(
_In_ struct _DRIVER_OBJECT *DriverObject
)
{
UNREFERENCED_PARAMETER(DriverObject);
UnHook();
}
typedef struct _LDR_DATA_TABLE_ENTRY {
LIST_ENTRY64 InLoadOrderLinks;
LIST_ENTRY64 InMemoryOrderLinks;
LIST_ENTRY64 InInitializationOrderLinks;
PVOID DllBase;
PVOID EntryPoint;
ULONG SizeOfImage;
UNICODE_STRING FullDllName;
UNICODE_STRING BaseDllName;
ULONG Flags;
USHORT LoadCount;
USHORT TlsIndex;
PVOID SectionPointer;
ULONG CheckSum;
PVOID LoadedImports;
PVOID EntryPointActivationContext;
PVOID PatchInformation;
LIST_ENTRY64 ForwarderLinks;
LIST_ENTRY64 ServiceTagLinks;
LIST_ENTRY64 StaticLinks;
PVOID ContextInformation;
ULONG OriginalBase;
LARGE_INTEGER LoadTime;
} LDR_DATA_TABLE_ENTRY, *PLDR_DATA_TABLE_ENTRY;
extern "C" NTSTATUS DriverEntry(PDRIVER_OBJECT pDriverObj, PUNICODE_STRING pRegPath)
{
UNREFERENCED_PARAMETER(pRegPath);
PLDR_DATA_TABLE_ENTRY ldr;
ldr = (PLDR_DATA_TABLE_ENTRY)pDriverObj->DriverSection;
ldr->Flags |= 0x20;
pDriverObj->DriverUnload = DriverUnLoad;
InitHook();
return STATUS_SUCCESS;
}
//Относительно полный код
#define PROCESS_TERMINATE (0x0001)
#define PROCESS_CREATE_THREAD (0x0002)
#define PROCESS_SET_SESSIONID (0x0004)
#define PROCESS_VM_OPERATION (0x0008)
#define PROCESS_VM_READ (0x0010)
#define PROCESS_VM_WRITE (0x0020)
#define PROCESS_DUP_HANDLE (0x0040)
#define PROCESS_CREATE_PROCESS (0x0080)
#define PROCESS_SET_QUOTA (0x0100)
#define PROCESS_SET_INFORMATION (0x0200)
#define PROCESS_QUERY_INFORMATION (0x0400)
#define PROCESS_SUSPEND_RESUME (0x0800)
#define PROCESS_QUERY_LIMITED_INFORMATION (0x1000)
#define PROCESS_SET_LIMITED_INFORMATION (0x2000)
Примечание. Удаление: ObUnRegisterCallbacks (obHandle);
NTSTATUS ProtectProcess()
{
OB_CALLBACK_REGISTRATION obReg;
OB_OPERATION_REGISTRATION opReg;
memset(&obReg, 0, sizeof(obReg));
obReg.Version = ObGetFilterVersion();
obReg.OperationRegistrationCount = 1;
obReg.RegistrationContext = NULL;
RtlInitUnicodeString(&obReg.Altitude, L"321000");
memset(&opReg, 0, sizeof(opReg));
opReg.ObjectType = PsProcessType;
opReg.Operations = OB_OPERATION_HANDLE_CREATE | OB_OPERATION_HANDLE_DUPLICATE;
opReg.PreOperation = (POB_PRE_OPERATION_CALLBACK)&preCall;
obReg.OperationRegistration = &opReg;
return ObRegisterCallbacks(&obReg, &obHandle);
}
OB_PREOP_CALLBACK_STATUS preCall(PVOID RegistrationContext, POB_PRE_OPERATION_INFORMATION pOperationInformation)
{
HANDLE pid = PsGetProcessId((PEPROCESS)pOperationInformation->Object);
if (pid == PID)
{
if (pOperationInformation->Operation == OB_OPERATION_HANDLE_CREATE)
{
if (pOperationInformation->Parameters->CreateHandleInformation.DesiredAccess & PROCESS_TERMINATE)
pOperationInformation->Parameters->CreateHandleInformation.DesiredAccess &= (~PROCESS_TERMINATE);
if (pOperationInformation->Parameters->CreateHandleInformation.DesiredAccess & PROCESS_VM_OPERATION)
pOperationInformation->Parameters->CreateHandleInformation.DesiredAccess &= (~PROCESS_VM_OPERATION);
if (pOperationInformation->Parameters->CreateHandleInformation.DesiredAccess & PROCESS_VM_READ)
pOperationInformation->Parameters->CreateHandleInformation.DesiredAccess &= (~PROCESS_VM_READ);
if (pOperationInformation->Parameters->CreateHandleInformation.DesiredAccess & PROCESS_VM_WRITE)
pOperationInformation->Parameters->CreateHandleInformation.DesiredAccess &= (~PROCESS_VM_WRITE);
if (pOperationInformation->Parameters->CreateHandleInformation.DesiredAccess & PROCESS_SUSPEND_RESUME)
pOperationInformation->Parameters->CreateHandleInformation.DesiredAccess &= (~PROCESS_SUSPEND_RESUME);
}
if (pOperationInformation->Operation == OB_OPERATION_HANDLE_DUPLICATE)
{
if (pOperationInformation->Parameters->DuplicateHandleInformation.DesiredAccess & PROCESS_TERMINATE)
pOperationInformation->Parameters->DuplicateHandleInformation.DesiredAccess &= (~PROCESS_TERMINATE);
if (pOperationInformation->Parameters->DuplicateHandleInformation.DesiredAccess & PROCESS_VM_OPERATION)
pOperationInformation->Parameters->DuplicateHandleInformation.DesiredAccess &= (~PROCESS_VM_OPERATION);
if (pOperationInformation->Parameters->DuplicateHandleInformation.DesiredAccess & PROCESS_VM_READ)
pOperationInformation->Parameters->DuplicateHandleInformation.DesiredAccess &= (~PROCESS_VM_READ);
if (pOperationInformation->Parameters->DuplicateHandleInformation.DesiredAccess & PROCESS_VM_WRITE)
pOperationInformation->Parameters->DuplicateHandleInformation.DesiredAccess &= (~PROCESS_VM_WRITE);
if (pOperationInformation->Parameters->DuplicateHandleInformation.DesiredAccess & PROCESS_SUSPEND_RESUME)
pOperationInformation->Parameters->DuplicateHandleInformation.DesiredAccess &= (~PROCESS_SUSPEND_RESUME);
}
}
return OB_PREOP_SUCCESS;
}
Фактически этот код реализован в BlockBone.
кодследующее:
Сначала определите необходимую структуру
#define EX_ADDITIONAL_INFO_SIGNATURE (ULONG_PTR)(-2)
typedef union _EXHANDLE
{
struct
{
int TagBits : 2;
int Index : 30;
} u;
void * GenericHandleOverlay;
ULONG_PTR Value;
} EXHANDLE, *PEXHANDLE;
typedef struct _HANDLE_TABLE
{
ULONG NextHandleNeedingPool;
long ExtraInfoPages;
LONG_PTR TableCode;
PEPROCESS QuotaProcess;
LIST_ENTRY HandleTableList;
ULONG UniqueProcessId;
ULONG Flags;
EX_PUSH_LOCK HandleContentionEvent;
EX_PUSH_LOCK HandleTableLock;
// More fields here...
} HANDLE_TABLE, *PHANDLE_TABLE;
typedef struct _HANDLE_TABLE_ENTRY // Size=16
{
union
{
ULONG_PTR VolatileLowValue; // Size=8 Offset=0
ULONG_PTR LowValue; // Size=8 Offset=0
struct _HANDLE_TABLE_ENTRY_INFO * InfoTable; // Size=8 Offset=0
struct
{
ULONG_PTR Unlocked : 1; // Size=8 Offset=0 BitOffset=0 BitCount=1
ULONG_PTR RefCnt : 16; // Size=8 Offset=0 BitOffset=1 BitCount=16
ULONG_PTR Attributes : 3; // Size=8 Offset=0 BitOffset=17 BitCount=3
ULONG_PTR ObjectPointerBits : 44; // Size=8 Offset=0 BitOffset=20 BitCount=44
};
};
union
{
ULONG_PTR HighValue; // Size=8 Offset=8
struct _HANDLE_TABLE_ENTRY * NextFreeHandleEntry; // Size=8 Offset=8
union _EXHANDLE LeafHandleValue; // Size=8 Offset=8
struct
{
ULONG GrantedAccessBits : 25; // Size=4 Offset=8 BitOffset=0 BitCount=25
ULONG NoRightsUpgrade : 1; // Size=4 Offset=8 BitOffset=25 BitCount=1
ULONG Spare : 6; // Size=4 Offset=8 BitOffset=26 BitCount=6
};
};
ULONG TypeInfo; // Size=4 Offset=12
} HANDLE_TABLE_ENTRY, *PHANDLE_TABLE_ENTRY;
/// <summary>
/// Input for IOCTL_BLACKBONE_GRANT_ACCESS
/// </summary>
typedef struct _HANDLE_GRANT_ACCESS
{
ULONGLONG handle; // Handle to modify
ULONG pid; // Process ID
ULONG access; // Access flags to grant
} HANDLE_GRANT_ACCESS, *PHANDLE_GRANT_ACCESS;
#define IOCTL_BLACKBONE_GRANT_ACCESS (ULONG)CTL_CODE(FILE_DEVICE_BLACKBONE, 0x802, METHOD_BUFFERED, FILE_READ_ACCESS | FILE_WRITE_ACCESS)
#define STATUS_WAIT_0 ((NTSTATUS)0x00000000L) // winnt
typedef BOOLEAN(*EX_ENUMERATE_HANDLE_ROUTINE)(
#if !defined(_WIN7_)
IN PHANDLE_TABLE HandleTable,
#endif
IN PHANDLE_TABLE_ENTRY HandleTableEntry,
IN HANDLE Handle,
IN PVOID EnumParameter
);
extern "C" NTKERNELAPI
BOOLEAN
ExEnumHandleTable(
IN PHANDLE_TABLE HandleTable,
IN EX_ENUMERATE_HANDLE_ROUTINE EnumHandleProcedure,
IN PVOID EnumParameter,
OUT PHANDLE Handle
);
extern "C" NTKERNELAPI
VOID
FASTCALL
ExfUnblockPushLock(
IN OUT PEX_PUSH_LOCK PushLock,
IN OUT PVOID WaitBlock
);
#define ExpIsValidObjectEntry(Entry) \
( (Entry != NULL) && (Entry->LowValue != 0) && (Entry->HighValue != EX_ADDITIONAL_INFO_SIGNATURE) )
Основной код следующий:
/// <summary>
/// Check if process is terminating
/// </summary>
/// <param name="imageBase">Process</param>
/// <returns>If TRUE - terminating</returns>
BOOLEAN BBCheckProcessTermination(PEPROCESS pProcess)
{
LARGE_INTEGER zeroTime = { 0 };
return KeWaitForSingleObject(pProcess, Executive, KernelMode, FALSE, &zeroTime) == STATUS_WAIT_0;
}
/// <summary>
/// Handle enumeration callback
/// </summary>
/// <param name="HandleTable">Process handle table</param>
/// <param name="HandleTableEntry">Handle entry</param>
/// <param name="Handle">Handle value</param>
/// <param name="EnumParameter">User context</param>
/// <returns>TRUE when desired handle is found</returns>
BOOLEAN BBHandleCallback(
#if !defined(_WIN7_)
IN PHANDLE_TABLE HandleTable,
#endif
IN PHANDLE_TABLE_ENTRY HandleTableEntry,
IN HANDLE Handle,
IN PVOID EnumParameter
)
{
BOOLEAN result = FALSE;
ASSERT(EnumParameter);
if (EnumParameter != NULL)
{
PHANDLE_GRANT_ACCESS pAccess = (PHANDLE_GRANT_ACCESS)EnumParameter;
if (Handle == (HANDLE)pAccess->handle)
{
if (ExpIsValidObjectEntry(HandleTableEntry))
{
// Update access
HandleTableEntry->GrantedAccessBits = pAccess->access;
result = TRUE;
}
else
{
}
}
}
#if !defined(_WIN7_)
// Release implicit locks
_InterlockedExchangeAdd8((char*)&HandleTableEntry->VolatileLowValue, 1); // Set Unlocked flag to 1
if (HandleTable != NULL && HandleTable->HandleContentionEvent)
ExfUnblockPushLock(&HandleTable->HandleContentionEvent, NULL);
#endif
return result;
}
/// <summary>
/// Change handle granted access
/// </summary>
/// <param name="pAccess">Request params</param>
/// <returns>Status code</returns>
NTSTATUS BBGrantAccess(IN PHANDLE_GRANT_ACCESS pAccess)
{
NTSTATUS status = STATUS_SUCCESS;
PEPROCESS pProcess = NULL;
status = PsLookupProcessByProcessId((HANDLE)pAccess->pid, &pProcess);
if (NT_SUCCESS(status) && BBCheckProcessTermination(pProcess))
status = STATUS_PROCESS_IS_TERMINATING;
if (NT_SUCCESS(status))
{
PHANDLE_TABLE pTable = *(PHANDLE_TABLE*)((PUCHAR)pProcess + 0x418);/*Найдите смещение OBJECTTABLE каждого EPROCESS в соответствии с системой*/
BOOLEAN found = ExEnumHandleTable(pTable, &BBHandleCallback, pAccess, NULL);
if (found == FALSE)
status = STATUS_NOT_FOUND;
}
else
{
}
if (pProcess)
ObDereferenceObject(pProcess);
return status;
}
Используйте тот же метод, что и выше. Вы можете указать процесс, а затем указать дескриптор этого процесса, чтобы повысить привилегии этого дескриптора.
Сначала вы можете увидеть РУЧКУ, а затем закрыть блокнот в первый раз. Поскольку драйвер защиты загружен, первое закрытие блокнота не удается.
Затем попробуйте закрыть блокнот во второй раз. В это время пользователю будет предложено нажать любую клавишу для продолжения. Ожидая нажатия любой клавиши, сначала загрузите драйвер повышения привилегий. пользовательскую программу и нажмите любую клавишу, чтобы продолжить.
Продолжение завершит защищенный процесс.
Эта статья демонстрирует это обычным способом. Если вы знаете принцип, вы сможете совершить прорыв самостоятельно. (Внедрение виртуальных разрешений, у которых нет разрешений на открытие и разрешений на запись, затем вы можете повысить привилегии, а затем использовать авторизованный дескриптор для работы.)