diff options
| author | 2021-12-23 01:10:36 -0800 | |
|---|---|---|
| committer | 2021-12-23 01:10:36 -0800 | |
| commit | 4e7a6639d2be8c1c6a195004a1ca612a25085fea (patch) | |
| tree | 3dca18bcc3afd788152bf1fbab8f1e14824c6aeb /src/core/hle/kernel/svc.cpp | |
| parent | Merge pull request #7616 from bunnei/fix-get-idle-ticks (diff) | |
| download | yuzu-4e7a6639d2be8c1c6a195004a1ca612a25085fea.tar.gz yuzu-4e7a6639d2be8c1c6a195004a1ca612a25085fea.tar.xz yuzu-4e7a6639d2be8c1c6a195004a1ca612a25085fea.zip | |
core: hle: kernel: Implement SetMemoryPermission.
- Not seen in any games yet, but validated with kernel tests.
Diffstat (limited to 'src/core/hle/kernel/svc.cpp')
| -rw-r--r-- | src/core/hle/kernel/svc.cpp | 32 |
1 files changed, 31 insertions, 1 deletions
diff --git a/src/core/hle/kernel/svc.cpp b/src/core/hle/kernel/svc.cpp index 37d67b72e..68cb47211 100644 --- a/src/core/hle/kernel/svc.cpp +++ b/src/core/hle/kernel/svc.cpp | |||
| @@ -164,6 +164,36 @@ static ResultCode SetHeapSize32(Core::System& system, u32* heap_addr, u32 heap_s | |||
| 164 | return result; | 164 | return result; |
| 165 | } | 165 | } |
| 166 | 166 | ||
| 167 | constexpr bool IsValidSetMemoryPermission(MemoryPermission perm) { | ||
| 168 | switch (perm) { | ||
| 169 | case MemoryPermission::None: | ||
| 170 | case MemoryPermission::Read: | ||
| 171 | case MemoryPermission::ReadWrite: | ||
| 172 | return true; | ||
| 173 | default: | ||
| 174 | return false; | ||
| 175 | } | ||
| 176 | } | ||
| 177 | |||
| 178 | static ResultCode SetMemoryPermission(Core::System& system, VAddr address, u64 size, | ||
| 179 | MemoryPermission perm) { | ||
| 180 | // Validate address / size. | ||
| 181 | R_UNLESS(Common::IsAligned(address, PageSize), ResultInvalidAddress); | ||
| 182 | R_UNLESS(Common::IsAligned(size, PageSize), ResultInvalidSize); | ||
| 183 | R_UNLESS(size > 0, ResultInvalidSize); | ||
| 184 | R_UNLESS((address < address + size), ResultInvalidCurrentMemory); | ||
| 185 | |||
| 186 | // Validate the permission. | ||
| 187 | R_UNLESS(IsValidSetMemoryPermission(perm), ResultInvalidNewMemoryPermission); | ||
| 188 | |||
| 189 | // Validate that the region is in range for the current process. | ||
| 190 | auto& page_table = system.Kernel().CurrentProcess()->PageTable(); | ||
| 191 | R_UNLESS(page_table.Contains(address, size), ResultInvalidCurrentMemory); | ||
| 192 | |||
| 193 | // Set the memory attribute. | ||
| 194 | return page_table.SetMemoryPermission(address, size, perm); | ||
| 195 | } | ||
| 196 | |||
| 167 | static ResultCode SetMemoryAttribute(Core::System& system, VAddr address, u64 size, u32 mask, | 197 | static ResultCode SetMemoryAttribute(Core::System& system, VAddr address, u64 size, u32 mask, |
| 168 | u32 attribute) { | 198 | u32 attribute) { |
| 169 | LOG_DEBUG(Kernel_SVC, | 199 | LOG_DEBUG(Kernel_SVC, |
| @@ -2724,7 +2754,7 @@ static const FunctionDef SVC_Table_32[] = { | |||
| 2724 | static const FunctionDef SVC_Table_64[] = { | 2754 | static const FunctionDef SVC_Table_64[] = { |
| 2725 | {0x00, nullptr, "Unknown"}, | 2755 | {0x00, nullptr, "Unknown"}, |
| 2726 | {0x01, SvcWrap64<SetHeapSize>, "SetHeapSize"}, | 2756 | {0x01, SvcWrap64<SetHeapSize>, "SetHeapSize"}, |
| 2727 | {0x02, nullptr, "SetMemoryPermission"}, | 2757 | {0x02, SvcWrap64<SetMemoryPermission>, "SetMemoryPermission"}, |
| 2728 | {0x03, SvcWrap64<SetMemoryAttribute>, "SetMemoryAttribute"}, | 2758 | {0x03, SvcWrap64<SetMemoryAttribute>, "SetMemoryAttribute"}, |
| 2729 | {0x04, SvcWrap64<MapMemory>, "MapMemory"}, | 2759 | {0x04, SvcWrap64<MapMemory>, "MapMemory"}, |
| 2730 | {0x05, SvcWrap64<UnmapMemory>, "UnmapMemory"}, | 2760 | {0x05, SvcWrap64<UnmapMemory>, "UnmapMemory"}, |