diff options
| author | 2021-02-14 02:46:01 -0800 | |
|---|---|---|
| committer | 2021-02-14 02:46:01 -0800 | |
| commit | b0a39153512b1efc031f31e80924e6c14068f4a1 (patch) | |
| tree | 6662126adde3eee72afb1f1491e51841e4567f57 | |
| parent | yuzu: Various frontend improvements to avoid crashes and improve experience o... (diff) | |
| parent | hle: service: ldn: IUserLocalCommunicationService: Improve the stub. (diff) | |
| download | yuzu-b0a39153512b1efc031f31e80924e6c14068f4a1.tar.gz yuzu-b0a39153512b1efc031f31e80924e6c14068f4a1.tar.xz yuzu-b0a39153512b1efc031f31e80924e6c14068f4a1.zip | |
Merge pull request #5920 from bunnei/am-ldn-fix
Fix LDN Initialization return code & resulting AM overflow
Diffstat (limited to '')
| -rw-r--r-- | src/core/CMakeLists.txt | 1 | ||||
| -rw-r--r-- | src/core/hle/service/am/am.cpp | 13 | ||||
| -rw-r--r-- | src/core/hle/service/ldn/errors.h | 13 | ||||
| -rw-r--r-- | src/core/hle/service/ldn/ldn.cpp | 36 |
4 files changed, 52 insertions, 11 deletions
diff --git a/src/core/CMakeLists.txt b/src/core/CMakeLists.txt index 1662ec63d..e74e6a668 100644 --- a/src/core/CMakeLists.txt +++ b/src/core/CMakeLists.txt | |||
| @@ -400,6 +400,7 @@ add_library(core STATIC | |||
| 400 | hle/service/hid/controllers/xpad.h | 400 | hle/service/hid/controllers/xpad.h |
| 401 | hle/service/lbl/lbl.cpp | 401 | hle/service/lbl/lbl.cpp |
| 402 | hle/service/lbl/lbl.h | 402 | hle/service/lbl/lbl.h |
| 403 | hle/service/ldn/errors.h | ||
| 403 | hle/service/ldn/ldn.cpp | 404 | hle/service/ldn/ldn.cpp |
| 404 | hle/service/ldn/ldn.h | 405 | hle/service/ldn/ldn.h |
| 405 | hle/service/ldr/ldr.cpp | 406 | hle/service/ldr/ldr.cpp |
diff --git a/src/core/hle/service/am/am.cpp b/src/core/hle/service/am/am.cpp index bb77c2569..8e1fe9438 100644 --- a/src/core/hle/service/am/am.cpp +++ b/src/core/hle/service/am/am.cpp | |||
| @@ -1047,20 +1047,21 @@ void IStorageAccessor::Write(Kernel::HLERequestContext& ctx) { | |||
| 1047 | 1047 | ||
| 1048 | const u64 offset{rp.Pop<u64>()}; | 1048 | const u64 offset{rp.Pop<u64>()}; |
| 1049 | const std::vector<u8> data{ctx.ReadBuffer()}; | 1049 | const std::vector<u8> data{ctx.ReadBuffer()}; |
| 1050 | const std::size_t size{std::min(data.size(), backing.GetSize() - offset)}; | ||
| 1050 | 1051 | ||
| 1051 | LOG_DEBUG(Service_AM, "called, offset={}, size={}", offset, data.size()); | 1052 | LOG_DEBUG(Service_AM, "called, offset={}, size={}", offset, size); |
| 1052 | 1053 | ||
| 1053 | if (data.size() > backing.GetSize() - offset) { | 1054 | if (offset > backing.GetSize()) { |
| 1054 | LOG_ERROR(Service_AM, | 1055 | LOG_ERROR(Service_AM, |
| 1055 | "offset is out of bounds, backing_buffer_sz={}, data_size={}, offset={}", | 1056 | "offset is out of bounds, backing_buffer_sz={}, data_size={}, offset={}", |
| 1056 | backing.GetSize(), data.size(), offset); | 1057 | backing.GetSize(), size, offset); |
| 1057 | 1058 | ||
| 1058 | IPC::ResponseBuilder rb{ctx, 2}; | 1059 | IPC::ResponseBuilder rb{ctx, 2}; |
| 1059 | rb.Push(ERR_SIZE_OUT_OF_BOUNDS); | 1060 | rb.Push(ERR_SIZE_OUT_OF_BOUNDS); |
| 1060 | return; | 1061 | return; |
| 1061 | } | 1062 | } |
| 1062 | 1063 | ||
| 1063 | std::memcpy(backing.GetData().data() + offset, data.data(), data.size()); | 1064 | std::memcpy(backing.GetData().data() + offset, data.data(), size); |
| 1064 | 1065 | ||
| 1065 | IPC::ResponseBuilder rb{ctx, 2}; | 1066 | IPC::ResponseBuilder rb{ctx, 2}; |
| 1066 | rb.Push(RESULT_SUCCESS); | 1067 | rb.Push(RESULT_SUCCESS); |
| @@ -1070,11 +1071,11 @@ void IStorageAccessor::Read(Kernel::HLERequestContext& ctx) { | |||
| 1070 | IPC::RequestParser rp{ctx}; | 1071 | IPC::RequestParser rp{ctx}; |
| 1071 | 1072 | ||
| 1072 | const u64 offset{rp.Pop<u64>()}; | 1073 | const u64 offset{rp.Pop<u64>()}; |
| 1073 | const std::size_t size{ctx.GetWriteBufferSize()}; | 1074 | const std::size_t size{std::min(ctx.GetWriteBufferSize(), backing.GetSize() - offset)}; |
| 1074 | 1075 | ||
| 1075 | LOG_DEBUG(Service_AM, "called, offset={}, size={}", offset, size); | 1076 | LOG_DEBUG(Service_AM, "called, offset={}, size={}", offset, size); |
| 1076 | 1077 | ||
| 1077 | if (size > backing.GetSize() - offset) { | 1078 | if (offset > backing.GetSize()) { |
| 1078 | LOG_ERROR(Service_AM, "offset is out of bounds, backing_buffer_sz={}, size={}, offset={}", | 1079 | LOG_ERROR(Service_AM, "offset is out of bounds, backing_buffer_sz={}, size={}, offset={}", |
| 1079 | backing.GetSize(), size, offset); | 1080 | backing.GetSize(), size, offset); |
| 1080 | 1081 | ||
diff --git a/src/core/hle/service/ldn/errors.h b/src/core/hle/service/ldn/errors.h new file mode 100644 index 000000000..a718c5c66 --- /dev/null +++ b/src/core/hle/service/ldn/errors.h | |||
| @@ -0,0 +1,13 @@ | |||
| 1 | // Copyright 2021 yuzu emulator team | ||
| 2 | // Licensed under GPLv2 or any later version | ||
| 3 | // Refer to the license.txt file included. | ||
| 4 | |||
| 5 | #pragma once | ||
| 6 | |||
| 7 | #include "core/hle/result.h" | ||
| 8 | |||
| 9 | namespace Service::LDN { | ||
| 10 | |||
| 11 | constexpr ResultCode ERROR_DISABLED{ErrorModule::LDN, 22}; | ||
| 12 | |||
| 13 | } // namespace Service::LDN | ||
diff --git a/src/core/hle/service/ldn/ldn.cpp b/src/core/hle/service/ldn/ldn.cpp index ee908f399..c630d93cd 100644 --- a/src/core/hle/service/ldn/ldn.cpp +++ b/src/core/hle/service/ldn/ldn.cpp | |||
| @@ -6,6 +6,7 @@ | |||
| 6 | 6 | ||
| 7 | #include "core/hle/ipc_helpers.h" | 7 | #include "core/hle/ipc_helpers.h" |
| 8 | #include "core/hle/result.h" | 8 | #include "core/hle/result.h" |
| 9 | #include "core/hle/service/ldn/errors.h" | ||
| 9 | #include "core/hle/service/ldn/ldn.h" | 10 | #include "core/hle/service/ldn/ldn.h" |
| 10 | #include "core/hle/service/sm/sm.h" | 11 | #include "core/hle/service/sm/sm.h" |
| 11 | 12 | ||
| @@ -103,7 +104,7 @@ public: | |||
| 103 | : ServiceFramework{system_, "IUserLocalCommunicationService"} { | 104 | : ServiceFramework{system_, "IUserLocalCommunicationService"} { |
| 104 | // clang-format off | 105 | // clang-format off |
| 105 | static const FunctionInfo functions[] = { | 106 | static const FunctionInfo functions[] = { |
| 106 | {0, nullptr, "GetState"}, | 107 | {0, &IUserLocalCommunicationService::GetState, "GetState"}, |
| 107 | {1, nullptr, "GetNetworkInfo"}, | 108 | {1, nullptr, "GetNetworkInfo"}, |
| 108 | {2, nullptr, "GetIpv4Address"}, | 109 | {2, nullptr, "GetIpv4Address"}, |
| 109 | {3, nullptr, "GetDisconnectReason"}, | 110 | {3, nullptr, "GetDisconnectReason"}, |
| @@ -138,13 +139,38 @@ public: | |||
| 138 | RegisterHandlers(functions); | 139 | RegisterHandlers(functions); |
| 139 | } | 140 | } |
| 140 | 141 | ||
| 141 | void Initialize2(Kernel::HLERequestContext& ctx) { | 142 | void GetState(Kernel::HLERequestContext& ctx) { |
| 142 | LOG_WARNING(Service_LDN, "(STUBBED) called"); | 143 | LOG_WARNING(Service_LDN, "(STUBBED) called"); |
| 143 | // Result success seem make this services start network and continue. | 144 | |
| 144 | // If we just pass result error then it will stop and maybe try again and again. | 145 | IPC::ResponseBuilder rb{ctx, 3}; |
| 146 | |||
| 147 | // Indicate a network error, as we do not actually emulate LDN | ||
| 148 | rb.Push(static_cast<u32>(State::Error)); | ||
| 149 | |||
| 150 | rb.Push(RESULT_SUCCESS); | ||
| 151 | } | ||
| 152 | |||
| 153 | void Initialize2(Kernel::HLERequestContext& ctx) { | ||
| 154 | LOG_DEBUG(Service_LDN, "called"); | ||
| 155 | |||
| 156 | is_initialized = true; | ||
| 157 | |||
| 145 | IPC::ResponseBuilder rb{ctx, 2}; | 158 | IPC::ResponseBuilder rb{ctx, 2}; |
| 146 | rb.Push(RESULT_UNKNOWN); | 159 | rb.Push(RESULT_SUCCESS); |
| 147 | } | 160 | } |
| 161 | |||
| 162 | private: | ||
| 163 | enum class State { | ||
| 164 | None, | ||
| 165 | Initialized, | ||
| 166 | AccessPointOpened, | ||
| 167 | AccessPointCreated, | ||
| 168 | StationOpened, | ||
| 169 | StationConnected, | ||
| 170 | Error, | ||
| 171 | }; | ||
| 172 | |||
| 173 | bool is_initialized{}; | ||
| 148 | }; | 174 | }; |
| 149 | 175 | ||
| 150 | class LDNS final : public ServiceFramework<LDNS> { | 176 | class LDNS final : public ServiceFramework<LDNS> { |