CpuTestAluRx.cs 37 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724
  1. #define AluRx
  2. using NUnit.Framework;
  3. namespace Ryujinx.Tests.Cpu
  4. {
  5. [Category("AluRx")]
  6. public sealed class CpuTestAluRx : CpuTest
  7. {
  8. #if AluRx
  9. private const int RndCnt = 2;
  10. [Test, Pairwise, Description("ADD <Xd|SP>, <Xn|SP>, <X><m>{, <extend> {#<amount>}}")]
  11. public void Add_X_64bit([Values(0u, 31u)] uint rd,
  12. [Values(1u, 31u)] uint rn,
  13. [Values(2u, 31u)] uint rm,
  14. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  15. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  16. [Values((ulong)0x0000000000000000, (ulong)0x7FFFFFFFFFFFFFFF,
  17. (ulong)0x8000000000000000, (ulong)0xFFFFFFFFFFFFFFFF)] [Random(RndCnt)] ulong xm,
  18. [Values(0b011u, 0b111u)] uint extend, // <LSL|UXTX, SXTX>
  19. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  20. {
  21. uint opcode = 0x8B206000; // ADD X0, X0, X0, UXTX #0
  22. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  23. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  24. if (rn != 31)
  25. {
  26. ulong x31 = TestContext.CurrentContext.Random.NextULong();
  27. SingleOpcode(opcode, x1: xnSp, x2: xm, x31: x31);
  28. }
  29. else
  30. {
  31. SingleOpcode(opcode, x31: xnSp, x2: xm);
  32. }
  33. CompareAgainstUnicorn();
  34. }
  35. [Test, Pairwise, Description("ADD <Xd|SP>, <Xn|SP>, <W><m>{, <extend> {#<amount>}}")]
  36. public void Add_W_64bit([Values(0u, 31u)] uint rd,
  37. [Values(1u, 31u)] uint rn,
  38. [Values(2u, 31u)] uint rm,
  39. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  40. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  41. [Values((uint)0x00000000, (uint)0x7FFFFFFF,
  42. (uint)0x80000000, (uint)0xFFFFFFFF)] [Random(RndCnt)] uint wm,
  43. [Values(0b000u, 0b001u, 0b010u, // <UXTB, UXTH, UXTW,
  44. 0b100u, 0b101u, 0b110u)] uint extend, // SXTB, SXTH, SXTW>
  45. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  46. {
  47. uint opcode = 0x8B200000; // ADD X0, X0, W0, UXTB #0
  48. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  49. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  50. if (rn != 31)
  51. {
  52. ulong x31 = TestContext.CurrentContext.Random.NextULong();
  53. SingleOpcode(opcode, x1: xnSp, x2: wm, x31: x31);
  54. }
  55. else
  56. {
  57. SingleOpcode(opcode, x31: xnSp, x2: wm);
  58. }
  59. CompareAgainstUnicorn();
  60. }
  61. [Test, Pairwise, Description("ADD <Xd|SP>, <Xn|SP>, <W><m>{, <extend> {#<amount>}}")]
  62. public void Add_H_64bit([Values(0u, 31u)] uint rd,
  63. [Values(1u, 31u)] uint rn,
  64. [Values(2u, 31u)] uint rm,
  65. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  66. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  67. [Values((ushort)0x0000, (ushort)0x7FFF,
  68. (ushort)0x8000, (ushort)0xFFFF)] [Random(RndCnt)] ushort wm,
  69. [Values(0b000u, 0b001u, 0b010u, // <UXTB, UXTH, UXTW,
  70. 0b100u, 0b101u, 0b110u)] uint extend, // SXTB, SXTH, SXTW>
  71. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  72. {
  73. uint opcode = 0x8B200000; // ADD X0, X0, W0, UXTB #0
  74. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  75. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  76. if (rn != 31)
  77. {
  78. ulong x31 = TestContext.CurrentContext.Random.NextULong();
  79. SingleOpcode(opcode, x1: xnSp, x2: wm, x31: x31);
  80. }
  81. else
  82. {
  83. SingleOpcode(opcode, x31: xnSp, x2: wm);
  84. }
  85. CompareAgainstUnicorn();
  86. }
  87. [Test, Pairwise, Description("ADD <Xd|SP>, <Xn|SP>, <W><m>{, <extend> {#<amount>}}")]
  88. public void Add_B_64bit([Values(0u, 31u)] uint rd,
  89. [Values(1u, 31u)] uint rn,
  90. [Values(2u, 31u)] uint rm,
  91. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  92. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  93. [Values((byte)0x00, (byte)0x7F,
  94. (byte)0x80, (byte)0xFF)] [Random(RndCnt)] byte wm,
  95. [Values(0b000u, 0b001u, 0b010u, // <UXTB, UXTH, UXTW,
  96. 0b100u, 0b101u, 0b110u)] uint extend, // SXTB, SXTH, SXTW>
  97. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  98. {
  99. uint opcode = 0x8B200000; // ADD X0, X0, W0, UXTB #0
  100. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  101. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  102. if (rn != 31)
  103. {
  104. ulong x31 = TestContext.CurrentContext.Random.NextULong();
  105. SingleOpcode(opcode, x1: xnSp, x2: wm, x31: x31);
  106. }
  107. else
  108. {
  109. SingleOpcode(opcode, x31: xnSp, x2: wm);
  110. }
  111. CompareAgainstUnicorn();
  112. }
  113. [Test, Pairwise, Description("ADD <Wd|WSP>, <Wn|WSP>, <Wm>{, <extend> {#<amount>}}")]
  114. public void Add_W_32bit([Values(0u, 31u)] uint rd,
  115. [Values(1u, 31u)] uint rn,
  116. [Values(2u, 31u)] uint rm,
  117. [Values(0x00000000u, 0x7FFFFFFFu,
  118. 0x80000000u, 0xFFFFFFFFu)] [Random(RndCnt)] uint wnWsp,
  119. [Values((uint)0x00000000, (uint)0x7FFFFFFF,
  120. (uint)0x80000000, (uint)0xFFFFFFFF)] [Random(RndCnt)] uint wm,
  121. [Values(0b000u, 0b001u, 0b010u, 0b011u, // <UXTB, UXTH, LSL|UXTW, UXTX,
  122. 0b100u, 0b101u, 0b110u, 0b111u)] uint extend, // SXTB, SXTH, SXTW, SXTX>
  123. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  124. {
  125. uint opcode = 0x0B200000; // ADD W0, W0, W0, UXTB #0
  126. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  127. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  128. if (rn != 31)
  129. {
  130. uint w31 = TestContext.CurrentContext.Random.NextUInt();
  131. SingleOpcode(opcode, x1: wnWsp, x2: wm, x31: w31);
  132. }
  133. else
  134. {
  135. SingleOpcode(opcode, x31: wnWsp, x2: wm);
  136. }
  137. CompareAgainstUnicorn();
  138. }
  139. [Test, Pairwise, Description("ADD <Wd|WSP>, <Wn|WSP>, <Wm>{, <extend> {#<amount>}}")]
  140. public void Add_H_32bit([Values(0u, 31u)] uint rd,
  141. [Values(1u, 31u)] uint rn,
  142. [Values(2u, 31u)] uint rm,
  143. [Values(0x00000000u, 0x7FFFFFFFu,
  144. 0x80000000u, 0xFFFFFFFFu)] [Random(RndCnt)] uint wnWsp,
  145. [Values((ushort)0x0000, (ushort)0x7FFF,
  146. (ushort)0x8000, (ushort)0xFFFF)] [Random(RndCnt)] ushort wm,
  147. [Values(0b000u, 0b001u, 0b010u, 0b011u, // <UXTB, UXTH, LSL|UXTW, UXTX,
  148. 0b100u, 0b101u, 0b110u, 0b111u)] uint extend, // SXTB, SXTH, SXTW, SXTX>
  149. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  150. {
  151. uint opcode = 0x0B200000; // ADD W0, W0, W0, UXTB #0
  152. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  153. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  154. if (rn != 31)
  155. {
  156. uint w31 = TestContext.CurrentContext.Random.NextUInt();
  157. SingleOpcode(opcode, x1: wnWsp, x2: wm, x31: w31);
  158. }
  159. else
  160. {
  161. SingleOpcode(opcode, x31: wnWsp, x2: wm);
  162. }
  163. CompareAgainstUnicorn();
  164. }
  165. [Test, Pairwise, Description("ADD <Wd|WSP>, <Wn|WSP>, <Wm>{, <extend> {#<amount>}}")]
  166. public void Add_B_32bit([Values(0u, 31u)] uint rd,
  167. [Values(1u, 31u)] uint rn,
  168. [Values(2u, 31u)] uint rm,
  169. [Values(0x00000000u, 0x7FFFFFFFu,
  170. 0x80000000u, 0xFFFFFFFFu)] [Random(RndCnt)] uint wnWsp,
  171. [Values((byte)0x00, (byte)0x7F,
  172. (byte)0x80, (byte)0xFF)] [Random(RndCnt)] byte wm,
  173. [Values(0b000u, 0b001u, 0b010u, 0b011u, // <UXTB, UXTH, LSL|UXTW, UXTX,
  174. 0b100u, 0b101u, 0b110u, 0b111u)] uint extend, // SXTB, SXTH, SXTW, SXTX>
  175. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  176. {
  177. uint opcode = 0x0B200000; // ADD W0, W0, W0, UXTB #0
  178. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  179. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  180. if (rn != 31)
  181. {
  182. uint w31 = TestContext.CurrentContext.Random.NextUInt();
  183. SingleOpcode(opcode, x1: wnWsp, x2: wm, x31: w31);
  184. }
  185. else
  186. {
  187. SingleOpcode(opcode, x31: wnWsp, x2: wm);
  188. }
  189. CompareAgainstUnicorn();
  190. }
  191. [Test, Pairwise, Description("ADDS <Xd>, <Xn|SP>, <X><m>{, <extend> {#<amount>}}")]
  192. public void Adds_X_64bit([Values(0u, 31u)] uint rd,
  193. [Values(1u, 31u)] uint rn,
  194. [Values(2u, 31u)] uint rm,
  195. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  196. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  197. [Values((ulong)0x0000000000000000, (ulong)0x7FFFFFFFFFFFFFFF,
  198. (ulong)0x8000000000000000, (ulong)0xFFFFFFFFFFFFFFFF)] [Random(RndCnt)] ulong xm,
  199. [Values(0b011u, 0b111u)] uint extend, // <LSL|UXTX, SXTX>
  200. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  201. {
  202. uint opcode = 0xAB206000; // ADDS X0, X0, X0, UXTX #0
  203. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  204. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  205. SingleOpcode(opcode, x1: xnSp, x2: xm, x31: xnSp);
  206. CompareAgainstUnicorn();
  207. }
  208. [Test, Pairwise, Description("ADDS <Xd>, <Xn|SP>, <W><m>{, <extend> {#<amount>}}")]
  209. public void Adds_W_64bit([Values(0u, 31u)] uint rd,
  210. [Values(1u, 31u)] uint rn,
  211. [Values(2u, 31u)] uint rm,
  212. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  213. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  214. [Values((uint)0x00000000, (uint)0x7FFFFFFF,
  215. (uint)0x80000000, (uint)0xFFFFFFFF)] [Random(RndCnt)] uint wm,
  216. [Values(0b000u, 0b001u, 0b010u, // <UXTB, UXTH, UXTW,
  217. 0b100u, 0b101u, 0b110u)] uint extend, // SXTB, SXTH, SXTW>
  218. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  219. {
  220. uint opcode = 0xAB200000; // ADDS X0, X0, W0, UXTB #0
  221. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  222. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  223. SingleOpcode(opcode, x1: xnSp, x2: wm, x31: xnSp);
  224. CompareAgainstUnicorn();
  225. }
  226. [Test, Pairwise, Description("ADDS <Xd>, <Xn|SP>, <W><m>{, <extend> {#<amount>}}")]
  227. public void Adds_H_64bit([Values(0u, 31u)] uint rd,
  228. [Values(1u, 31u)] uint rn,
  229. [Values(2u, 31u)] uint rm,
  230. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  231. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  232. [Values((ushort)0x0000, (ushort)0x7FFF,
  233. (ushort)0x8000, (ushort)0xFFFF)] [Random(RndCnt)] ushort wm,
  234. [Values(0b000u, 0b001u, 0b010u, // <UXTB, UXTH, UXTW,
  235. 0b100u, 0b101u, 0b110u)] uint extend, // SXTB, SXTH, SXTW>
  236. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  237. {
  238. uint opcode = 0xAB200000; // ADDS X0, X0, W0, UXTB #0
  239. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  240. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  241. SingleOpcode(opcode, x1: xnSp, x2: wm, x31: xnSp);
  242. CompareAgainstUnicorn();
  243. }
  244. [Test, Pairwise, Description("ADDS <Xd>, <Xn|SP>, <W><m>{, <extend> {#<amount>}}")]
  245. public void Adds_B_64bit([Values(0u, 31u)] uint rd,
  246. [Values(1u, 31u)] uint rn,
  247. [Values(2u, 31u)] uint rm,
  248. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  249. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  250. [Values((byte)0x00, (byte)0x7F,
  251. (byte)0x80, (byte)0xFF)] [Random(RndCnt)] byte wm,
  252. [Values(0b000u, 0b001u, 0b010u, // <UXTB, UXTH, UXTW,
  253. 0b100u, 0b101u, 0b110u)] uint extend, // SXTB, SXTH, SXTW>
  254. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  255. {
  256. uint opcode = 0xAB200000; // ADDS X0, X0, W0, UXTB #0
  257. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  258. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  259. SingleOpcode(opcode, x1: xnSp, x2: wm, x31: xnSp);
  260. CompareAgainstUnicorn();
  261. }
  262. [Test, Pairwise, Description("ADDS <Wd>, <Wn|WSP>, <Wm>{, <extend> {#<amount>}}")]
  263. public void Adds_W_32bit([Values(0u, 31u)] uint rd,
  264. [Values(1u, 31u)] uint rn,
  265. [Values(2u, 31u)] uint rm,
  266. [Values(0x00000000u, 0x7FFFFFFFu,
  267. 0x80000000u, 0xFFFFFFFFu)] [Random(RndCnt)] uint wnWsp,
  268. [Values((uint)0x00000000, (uint)0x7FFFFFFF,
  269. (uint)0x80000000, (uint)0xFFFFFFFF)] [Random(RndCnt)] uint wm,
  270. [Values(0b000u, 0b001u, 0b010u, 0b011u, // <UXTB, UXTH, LSL|UXTW, UXTX,
  271. 0b100u, 0b101u, 0b110u, 0b111u)] uint extend, // SXTB, SXTH, SXTW, SXTX>
  272. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  273. {
  274. uint opcode = 0x2B200000; // ADDS W0, W0, W0, UXTB #0
  275. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  276. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  277. SingleOpcode(opcode, x1: wnWsp, x2: wm, x31: wnWsp);
  278. CompareAgainstUnicorn();
  279. }
  280. [Test, Pairwise, Description("ADDS <Wd>, <Wn|WSP>, <Wm>{, <extend> {#<amount>}}")]
  281. public void Adds_H_32bit([Values(0u, 31u)] uint rd,
  282. [Values(1u, 31u)] uint rn,
  283. [Values(2u, 31u)] uint rm,
  284. [Values(0x00000000u, 0x7FFFFFFFu,
  285. 0x80000000u, 0xFFFFFFFFu)] [Random(RndCnt)] uint wnWsp,
  286. [Values((ushort)0x0000, (ushort)0x7FFF,
  287. (ushort)0x8000, (ushort)0xFFFF)] [Random(RndCnt)] ushort wm,
  288. [Values(0b000u, 0b001u, 0b010u, 0b011u, // <UXTB, UXTH, LSL|UXTW, UXTX,
  289. 0b100u, 0b101u, 0b110u, 0b111u)] uint extend, // SXTB, SXTH, SXTW, SXTX>
  290. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  291. {
  292. uint opcode = 0x2B200000; // ADDS W0, W0, W0, UXTB #0
  293. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  294. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  295. SingleOpcode(opcode, x1: wnWsp, x2: wm, x31: wnWsp);
  296. CompareAgainstUnicorn();
  297. }
  298. [Test, Pairwise, Description("ADDS <Wd>, <Wn|WSP>, <Wm>{, <extend> {#<amount>}}")]
  299. public void Adds_B_32bit([Values(0u, 31u)] uint rd,
  300. [Values(1u, 31u)] uint rn,
  301. [Values(2u, 31u)] uint rm,
  302. [Values(0x00000000u, 0x7FFFFFFFu,
  303. 0x80000000u, 0xFFFFFFFFu)] [Random(RndCnt)] uint wnWsp,
  304. [Values((byte)0x00, (byte)0x7F,
  305. (byte)0x80, (byte)0xFF)] [Random(RndCnt)] byte wm,
  306. [Values(0b000u, 0b001u, 0b010u, 0b011u, // <UXTB, UXTH, LSL|UXTW, UXTX,
  307. 0b100u, 0b101u, 0b110u, 0b111u)] uint extend, // SXTB, SXTH, SXTW, SXTX>
  308. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  309. {
  310. uint opcode = 0x2B200000; // ADDS W0, W0, W0, UXTB #0
  311. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  312. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  313. SingleOpcode(opcode, x1: wnWsp, x2: wm, x31: wnWsp);
  314. CompareAgainstUnicorn();
  315. }
  316. [Test, Pairwise, Description("SUB <Xd|SP>, <Xn|SP>, <X><m>{, <extend> {#<amount>}}")]
  317. public void Sub_X_64bit([Values(0u, 31u)] uint rd,
  318. [Values(1u, 31u)] uint rn,
  319. [Values(2u, 31u)] uint rm,
  320. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  321. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  322. [Values((ulong)0x0000000000000000, (ulong)0x7FFFFFFFFFFFFFFF,
  323. (ulong)0x8000000000000000, (ulong)0xFFFFFFFFFFFFFFFF)] [Random(RndCnt)] ulong xm,
  324. [Values(0b011u, 0b111u)] uint extend, // <LSL|UXTX, SXTX>
  325. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  326. {
  327. uint opcode = 0xCB206000; // SUB X0, X0, X0, UXTX #0
  328. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  329. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  330. if (rn != 31)
  331. {
  332. ulong x31 = TestContext.CurrentContext.Random.NextULong();
  333. SingleOpcode(opcode, x1: xnSp, x2: xm, x31: x31);
  334. }
  335. else
  336. {
  337. SingleOpcode(opcode, x31: xnSp, x2: xm);
  338. }
  339. CompareAgainstUnicorn();
  340. }
  341. [Test, Pairwise, Description("SUB <Xd|SP>, <Xn|SP>, <W><m>{, <extend> {#<amount>}}")]
  342. public void Sub_W_64bit([Values(0u, 31u)] uint rd,
  343. [Values(1u, 31u)] uint rn,
  344. [Values(2u, 31u)] uint rm,
  345. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  346. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  347. [Values((uint)0x00000000, (uint)0x7FFFFFFF,
  348. (uint)0x80000000, (uint)0xFFFFFFFF)] [Random(RndCnt)] uint wm,
  349. [Values(0b000u, 0b001u, 0b010u, // <UXTB, UXTH, UXTW,
  350. 0b100u, 0b101u, 0b110u)] uint extend, // SXTB, SXTH, SXTW>
  351. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  352. {
  353. uint opcode = 0xCB200000; // SUB X0, X0, W0, UXTB #0
  354. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  355. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  356. if (rn != 31)
  357. {
  358. ulong x31 = TestContext.CurrentContext.Random.NextULong();
  359. SingleOpcode(opcode, x1: xnSp, x2: wm, x31: x31);
  360. }
  361. else
  362. {
  363. SingleOpcode(opcode, x31: xnSp, x2: wm);
  364. }
  365. CompareAgainstUnicorn();
  366. }
  367. [Test, Pairwise, Description("SUB <Xd|SP>, <Xn|SP>, <W><m>{, <extend> {#<amount>}}")]
  368. public void Sub_H_64bit([Values(0u, 31u)] uint rd,
  369. [Values(1u, 31u)] uint rn,
  370. [Values(2u, 31u)] uint rm,
  371. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  372. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  373. [Values((ushort)0x0000, (ushort)0x7FFF,
  374. (ushort)0x8000, (ushort)0xFFFF)] [Random(RndCnt)] ushort wm,
  375. [Values(0b000u, 0b001u, 0b010u, // <UXTB, UXTH, UXTW,
  376. 0b100u, 0b101u, 0b110u)] uint extend, // SXTB, SXTH, SXTW>
  377. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  378. {
  379. uint opcode = 0xCB200000; // SUB X0, X0, W0, UXTB #0
  380. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  381. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  382. if (rn != 31)
  383. {
  384. ulong x31 = TestContext.CurrentContext.Random.NextULong();
  385. SingleOpcode(opcode, x1: xnSp, x2: wm, x31: x31);
  386. }
  387. else
  388. {
  389. SingleOpcode(opcode, x31: xnSp, x2: wm);
  390. }
  391. CompareAgainstUnicorn();
  392. }
  393. [Test, Pairwise, Description("SUB <Xd|SP>, <Xn|SP>, <W><m>{, <extend> {#<amount>}}")]
  394. public void Sub_B_64bit([Values(0u, 31u)] uint rd,
  395. [Values(1u, 31u)] uint rn,
  396. [Values(2u, 31u)] uint rm,
  397. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  398. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  399. [Values((byte)0x00, (byte)0x7F,
  400. (byte)0x80, (byte)0xFF)] [Random(RndCnt)] byte wm,
  401. [Values(0b000u, 0b001u, 0b010u, // <UXTB, UXTH, UXTW,
  402. 0b100u, 0b101u, 0b110u)] uint extend, // SXTB, SXTH, SXTW>
  403. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  404. {
  405. uint opcode = 0xCB200000; // SUB X0, X0, W0, UXTB #0
  406. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  407. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  408. if (rn != 31)
  409. {
  410. ulong x31 = TestContext.CurrentContext.Random.NextULong();
  411. SingleOpcode(opcode, x1: xnSp, x2: wm, x31: x31);
  412. }
  413. else
  414. {
  415. SingleOpcode(opcode, x31: xnSp, x2: wm);
  416. }
  417. CompareAgainstUnicorn();
  418. }
  419. [Test, Pairwise, Description("SUB <Wd|WSP>, <Wn|WSP>, <Wm>{, <extend> {#<amount>}}")]
  420. public void Sub_W_32bit([Values(0u, 31u)] uint rd,
  421. [Values(1u, 31u)] uint rn,
  422. [Values(2u, 31u)] uint rm,
  423. [Values(0x00000000u, 0x7FFFFFFFu,
  424. 0x80000000u, 0xFFFFFFFFu)] [Random(RndCnt)] uint wnWsp,
  425. [Values((uint)0x00000000, (uint)0x7FFFFFFF,
  426. (uint)0x80000000, (uint)0xFFFFFFFF)] [Random(RndCnt)] uint wm,
  427. [Values(0b000u, 0b001u, 0b010u, 0b011u, // <UXTB, UXTH, LSL|UXTW, UXTX,
  428. 0b100u, 0b101u, 0b110u, 0b111u)] uint extend, // SXTB, SXTH, SXTW, SXTX>
  429. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  430. {
  431. uint opcode = 0x4B200000; // SUB W0, W0, W0, UXTB #0
  432. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  433. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  434. if (rn != 31)
  435. {
  436. uint w31 = TestContext.CurrentContext.Random.NextUInt();
  437. SingleOpcode(opcode, x1: wnWsp, x2: wm, x31: w31);
  438. }
  439. else
  440. {
  441. SingleOpcode(opcode, x31: wnWsp, x2: wm);
  442. }
  443. CompareAgainstUnicorn();
  444. }
  445. [Test, Pairwise, Description("SUB <Wd|WSP>, <Wn|WSP>, <Wm>{, <extend> {#<amount>}}")]
  446. public void Sub_H_32bit([Values(0u, 31u)] uint rd,
  447. [Values(1u, 31u)] uint rn,
  448. [Values(2u, 31u)] uint rm,
  449. [Values(0x00000000u, 0x7FFFFFFFu,
  450. 0x80000000u, 0xFFFFFFFFu)] [Random(RndCnt)] uint wnWsp,
  451. [Values((ushort)0x0000, (ushort)0x7FFF,
  452. (ushort)0x8000, (ushort)0xFFFF)] [Random(RndCnt)] ushort wm,
  453. [Values(0b000u, 0b001u, 0b010u, 0b011u, // <UXTB, UXTH, LSL|UXTW, UXTX,
  454. 0b100u, 0b101u, 0b110u, 0b111u)] uint extend, // SXTB, SXTH, SXTW, SXTX>
  455. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  456. {
  457. uint opcode = 0x4B200000; // SUB W0, W0, W0, UXTB #0
  458. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  459. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  460. if (rn != 31)
  461. {
  462. uint w31 = TestContext.CurrentContext.Random.NextUInt();
  463. SingleOpcode(opcode, x1: wnWsp, x2: wm, x31: w31);
  464. }
  465. else
  466. {
  467. SingleOpcode(opcode, x31: wnWsp, x2: wm);
  468. }
  469. CompareAgainstUnicorn();
  470. }
  471. [Test, Pairwise, Description("SUB <Wd|WSP>, <Wn|WSP>, <Wm>{, <extend> {#<amount>}}")]
  472. public void Sub_B_32bit([Values(0u, 31u)] uint rd,
  473. [Values(1u, 31u)] uint rn,
  474. [Values(2u, 31u)] uint rm,
  475. [Values(0x00000000u, 0x7FFFFFFFu,
  476. 0x80000000u, 0xFFFFFFFFu)] [Random(RndCnt)] uint wnWsp,
  477. [Values((byte)0x00, (byte)0x7F,
  478. (byte)0x80, (byte)0xFF)] [Random(RndCnt)] byte wm,
  479. [Values(0b000u, 0b001u, 0b010u, 0b011u, // <UXTB, UXTH, LSL|UXTW, UXTX,
  480. 0b100u, 0b101u, 0b110u, 0b111u)] uint extend, // SXTB, SXTH, SXTW, SXTX>
  481. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  482. {
  483. uint opcode = 0x4B200000; // SUB W0, W0, W0, UXTB #0
  484. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  485. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  486. if (rn != 31)
  487. {
  488. uint w31 = TestContext.CurrentContext.Random.NextUInt();
  489. SingleOpcode(opcode, x1: wnWsp, x2: wm, x31: w31);
  490. }
  491. else
  492. {
  493. SingleOpcode(opcode, x31: wnWsp, x2: wm);
  494. }
  495. CompareAgainstUnicorn();
  496. }
  497. [Test, Pairwise, Description("SUBS <Xd>, <Xn|SP>, <X><m>{, <extend> {#<amount>}}")]
  498. public void Subs_X_64bit([Values(0u, 31u)] uint rd,
  499. [Values(1u, 31u)] uint rn,
  500. [Values(2u, 31u)] uint rm,
  501. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  502. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  503. [Values((ulong)0x0000000000000000, (ulong)0x7FFFFFFFFFFFFFFF,
  504. (ulong)0x8000000000000000, (ulong)0xFFFFFFFFFFFFFFFF)] [Random(RndCnt)] ulong xm,
  505. [Values(0b011u, 0b111u)] uint extend, // <LSL|UXTX, SXTX>
  506. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  507. {
  508. uint opcode = 0xEB206000; // SUBS X0, X0, X0, UXTX #0
  509. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  510. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  511. SingleOpcode(opcode, x1: xnSp, x2: xm, x31: xnSp);
  512. CompareAgainstUnicorn();
  513. }
  514. [Test, Pairwise, Description("SUBS <Xd>, <Xn|SP>, <W><m>{, <extend> {#<amount>}}")]
  515. public void Subs_W_64bit([Values(0u, 31u)] uint rd,
  516. [Values(1u, 31u)] uint rn,
  517. [Values(2u, 31u)] uint rm,
  518. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  519. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  520. [Values((uint)0x00000000, (uint)0x7FFFFFFF,
  521. (uint)0x80000000, (uint)0xFFFFFFFF)] [Random(RndCnt)] uint wm,
  522. [Values(0b000u, 0b001u, 0b010u, // <UXTB, UXTH, UXTW,
  523. 0b100u, 0b101u, 0b110u)] uint extend, // SXTB, SXTH, SXTW>
  524. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  525. {
  526. uint opcode = 0xEB200000; // SUBS X0, X0, W0, UXTB #0
  527. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  528. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  529. SingleOpcode(opcode, x1: xnSp, x2: wm, x31: xnSp);
  530. CompareAgainstUnicorn();
  531. }
  532. [Test, Pairwise, Description("SUBS <Xd>, <Xn|SP>, <W><m>{, <extend> {#<amount>}}")]
  533. public void Subs_H_64bit([Values(0u, 31u)] uint rd,
  534. [Values(1u, 31u)] uint rn,
  535. [Values(2u, 31u)] uint rm,
  536. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  537. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  538. [Values((ushort)0x0000, (ushort)0x7FFF,
  539. (ushort)0x8000, (ushort)0xFFFF)] [Random(RndCnt)] ushort wm,
  540. [Values(0b000u, 0b001u, 0b010u, // <UXTB, UXTH, UXTW,
  541. 0b100u, 0b101u, 0b110u)] uint extend, // SXTB, SXTH, SXTW>
  542. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  543. {
  544. uint opcode = 0xEB200000; // SUBS X0, X0, W0, UXTB #0
  545. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  546. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  547. SingleOpcode(opcode, x1: xnSp, x2: wm, x31: xnSp);
  548. CompareAgainstUnicorn();
  549. }
  550. [Test, Pairwise, Description("SUBS <Xd>, <Xn|SP>, <W><m>{, <extend> {#<amount>}}")]
  551. public void Subs_B_64bit([Values(0u, 31u)] uint rd,
  552. [Values(1u, 31u)] uint rn,
  553. [Values(2u, 31u)] uint rm,
  554. [Values(0x0000000000000000ul, 0x7FFFFFFFFFFFFFFFul,
  555. 0x8000000000000000ul, 0xFFFFFFFFFFFFFFFFul)] [Random(RndCnt)] ulong xnSp,
  556. [Values((byte)0x00, (byte)0x7F,
  557. (byte)0x80, (byte)0xFF)] [Random(RndCnt)] byte wm,
  558. [Values(0b000u, 0b001u, 0b010u, // <UXTB, UXTH, UXTW,
  559. 0b100u, 0b101u, 0b110u)] uint extend, // SXTB, SXTH, SXTW>
  560. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  561. {
  562. uint opcode = 0xEB200000; // SUBS X0, X0, W0, UXTB #0
  563. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  564. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  565. SingleOpcode(opcode, x1: xnSp, x2: wm, x31: xnSp);
  566. CompareAgainstUnicorn();
  567. }
  568. [Test, Pairwise, Description("SUBS <Wd>, <Wn|WSP>, <Wm>{, <extend> {#<amount>}}")]
  569. public void Subs_W_32bit([Values(0u, 31u)] uint rd,
  570. [Values(1u, 31u)] uint rn,
  571. [Values(2u, 31u)] uint rm,
  572. [Values(0x00000000u, 0x7FFFFFFFu,
  573. 0x80000000u, 0xFFFFFFFFu)] [Random(RndCnt)] uint wnWsp,
  574. [Values((uint)0x00000000, (uint)0x7FFFFFFF,
  575. (uint)0x80000000, (uint)0xFFFFFFFF)] [Random(RndCnt)] uint wm,
  576. [Values(0b000u, 0b001u, 0b010u, 0b011u, // <UXTB, UXTH, LSL|UXTW, UXTX,
  577. 0b100u, 0b101u, 0b110u, 0b111u)] uint extend, // SXTB, SXTH, SXTW, SXTX>
  578. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  579. {
  580. uint opcode = 0x6B200000; // SUBS W0, W0, W0, UXTB #0
  581. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  582. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  583. SingleOpcode(opcode, x1: wnWsp, x2: wm, x31: wnWsp);
  584. CompareAgainstUnicorn();
  585. }
  586. [Test, Pairwise, Description("SUBS <Wd>, <Wn|WSP>, <Wm>{, <extend> {#<amount>}}")]
  587. public void Subs_H_32bit([Values(0u, 31u)] uint rd,
  588. [Values(1u, 31u)] uint rn,
  589. [Values(2u, 31u)] uint rm,
  590. [Values(0x00000000u, 0x7FFFFFFFu,
  591. 0x80000000u, 0xFFFFFFFFu)] [Random(RndCnt)] uint wnWsp,
  592. [Values((ushort)0x0000, (ushort)0x7FFF,
  593. (ushort)0x8000, (ushort)0xFFFF)] [Random(RndCnt)] ushort wm,
  594. [Values(0b000u, 0b001u, 0b010u, 0b011u, // <UXTB, UXTH, LSL|UXTW, UXTX,
  595. 0b100u, 0b101u, 0b110u, 0b111u)] uint extend, // SXTB, SXTH, SXTW, SXTX>
  596. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  597. {
  598. uint opcode = 0x6B200000; // SUBS W0, W0, W0, UXTB #0
  599. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  600. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  601. SingleOpcode(opcode, x1: wnWsp, x2: wm, x31: wnWsp);
  602. CompareAgainstUnicorn();
  603. }
  604. [Test, Pairwise, Description("SUBS <Wd>, <Wn|WSP>, <Wm>{, <extend> {#<amount>}}")]
  605. public void Subs_B_32bit([Values(0u, 31u)] uint rd,
  606. [Values(1u, 31u)] uint rn,
  607. [Values(2u, 31u)] uint rm,
  608. [Values(0x00000000u, 0x7FFFFFFFu,
  609. 0x80000000u, 0xFFFFFFFFu)] [Random(RndCnt)] uint wnWsp,
  610. [Values((byte)0x00, (byte)0x7F,
  611. (byte)0x80, (byte)0xFF)] [Random(RndCnt)] byte wm,
  612. [Values(0b000u, 0b001u, 0b010u, 0b011u, // <UXTB, UXTH, LSL|UXTW, UXTX,
  613. 0b100u, 0b101u, 0b110u, 0b111u)] uint extend, // SXTB, SXTH, SXTW, SXTX>
  614. [Values(0u, 1u, 2u, 3u, 4u)] uint amount)
  615. {
  616. uint opcode = 0x6B200000; // SUBS W0, W0, W0, UXTB #0
  617. opcode |= ((rm & 31) << 16) | ((rn & 31) << 5) | ((rd & 31) << 0);
  618. opcode |= ((extend & 7) << 13) | ((amount & 7) << 10);
  619. SingleOpcode(opcode, x1: wnWsp, x2: wm, x31: wnWsp);
  620. CompareAgainstUnicorn();
  621. }
  622. #endif
  623. }
  624. }