function_wrappers.h 6.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228
  1. // Copyright 2014 Citra Emulator Project
  2. // Licensed under GPLv2 or any later version
  3. // Refer to the license.txt file included.
  4. #pragma once
  5. #include "common/common_types.h"
  6. #include "core/arm/arm_interface.h"
  7. #include "core/memory.h"
  8. #include "core/hle/hle.h"
  9. #include "core/hle/result.h"
  10. #include "core/hle/svc.h"
  11. namespace HLE {
  12. #define PARAM(n) Core::g_app_core->GetReg(n)
  13. /// An invalid result code that is meant to be overwritten when a thread resumes from waiting
  14. static const ResultCode RESULT_INVALID(0xDEADC0DE);
  15. /**
  16. * HLE a function return from the current ARM11 userland process
  17. * @param res Result to return
  18. */
  19. static inline void FuncReturn(u32 res) {
  20. Core::g_app_core->SetReg(0, res);
  21. }
  22. /**
  23. * HLE a function return (64-bit) from the current ARM11 userland process
  24. * @param res Result to return (64-bit)
  25. * @todo Verify that this function is correct
  26. */
  27. static inline void FuncReturn64(u64 res) {
  28. Core::g_app_core->SetReg(0, (u32)(res & 0xFFFFFFFF));
  29. Core::g_app_core->SetReg(1, (u32)((res >> 32) & 0xFFFFFFFF));
  30. }
  31. ////////////////////////////////////////////////////////////////////////////////////////////////////
  32. // Function wrappers that return type ResultCode
  33. template<ResultCode func(u32, u32, u32, u32)> void Wrap() {
  34. FuncReturn(func(PARAM(0), PARAM(1), PARAM(2), PARAM(3)).raw);
  35. }
  36. template<ResultCode func(u32*, u32, u32, u32, u32, u32)> void Wrap(){
  37. u32 param_1 = 0;
  38. u32 retval = func(&param_1, PARAM(0), PARAM(1), PARAM(2), PARAM(3), PARAM(4)).raw;
  39. Core::g_app_core->SetReg(1, param_1);
  40. FuncReturn(retval);
  41. }
  42. template<ResultCode func(u32*, s32, u32, u32, u32, s32)> void Wrap() {
  43. u32 param_1 = 0;
  44. u32 retval = func(&param_1, PARAM(0), PARAM(1), PARAM(2), PARAM(3), PARAM(4)).raw;
  45. Core::g_app_core->SetReg(1, param_1);
  46. FuncReturn(retval);
  47. }
  48. template<ResultCode func(s32*, u32*, s32, bool, s64)> void Wrap() {
  49. s32 param_1 = 0;
  50. s32 retval = func(&param_1, (Handle*)Memory::GetPointer(PARAM(1)), (s32)PARAM(2),
  51. (PARAM(3) != 0), (((s64)PARAM(4) << 32) | PARAM(0))).raw;
  52. if (retval != RESULT_INVALID.raw) {
  53. Core::g_app_core->SetReg(1, (u32)param_1);
  54. FuncReturn(retval);
  55. }
  56. }
  57. template<ResultCode func(u32, u32, u32, u32, s64)> void Wrap() {
  58. FuncReturn(func(PARAM(0), PARAM(1), PARAM(2), PARAM(3), (((s64)PARAM(5) << 32) | PARAM(4))).raw);
  59. }
  60. template<ResultCode func(u32*)> void Wrap(){
  61. u32 param_1 = 0;
  62. u32 retval = func(&param_1).raw;
  63. Core::g_app_core->SetReg(1, param_1);
  64. FuncReturn(retval);
  65. }
  66. template<ResultCode func(u32, s64)> void Wrap() {
  67. s32 retval = func(PARAM(0), (((s64)PARAM(3) << 32) | PARAM(2))).raw;
  68. if (retval != RESULT_INVALID.raw) {
  69. FuncReturn(retval);
  70. }
  71. }
  72. template<ResultCode func(MemoryInfo*, PageInfo*, u32)> void Wrap() {
  73. MemoryInfo memory_info = {};
  74. PageInfo page_info = {};
  75. u32 retval = func(&memory_info, &page_info, PARAM(2)).raw;
  76. Core::g_app_core->SetReg(1, memory_info.base_address);
  77. Core::g_app_core->SetReg(2, memory_info.size);
  78. Core::g_app_core->SetReg(3, memory_info.permission);
  79. Core::g_app_core->SetReg(4, memory_info.state);
  80. Core::g_app_core->SetReg(5, page_info.flags);
  81. FuncReturn(retval);
  82. }
  83. template<ResultCode func(MemoryInfo*, PageInfo*, Handle, u32)> void Wrap() {
  84. MemoryInfo memory_info = {};
  85. PageInfo page_info = {};
  86. u32 retval = func(&memory_info, &page_info, PARAM(2), PARAM(3)).raw;
  87. Core::g_app_core->SetReg(1, memory_info.base_address);
  88. Core::g_app_core->SetReg(2, memory_info.size);
  89. Core::g_app_core->SetReg(3, memory_info.permission);
  90. Core::g_app_core->SetReg(4, memory_info.state);
  91. Core::g_app_core->SetReg(5, page_info.flags);
  92. FuncReturn(retval);
  93. }
  94. template<ResultCode func(s32*, u32)> void Wrap(){
  95. s32 param_1 = 0;
  96. u32 retval = func(&param_1, PARAM(1)).raw;
  97. Core::g_app_core->SetReg(1, param_1);
  98. FuncReturn(retval);
  99. }
  100. template<ResultCode func(u32, s32)> void Wrap() {
  101. FuncReturn(func(PARAM(0), (s32)PARAM(1)).raw);
  102. }
  103. template<ResultCode func(u32*, u32)> void Wrap(){
  104. u32 param_1 = 0;
  105. u32 retval = func(&param_1, PARAM(1)).raw;
  106. Core::g_app_core->SetReg(1, param_1);
  107. FuncReturn(retval);
  108. }
  109. template<ResultCode func(u32)> void Wrap() {
  110. FuncReturn(func(PARAM(0)).raw);
  111. }
  112. template<ResultCode func(s64*, u32, u32*, u32)> void Wrap(){
  113. FuncReturn(func((s64*)Memory::GetPointer(PARAM(0)), PARAM(1), (u32*)Memory::GetPointer(PARAM(2)),
  114. (s32)PARAM(3)).raw);
  115. }
  116. template<ResultCode func(u32*, const char*)> void Wrap() {
  117. u32 param_1 = 0;
  118. u32 retval = func(&param_1, (char*)Memory::GetPointer(PARAM(1))).raw;
  119. Core::g_app_core->SetReg(1, param_1);
  120. FuncReturn(retval);
  121. }
  122. template<ResultCode func(u32*, s32, s32)> void Wrap() {
  123. u32 param_1 = 0;
  124. u32 retval = func(&param_1, PARAM(1), PARAM(2)).raw;
  125. Core::g_app_core->SetReg(1, param_1);
  126. FuncReturn(retval);
  127. }
  128. template<ResultCode func(s32*, u32, s32)> void Wrap() {
  129. s32 param_1 = 0;
  130. u32 retval = func(&param_1, PARAM(1), PARAM(2)).raw;
  131. Core::g_app_core->SetReg(1, param_1);
  132. FuncReturn(retval);
  133. }
  134. template<ResultCode func(s64*, u32, s32)> void Wrap() {
  135. s64 param_1 = 0;
  136. u32 retval = func(&param_1, PARAM(1), PARAM(2)).raw;
  137. Core::g_app_core->SetReg(1, (u32)param_1);
  138. Core::g_app_core->SetReg(2, (u32)(param_1 >> 32));
  139. FuncReturn(retval);
  140. }
  141. template<ResultCode func(u32*, u32, u32, u32, u32)> void Wrap() {
  142. u32 param_1 = 0;
  143. u32 retval = func(&param_1, PARAM(1), PARAM(2), PARAM(3), PARAM(4)).raw;
  144. Core::g_app_core->SetReg(1, param_1);
  145. FuncReturn(retval);
  146. }
  147. template<ResultCode func(u32, s64, s64)> void Wrap() {
  148. s64 param1 = ((u64)PARAM(3) << 32) | PARAM(2);
  149. s64 param2 = ((u64)PARAM(4) << 32) | PARAM(1);
  150. FuncReturn(func(PARAM(0), param1, param2).raw);
  151. }
  152. template<ResultCode func(s64*, Handle, u32)> void Wrap() {
  153. s64 param_1 = 0;
  154. u32 retval = func(&param_1, PARAM(1), PARAM(2)).raw;
  155. Core::g_app_core->SetReg(1, (u32)param_1);
  156. Core::g_app_core->SetReg(2, (u32)(param_1 >> 32));
  157. FuncReturn(retval);
  158. }
  159. template<ResultCode func(Handle, u32)> void Wrap() {
  160. FuncReturn(func(PARAM(0), PARAM(1)).raw);
  161. }
  162. ////////////////////////////////////////////////////////////////////////////////////////////////////
  163. // Function wrappers that return type u32
  164. template<u32 func()> void Wrap() {
  165. FuncReturn(func());
  166. }
  167. ////////////////////////////////////////////////////////////////////////////////////////////////////
  168. // Function wrappers that return type s64
  169. template<s64 func()> void Wrap() {
  170. FuncReturn64(func());
  171. }
  172. ////////////////////////////////////////////////////////////////////////////////////////////////////
  173. /// Function wrappers that return type void
  174. template<void func(s64)> void Wrap() {
  175. func(((s64)PARAM(1) << 32) | PARAM(0));
  176. }
  177. template<void func(const char*)> void Wrap() {
  178. func((char*)Memory::GetPointer(PARAM(0)));
  179. }
  180. template<void func(u8)> void Wrap() {
  181. func((u8)PARAM(0));
  182. }
  183. #undef PARAM
  184. #undef FuncReturn
  185. } // namespace HLE