kern: update KAddressSpaceInfo to reflect 20.0.0 changes

This commit is contained in:
Michael Scire 2025-04-30 18:56:47 -07:00 committed by SciresM
parent 66fcf33a2c
commit 3e19e4d004
6 changed files with 40 additions and 16 deletions

View file

@ -37,7 +37,7 @@ namespace ams::kern {
size_t m_size; size_t m_size;
Type m_type; Type m_type;
public: public:
static uintptr_t GetAddressSpaceStart(ams::svc::CreateProcessFlag flags, Type type); static uintptr_t GetAddressSpaceStart(ams::svc::CreateProcessFlag flags, Type type, size_t code_size);
static size_t GetAddressSpaceSize(ams::svc::CreateProcessFlag flags, Type type); static size_t GetAddressSpaceSize(ams::svc::CreateProcessFlag flags, Type type);
static void SetAddressSpaceSize(size_t width, Type type, size_t size); static void SetAddressSpaceSize(size_t width, Type type, size_t size);

View file

@ -66,12 +66,39 @@ namespace ams::kern {
} }
uintptr_t KAddressSpaceInfo::GetAddressSpaceStart(ams::svc::CreateProcessFlag flags, KAddressSpaceInfo::Type type) { uintptr_t KAddressSpaceInfo::GetAddressSpaceStart(ams::svc::CreateProcessFlag flags, KAddressSpaceInfo::Type type, size_t code_size) {
MESOSPHERE_UNUSED(code_size);
return GetAddressSpaceInfo(GetAddressSpaceWidth(flags), type).GetAddress(); return GetAddressSpaceInfo(GetAddressSpaceWidth(flags), type).GetAddress();
} }
size_t KAddressSpaceInfo::GetAddressSpaceSize(ams::svc::CreateProcessFlag flags, KAddressSpaceInfo::Type type) { size_t KAddressSpaceInfo::GetAddressSpaceSize(ams::svc::CreateProcessFlag flags, KAddressSpaceInfo::Type type) {
return GetAddressSpaceInfo(GetAddressSpaceWidth(flags), type).GetSize(); /* Extract the address space from the create process flags. */
const auto as_flags = (flags & ams::svc::CreateProcessFlag_AddressSpaceMask);
/* Get the address space width. */
const auto as_width = GetAddressSpaceWidth(flags);
/* Get the size. */
size_t as_size = GetAddressSpaceInfo(as_width, type).GetSize();
/* If we're getting size for 32-bit without alias, adjust the sizes accordingly. */
if (as_flags == ams::svc::CreateProcessFlag_AddressSpace32BitWithoutAlias) {
switch (type) {
/* The heap space receives space that would otherwise go to the alias space. */
case KAddressSpaceInfo::Type_Heap:
as_size += GetAddressSpaceInfo(as_width, KAddressSpaceInfo::Type_Alias).GetSize();
break;
/* The alias space doesn't exist. */
case KAddressSpaceInfo::Type_Alias:
as_size = 0;
break;
/* Nothing to do by default. */
default:
break;
}
}
return as_size;
} }
void KAddressSpaceInfo::SetAddressSpaceSize(size_t width, Type type, size_t size) { void KAddressSpaceInfo::SetAddressSpaceSize(size_t width, Type type, size_t size) {

View file

@ -229,9 +229,12 @@ namespace ams::kern {
out->flags |= ams::svc::CreateProcessFlag_DisableDeviceAddressSpaceMerge; out->flags |= ams::svc::CreateProcessFlag_DisableDeviceAddressSpaceMerge;
/* Set and check code address. */ /* Set and check code address. */
/* NOTE: Even though Nintendo passes a size to GetAddressSpaceStart at other call sites, they pass */
/* a number of pages here. Even though this is presumably only used for debug assertions, this is */
/* almost certainly a bug. */
using ASType = KAddressSpaceInfo::Type; using ASType = KAddressSpaceInfo::Type;
const ASType as_type = this->Is64BitAddressSpace() ? ((GetTargetFirmware() >= TargetFirmware_2_0_0) ? KAddressSpaceInfo::Type_Map39Bit : KAddressSpaceInfo::Type_MapSmall) : KAddressSpaceInfo::Type_MapSmall; const ASType as_type = this->Is64BitAddressSpace() ? ((GetTargetFirmware() >= TargetFirmware_2_0_0) ? KAddressSpaceInfo::Type_Map39Bit : KAddressSpaceInfo::Type_MapSmall) : KAddressSpaceInfo::Type_MapSmall;
const uintptr_t map_start = KAddressSpaceInfo::GetAddressSpaceStart(static_cast<ams::svc::CreateProcessFlag>(out->flags), as_type); const uintptr_t map_start = KAddressSpaceInfo::GetAddressSpaceStart(static_cast<ams::svc::CreateProcessFlag>(out->flags), as_type, out->code_num_pages);
const size_t map_size = KAddressSpaceInfo::GetAddressSpaceSize(static_cast<ams::svc::CreateProcessFlag>(out->flags), as_type); const size_t map_size = KAddressSpaceInfo::GetAddressSpaceSize(static_cast<ams::svc::CreateProcessFlag>(out->flags), as_type);
const uintptr_t map_end = map_start + map_size; const uintptr_t map_end = map_start + map_size;
out->code_address = map_start + start_address; out->code_address = map_start + start_address;

View file

@ -141,7 +141,7 @@ namespace ams::kern {
/* Define helpers. */ /* Define helpers. */
auto GetSpaceStart = [&](KAddressSpaceInfo::Type type) ALWAYS_INLINE_LAMBDA { auto GetSpaceStart = [&](KAddressSpaceInfo::Type type) ALWAYS_INLINE_LAMBDA {
return KAddressSpaceInfo::GetAddressSpaceStart(flags, type); return KAddressSpaceInfo::GetAddressSpaceStart(flags, type, code_size);
}; };
auto GetSpaceSize = [&](KAddressSpaceInfo::Type type) ALWAYS_INLINE_LAMBDA { auto GetSpaceSize = [&](KAddressSpaceInfo::Type type) ALWAYS_INLINE_LAMBDA {
return KAddressSpaceInfo::GetAddressSpaceSize(flags, type); return KAddressSpaceInfo::GetAddressSpaceSize(flags, type);
@ -155,12 +155,6 @@ namespace ams::kern {
size_t alias_region_size = GetSpaceSize(KAddressSpaceInfo::Type_Alias); size_t alias_region_size = GetSpaceSize(KAddressSpaceInfo::Type_Alias);
size_t heap_region_size = GetSpaceSize(KAddressSpaceInfo::Type_Heap); size_t heap_region_size = GetSpaceSize(KAddressSpaceInfo::Type_Heap);
/* Adjust heap/alias size if we don't have an alias region. */
if ((flags & ams::svc::CreateProcessFlag_AddressSpaceMask) == ams::svc::CreateProcessFlag_AddressSpace32BitWithoutAlias) {
heap_region_size += alias_region_size;
alias_region_size = 0;
}
/* Set code regions and determine remaining sizes. */ /* Set code regions and determine remaining sizes. */
KProcessAddress process_code_start; KProcessAddress process_code_start;
KProcessAddress process_code_end; KProcessAddress process_code_end;

View file

@ -221,7 +221,7 @@ namespace ams::kern {
} }
/* Set max memory. */ /* Set max memory. */
m_max_process_memory = m_page_table.GetHeapRegionSize(); m_max_process_memory = KAddressSpaceInfo::GetAddressSpaceSize(static_cast<ams::svc::CreateProcessFlag>(m_flags), KAddressSpaceInfo::Type_Heap);
/* Generate random entropy. */ /* Generate random entropy. */
KSystemControl::GenerateRandom(m_entropy, util::size(m_entropy)); KSystemControl::GenerateRandom(m_entropy, util::size(m_entropy));

View file

@ -109,11 +109,12 @@ namespace ams::kern::svc {
/* Decide on an address space map region. */ /* Decide on an address space map region. */
uintptr_t map_start, map_end; uintptr_t map_start, map_end;
size_t map_size; size_t map_size;
const size_t code_size = params.code_num_pages * PageSize;
switch (params.flags & ams::svc::CreateProcessFlag_AddressSpaceMask) { switch (params.flags & ams::svc::CreateProcessFlag_AddressSpaceMask) {
case ams::svc::CreateProcessFlag_AddressSpace32Bit: case ams::svc::CreateProcessFlag_AddressSpace32Bit:
case ams::svc::CreateProcessFlag_AddressSpace32BitWithoutAlias: case ams::svc::CreateProcessFlag_AddressSpace32BitWithoutAlias:
{ {
map_start = KAddressSpaceInfo::GetAddressSpaceStart(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_MapSmall); map_start = KAddressSpaceInfo::GetAddressSpaceStart(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_MapSmall, code_size);
map_size = KAddressSpaceInfo::GetAddressSpaceSize(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_MapSmall); map_size = KAddressSpaceInfo::GetAddressSpaceSize(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_MapSmall);
map_end = map_start + map_size; map_end = map_start + map_size;
} }
@ -123,7 +124,7 @@ namespace ams::kern::svc {
/* 64-bit address space requires 64-bit process. */ /* 64-bit address space requires 64-bit process. */
R_UNLESS(is_64_bit, svc::ResultInvalidCombination()); R_UNLESS(is_64_bit, svc::ResultInvalidCombination());
map_start = KAddressSpaceInfo::GetAddressSpaceStart(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_MapSmall); map_start = KAddressSpaceInfo::GetAddressSpaceStart(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_MapSmall, code_size);
map_size = KAddressSpaceInfo::GetAddressSpaceSize(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_MapSmall); map_size = KAddressSpaceInfo::GetAddressSpaceSize(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_MapSmall);
map_end = map_start + map_size; map_end = map_start + map_size;
} }
@ -133,7 +134,7 @@ namespace ams::kern::svc {
/* 64-bit address space requires 64-bit process. */ /* 64-bit address space requires 64-bit process. */
R_UNLESS(is_64_bit, svc::ResultInvalidCombination()); R_UNLESS(is_64_bit, svc::ResultInvalidCombination());
map_start = KAddressSpaceInfo::GetAddressSpaceStart(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_Map39Bit); map_start = KAddressSpaceInfo::GetAddressSpaceStart(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_Map39Bit, code_size);
map_end = map_start + KAddressSpaceInfo::GetAddressSpaceSize(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_Map39Bit); map_end = map_start + KAddressSpaceInfo::GetAddressSpaceSize(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_Map39Bit);
map_size = KAddressSpaceInfo::GetAddressSpaceSize(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_Heap); map_size = KAddressSpaceInfo::GetAddressSpaceSize(static_cast<ams::svc::CreateProcessFlag>(params.flags), KAddressSpaceInfo::Type_Heap);
@ -181,7 +182,6 @@ namespace ams::kern::svc {
const size_t code_num_pages = params.code_num_pages; const size_t code_num_pages = params.code_num_pages;
const size_t system_resource_num_pages = params.system_resource_num_pages; const size_t system_resource_num_pages = params.system_resource_num_pages;
const size_t total_pages = code_num_pages + system_resource_num_pages; const size_t total_pages = code_num_pages + system_resource_num_pages;
const size_t code_size = code_num_pages * PageSize;
const size_t system_resource_size = system_resource_num_pages * PageSize; const size_t system_resource_size = system_resource_num_pages * PageSize;
const size_t total_size = code_size + system_resource_size; const size_t total_size = code_size + system_resource_size;