mirror of
https://github.com/momo5502/emulator.git
synced 2026-01-19 11:43:56 +00:00
Prepare handle cleanup
This commit is contained in:
@@ -344,9 +344,9 @@ namespace
|
||||
proc_params.Length = sizeof(proc_params);
|
||||
proc_params.Flags = 0x6001 | 0x80000000; // Prevent CsrClientConnectToServer
|
||||
|
||||
proc_params.ConsoleHandle = reinterpret_cast<HANDLE>(CONSOLE_HANDLE);
|
||||
proc_params.StandardOutput = reinterpret_cast<HANDLE>(STDOUT_HANDLE);
|
||||
proc_params.StandardInput = reinterpret_cast<HANDLE>(STDIN_HANDLE);
|
||||
proc_params.ConsoleHandle = CONSOLE_HANDLE.h;
|
||||
proc_params.StandardOutput = STDOUT_HANDLE.h;
|
||||
proc_params.StandardInput = STDIN_HANDLE.h;
|
||||
proc_params.StandardError = proc_params.StandardOutput;
|
||||
|
||||
gs.make_unicode_string(proc_params.CurrentDirectory.DosPath, L"C:\\Users\\mauri\\Desktop");
|
||||
@@ -714,7 +714,6 @@ namespace
|
||||
|
||||
const auto allocation_size = combined_size + mach_frame_size;
|
||||
|
||||
|
||||
const auto initial_sp = emu.reg(x64_register::rsp);
|
||||
const auto new_sp = align_down(initial_sp - allocation_size, 0x100);
|
||||
|
||||
|
||||
@@ -224,36 +224,38 @@ namespace
|
||||
NTSTATUS handle_NtSetEvent(const syscall_context& c, const uint64_t handle,
|
||||
const emulator_object<LONG> previous_state)
|
||||
{
|
||||
if (handle & EVENT_BIT)
|
||||
const auto value = get_handle_value(handle);
|
||||
if (value.type != handle_types::event)
|
||||
{
|
||||
const auto event_index = static_cast<uint32_t>(handle & ~EVENT_BIT);
|
||||
const auto entry = c.proc.events.find(event_index);
|
||||
if (entry != c.proc.events.end())
|
||||
{
|
||||
if (previous_state.value())
|
||||
{
|
||||
previous_state.write(entry->second.signaled ? 1ULL : 0ULL);
|
||||
}
|
||||
|
||||
entry->second.signaled = true;
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
return STATUS_INVALID_HANDLE;
|
||||
}
|
||||
|
||||
return STATUS_INVALID_HANDLE;
|
||||
const auto entry = c.proc.events.find(value.id);
|
||||
if (entry == c.proc.events.end())
|
||||
{
|
||||
return STATUS_INVALID_HANDLE;
|
||||
}
|
||||
|
||||
if (previous_state.value())
|
||||
{
|
||||
previous_state.write(entry->second.signaled ? 1ULL : 0ULL);
|
||||
}
|
||||
|
||||
entry->second.signaled = true;
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
NTSTATUS handle_NtClose(const syscall_context& c, const uint64_t handle)
|
||||
{
|
||||
if (handle & PSEUDO_BIT)
|
||||
const auto value = get_handle_value(handle);
|
||||
if (value.is_pseudo)
|
||||
{
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
if (handle & EVENT_BIT)
|
||||
if (value.type == handle_types::event)
|
||||
{
|
||||
const auto event_index = static_cast<uint32_t>(handle & ~EVENT_BIT);
|
||||
const auto entry = c.proc.events.find(event_index);
|
||||
const auto entry = c.proc.events.find(value.id);
|
||||
if (entry != c.proc.events.end())
|
||||
{
|
||||
c.proc.events.erase(entry);
|
||||
@@ -261,10 +263,9 @@ namespace
|
||||
}
|
||||
}
|
||||
|
||||
if (handle & FILE_BIT)
|
||||
if (value.type == handle_types::file)
|
||||
{
|
||||
const auto event_index = static_cast<uint32_t>(handle & ~FILE_BIT);
|
||||
const auto entry = c.proc.files.find(event_index);
|
||||
const auto entry = c.proc.files.find(value.id);
|
||||
if (entry != c.proc.files.end())
|
||||
{
|
||||
c.proc.files.erase(entry);
|
||||
@@ -305,7 +306,8 @@ namespace
|
||||
}
|
||||
}
|
||||
|
||||
event_handle.write(index | EVENT_BIT);
|
||||
const auto h = make_handle(index, handle_types::event, false);
|
||||
event_handle.write(h.bits);
|
||||
|
||||
c.proc.events.try_emplace(index, initial_state != FALSE, event_type);
|
||||
|
||||
@@ -354,7 +356,8 @@ namespace
|
||||
}
|
||||
}
|
||||
|
||||
file_handle.write(index | FILE_BIT);
|
||||
const auto h = make_handle(index, handle_types::file, false);
|
||||
file_handle.write(h.bits);
|
||||
|
||||
auto status = STATUS_SUCCESS;
|
||||
object_attributes.access([&](const OBJECT_ATTRIBUTES& attributes)
|
||||
@@ -384,7 +387,7 @@ namespace
|
||||
|
||||
if (filename == L"\\Windows\\SharedSection")
|
||||
{
|
||||
section_handle.write(SHARED_SECTION);
|
||||
section_handle.write(SHARED_SECTION.bits);
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
@@ -395,7 +398,6 @@ namespace
|
||||
return STATUS_NOT_SUPPORTED;
|
||||
}
|
||||
|
||||
|
||||
if (filename.starts_with(L"api-ms-"))
|
||||
{
|
||||
filename = L"C:\\WINDOWS\\System32\\downlevel\\" + filename;
|
||||
@@ -419,7 +421,8 @@ namespace
|
||||
}
|
||||
}
|
||||
|
||||
section_handle.write(index | FILE_BIT);
|
||||
const auto h = make_handle(index, handle_types::file, false);
|
||||
section_handle.write(h.bits);
|
||||
|
||||
c.proc.files.try_emplace(index, std::move(filename));
|
||||
|
||||
@@ -438,13 +441,13 @@ namespace
|
||||
return STATUS_INVALID_HANDLE;
|
||||
}
|
||||
|
||||
if (!(section_handle & FILE_BIT))
|
||||
const auto value = get_handle_value(section_handle);
|
||||
if (value.type != handle_types::file)
|
||||
{
|
||||
return STATUS_INVALID_HANDLE;
|
||||
}
|
||||
|
||||
const auto section_index = static_cast<uint32_t>(section_handle & ~FILE_BIT);
|
||||
const auto section_entry = c.proc.files.find(section_index);
|
||||
const auto section_entry = c.proc.files.find(value.id);
|
||||
if (section_entry == c.proc.files.end())
|
||||
{
|
||||
return STATUS_INVALID_HANDLE;
|
||||
@@ -870,7 +873,7 @@ namespace
|
||||
|
||||
if (object_name == L"\\KnownDlls")
|
||||
{
|
||||
directory_handle.write(KNOWN_DLLS_DIRECTORY);
|
||||
directory_handle.write(KNOWN_DLLS_DIRECTORY.bits);
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
@@ -886,7 +889,7 @@ namespace
|
||||
|
||||
if (object_name == L"KnownDllPath")
|
||||
{
|
||||
link_handle.write(KNOWN_DLLS_SYMLINK);
|
||||
link_handle.write(KNOWN_DLLS_SYMLINK.bits);
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
@@ -1023,7 +1026,7 @@ namespace
|
||||
puts("NtCreateSection not supported");
|
||||
c.emu.stop();
|
||||
|
||||
section_handle.write(SHARED_SECTION);
|
||||
section_handle.write(SHARED_SECTION.bits);
|
||||
/*
|
||||
maximum_size.access([](LARGE_INTEGER& large_int)
|
||||
{
|
||||
@@ -1139,14 +1142,15 @@ namespace
|
||||
|
||||
if (filename == L"\\Device\\ConDrv\\Server")
|
||||
{
|
||||
file_handle.write(CONSOLE_SERVER);
|
||||
file_handle.write(CONSOLE_SERVER.bits);
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
const auto root_handle = reinterpret_cast<uint64_t>(attributes.RootDirectory);
|
||||
if ((root_handle & PSEUDO_BIT) && (filename == L"\\Reference" || filename == L"\\Connect"))
|
||||
handle root_handle{};
|
||||
root_handle.bits = reinterpret_cast<uint64_t>(attributes.RootDirectory);
|
||||
if (root_handle.value.is_pseudo && (filename == L"\\Reference" || filename == L"\\Connect"))
|
||||
{
|
||||
file_handle.write(root_handle);
|
||||
file_handle.write(root_handle.bits);
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
@@ -3,20 +3,80 @@
|
||||
#include <x64_emulator.hpp>
|
||||
#include "process_context.hpp"
|
||||
|
||||
constexpr uint64_t PSEUDO_BIT = 1ULL << 63ULL;
|
||||
constexpr uint64_t EVENT_BIT = 1ULL << 62ULL;
|
||||
constexpr uint64_t DIRECTORY_BIT = 1ULL << 61ULL;
|
||||
constexpr uint64_t SYMLINK_BIT = 1ULL << 60ULL;
|
||||
constexpr uint64_t FILE_BIT = 1ULL << 59ULL;
|
||||
struct handle_types
|
||||
{
|
||||
enum type : uint16_t
|
||||
{
|
||||
file,
|
||||
event,
|
||||
section,
|
||||
symlink,
|
||||
directory,
|
||||
};
|
||||
};
|
||||
|
||||
constexpr uint64_t KNOWN_DLLS_DIRECTORY = DIRECTORY_BIT | PSEUDO_BIT | 0x1337;
|
||||
constexpr uint64_t KNOWN_DLLS_SYMLINK = SYMLINK_BIT | PSEUDO_BIT | 0x1337;
|
||||
constexpr uint64_t SHARED_SECTION = FILE_BIT | PSEUDO_BIT | 0x1337;
|
||||
constexpr uint64_t CONSOLE_SERVER = FILE_BIT | PSEUDO_BIT | 0x1338;
|
||||
#pragma pack(push)
|
||||
#pragma pack(1)
|
||||
struct handle_value
|
||||
{
|
||||
uint64_t id : 32;
|
||||
uint64_t type : 16;
|
||||
uint64_t padding : 15;
|
||||
uint64_t is_pseudo : 1;
|
||||
};
|
||||
#pragma pack(pop)
|
||||
|
||||
constexpr uint64_t CONSOLE_HANDLE = FILE_BIT | PSEUDO_BIT | 0x01;
|
||||
constexpr uint64_t STDOUT_HANDLE = FILE_BIT | PSEUDO_BIT | 0x02;
|
||||
constexpr uint64_t STDIN_HANDLE = FILE_BIT | PSEUDO_BIT | 0x03;
|
||||
static_assert(sizeof(handle_value) == 8);
|
||||
|
||||
union handle
|
||||
{
|
||||
handle_value value;
|
||||
uint64_t bits;
|
||||
HANDLE h;
|
||||
};
|
||||
|
||||
inline bool operator==(const handle& h1, const handle& h2)
|
||||
{
|
||||
return h1.bits == h2.bits;
|
||||
}
|
||||
|
||||
inline bool operator==(const handle& h1, const uint64_t& h2)
|
||||
{
|
||||
return h1.bits == h2;
|
||||
}
|
||||
|
||||
inline handle_value get_handle_value(const uint64_t h)
|
||||
{
|
||||
handle hh{};
|
||||
hh.bits = h;
|
||||
return hh.value;
|
||||
}
|
||||
|
||||
constexpr handle make_handle(const uint32_t id, const handle_types::type type, const bool is_pseudo)
|
||||
{
|
||||
handle_value value{};
|
||||
|
||||
value.padding = 0;
|
||||
value.id = id;
|
||||
value.type = type;
|
||||
value.is_pseudo = is_pseudo;
|
||||
|
||||
return {value};
|
||||
}
|
||||
|
||||
constexpr handle make_pseudo_handle(const uint32_t id, const handle_types::type type)
|
||||
{
|
||||
return make_handle(id, type, true);
|
||||
}
|
||||
|
||||
constexpr auto KNOWN_DLLS_DIRECTORY = make_pseudo_handle(0x1337, handle_types::directory);
|
||||
constexpr auto KNOWN_DLLS_SYMLINK = make_pseudo_handle(0x1337, handle_types::symlink);
|
||||
constexpr auto SHARED_SECTION = make_pseudo_handle(0x1337, handle_types::section);
|
||||
constexpr auto CONSOLE_SERVER = make_pseudo_handle(0x1337, handle_types::section);
|
||||
|
||||
constexpr auto CONSOLE_HANDLE = make_pseudo_handle(0x1, handle_types::file);
|
||||
constexpr auto STDOUT_HANDLE = make_pseudo_handle(0x2, handle_types::file);
|
||||
constexpr auto STDIN_HANDLE = make_pseudo_handle(0x3, handle_types::file);
|
||||
|
||||
struct syscall_context;
|
||||
using syscall_handler = void(*)(const syscall_context& c);
|
||||
|
||||
Reference in New Issue
Block a user