| 176 | } |
| 177 | |
| 178 | NX_NORETURN void LoadTarget() { |
| 179 | RestoreTls(); |
| 180 | |
| 181 | if(g_TargetMapAddress > 0) { |
| 182 | // Unmap previous target |
| 183 | const auto rw_size = AlignUp<PageAlignment>(g_TargetHeader.segments[2].size + g_TargetHeader.bss_size); |
| 184 | |
| 185 | if(R_FAILED(svcUnmapProcessCodeMemory(g_SelfProcessHandle, g_TargetMapAddress + g_TargetHeader.segments[0].file_off, reinterpret_cast<u64>(g_TargetHeapAddress) + g_TargetHeader.segments[0].file_off, g_TargetHeader.segments[0].size))) { |
| 186 | UL_RC_ASSERT(hbloader::ResultUnmapTextFailure); |
| 187 | } |
| 188 | |
| 189 | if(R_FAILED(svcUnmapProcessCodeMemory(g_SelfProcessHandle, g_TargetMapAddress + g_TargetHeader.segments[1].file_off, reinterpret_cast<u64>(g_TargetHeapAddress) + g_TargetHeader.segments[1].file_off, g_TargetHeader.segments[1].size))) { |
| 190 | UL_RC_ASSERT(hbloader::ResultUnmapRodataFailure); |
| 191 | } |
| 192 | |
| 193 | if(R_FAILED(svcUnmapProcessCodeMemory(g_SelfProcessHandle, g_TargetMapAddress + g_TargetHeader.segments[2].file_off, reinterpret_cast<u64>(g_TargetHeapAddress) + g_TargetHeader.segments[2].file_off, rw_size))) { |
| 194 | UL_RC_ASSERT(hbloader::ResultUnmapDataBssFailure); |
| 195 | } |
| 196 | |
| 197 | g_TargetMapAddress = 0; |
| 198 | } |
| 199 | |
| 200 | if(g_NextTargetPath[0] == '\0') { |
| 201 | util::CopyToStringBuffer(g_NextTargetPath, g_TargetInput.nro_path); |
| 202 | util::CopyToStringBuffer(g_NextTargetArgv, g_TargetInput.nro_argv); |
| 203 | } |
| 204 | |
| 205 | util::CopyToStringBuffer(g_TargetCurrentArgv, g_NextTargetArgv); |
| 206 | |
| 207 | auto target_base = g_TargetHeapAddress; |
| 208 | auto target_start = reinterpret_cast<NroStart*>(target_base); |
| 209 | auto target_header = reinterpret_cast<NroHeader*>(target_base + sizeof(NroStart)); |
| 210 | auto rest = target_base + sizeof(NroStart) + sizeof(NroHeader); |
| 211 | |
| 212 | { |
| 213 | UL_RC_ASSERT(InitializeFsdev()); |
| 214 | util::OnScopeExit exit_fsdev([]() { |
| 215 | FinalizeFsdev(); |
| 216 | }); |
| 217 | |
| 218 | { |
| 219 | auto f = fopen(g_NextTargetPath, "rb"); |
| 220 | if(f == nullptr) { |
| 221 | UL_RC_ASSERT(MAKERESULT(333, 900 + errno)); |
| 222 | UL_RC_ASSERT(hbloader::ResultNroOpenFailure); |
| 223 | } |
| 224 | util::OnScopeExit file_close([&]() { |
| 225 | fclose(f); |
| 226 | }); |
| 227 | |
| 228 | if(fread(target_start, sizeof(NroStart), 1, f) != 1) { |
| 229 | UL_RC_ASSERT(hbloader::ResultNroHeaderReadFailure); |
| 230 | } |
| 231 | if(fread(target_header, sizeof(NroHeader), 1, f) != 1) { |
| 232 | UL_RC_ASSERT(hbloader::ResultNroHeaderReadFailure); |
| 233 | } |
| 234 | |
| 235 | if(target_header->magic != NROHEADER_MAGIC) { |
no test coverage detected