@@ -153,15 +153,268 @@ public void TestLoadRegisterLiteral()
153153 public void TestLoadStoredOrdered ( )
154154 {
155155 var insn = DisassembleAndCheckMnemonic ( 0xC8DFFE88 , Arm64Mnemonic . LDAR ) ;
156-
157- Assert . Equal ( "0x00000000 LDAR X8, X20" , insn . ToString ( ) ) ;
156+ Assert . Equal ( "0x00000000 LDAR X8, [X20]" , insn . ToString ( ) ) ;
157+
158+ insn = DisassembleAndCheckMnemonic ( 0x08DFFC41 , Arm64Mnemonic . LDARB ) ;
159+ Assert . Equal ( "0x00000000 LDARB W1, [X2]" , insn . ToString ( ) ) ;
160+
161+ insn = DisassembleAndCheckMnemonic ( 0x089FFC83 , Arm64Mnemonic . STLRB ) ;
162+ Assert . Equal ( "0x00000000 STLRB W3, [X4]" , insn . ToString ( ) ) ;
163+
164+ insn = DisassembleAndCheckMnemonic ( 0x48DFFCC5 , Arm64Mnemonic . LDARH ) ;
165+ Assert . Equal ( "0x00000000 LDARH W5, [X6]" , insn . ToString ( ) ) ;
166+
167+ insn = DisassembleAndCheckMnemonic ( 0x489FFD07 , Arm64Mnemonic . STLRH ) ;
168+ Assert . Equal ( "0x00000000 STLRH W7, [X8]" , insn . ToString ( ) ) ;
169+
170+ insn = DisassembleAndCheckMnemonic ( 0x88DFFD49 , Arm64Mnemonic . LDAR ) ;
171+ Assert . Equal ( "0x00000000 LDAR W9, [X10]" , insn . ToString ( ) ) ;
172+
173+ insn = DisassembleAndCheckMnemonic ( 0x889FFD8B , Arm64Mnemonic . STLR ) ;
174+ Assert . Equal ( "0x00000000 STLR W11, [X12]" , insn . ToString ( ) ) ;
175+
176+ insn = DisassembleAndCheckMnemonic ( 0xC89FFE0F , Arm64Mnemonic . STLR ) ;
177+ Assert . Equal ( "0x00000000 STLR X15, [X16]" , insn . ToString ( ) ) ;
178+
179+ insn = DisassembleAndCheckMnemonic ( 0xC8DF7E51 , Arm64Mnemonic . LDLAR ) ;
180+ Assert . Equal ( "0x00000000 LDLAR X17, [X18]" , insn . ToString ( ) ) ;
181+
182+ insn = DisassembleAndCheckMnemonic ( 0x889F7E93 , Arm64Mnemonic . STLLR ) ;
183+ Assert . Equal ( "0x00000000 STLLR W19, [X20]" , insn . ToString ( ) ) ;
158184 }
159185
160186 [ Fact ]
161187 public void TestLoadRegExtended ( )
162188 {
163189 var insn = DisassembleAndCheckMnemonic ( 0xF8685928 , Arm64Mnemonic . LDR ) ;
164-
190+
165191 Assert . Equal ( "0x00000000 LDR X8, [X9, W8, UXTW #3]" , insn . ToString ( ) ) ;
166192 }
193+
194+ [ Fact ]
195+ public void TestVector128RegOffset ( )
196+ {
197+ //STR Q1, [X2, X3, LSL #4]
198+ var insn = DisassembleAndCheckMnemonic ( 0x3CA37841 , Arm64Mnemonic . STR ) ;
199+
200+ Assert . Equal ( Arm64Register . V1 , insn . Op0Reg ) ;
201+ Assert . Equal ( Arm64Register . X2 , insn . MemBase ) ;
202+ Assert . Equal ( Arm64Register . X3 , insn . MemAddendReg ) ;
203+ Assert . Equal ( Arm64ShiftType . LSL , insn . MemShiftType ) ;
204+ Assert . Equal ( 4 , insn . MemExtendOrShiftAmount ) ;
205+
206+ Assert . Equal ( "0x00000000 STR V1, [X2, X3, LSL #4]" , insn . ToString ( ) ) ;
207+
208+ //LDR Q30, [X5, W6, UXTW #4]
209+ insn = DisassembleAndCheckMnemonic ( 0x3CE658BE , Arm64Mnemonic . LDR ) ;
210+
211+ Assert . Equal ( Arm64Register . V30 , insn . Op0Reg ) ;
212+ Assert . Equal ( Arm64ExtendType . UXTW , insn . MemExtendType ) ;
213+ Assert . Equal ( 4 , insn . MemExtendOrShiftAmount ) ;
214+
215+ Assert . Equal ( "0x00000000 LDR V30, [X5, W6, UXTW #4]" , insn . ToString ( ) ) ;
216+ }
217+
218+ [ Fact ]
219+ public void TestVectorRegOffset ( )
220+ {
221+ var insn = DisassembleAndCheckMnemonic ( 0x3C256883 , Arm64Mnemonic . STR ) ;
222+ Assert . Equal ( "0x00000000 STR B3, [X4, X5]" , insn . ToString ( ) ) ;
223+
224+ insn = DisassembleAndCheckMnemonic ( 0x7C25D883 , Arm64Mnemonic . STR ) ;
225+ Assert . Equal ( "0x00000000 STR H3, [X4, W5, SXTW #1]" , insn . ToString ( ) ) ;
226+
227+ insn = DisassembleAndCheckMnemonic ( 0xBC627829 , Arm64Mnemonic . LDR ) ;
228+ Assert . Equal ( "0x00000000 LDR S9, [X1, X2, LSL #2]" , insn . ToString ( ) ) ;
229+
230+ insn = DisassembleAndCheckMnemonic ( 0xFC645867 , Arm64Mnemonic . LDR ) ;
231+ Assert . Equal ( "0x00000000 LDR D7, [X3, W4, UXTW #3]" , insn . ToString ( ) ) ;
232+ }
233+
234+ [ Fact ]
235+ public void TestGpRegOffset ( )
236+ {
237+ var insn = DisassembleAndCheckMnemonic ( 0xF82CD96A , Arm64Mnemonic . STR ) ;
238+ Assert . Equal ( "0x00000000 STR X10, [X11, W12, SXTW #3]" , insn . ToString ( ) ) ;
239+
240+ insn = DisassembleAndCheckMnemonic ( 0xB863C841 , Arm64Mnemonic . LDR ) ;
241+ Assert . Equal ( "0x00000000 LDR W1, [X2, W3, SXTW]" , insn . ToString ( ) ) ;
242+
243+ insn = DisassembleAndCheckMnemonic ( 0x38296907 , Arm64Mnemonic . STRB ) ;
244+ Assert . Equal ( "0x00000000 STRB W7, [X8, X9]" , insn . ToString ( ) ) ;
245+
246+ insn = DisassembleAndCheckMnemonic ( 0x38294907 , Arm64Mnemonic . STRB ) ;
247+ Assert . Equal ( "0x00000000 STRB W7, [X8, W9, UXTW]" , insn . ToString ( ) ) ;
248+
249+ //LSL #0 with the S flag set is encoded distinctly from a plain register offset
250+ insn = DisassembleAndCheckMnemonic ( 0x38697907 , Arm64Mnemonic . LDRB ) ;
251+ Assert . Equal ( "0x00000000 LDRB W7, [X8, X9, LSL #0]" , insn . ToString ( ) ) ;
252+
253+ insn = DisassembleAndCheckMnemonic ( 0x782778C5 , Arm64Mnemonic . STRH ) ;
254+ Assert . Equal ( "0x00000000 STRH W5, [X6, X7, LSL #1]" , insn . ToString ( ) ) ;
255+
256+ insn = DisassembleAndCheckMnemonic ( 0x7867D8C5 , Arm64Mnemonic . LDRH ) ;
257+ Assert . Equal ( "0x00000000 LDRH W5, [X6, W7, SXTW #1]" , insn . ToString ( ) ) ;
258+
259+ insn = DisassembleAndCheckMnemonic ( 0xF876FAB4 , Arm64Mnemonic . LDR ) ;
260+ Assert . Equal ( "0x00000000 LDR X20, [X21, X22, SXTX #3]" , insn . ToString ( ) ) ;
261+
262+ insn = DisassembleAndCheckMnemonic ( 0xF876EAB4 , Arm64Mnemonic . LDR ) ;
263+ Assert . Equal ( "0x00000000 LDR X20, [X21, X22, SXTX]" , insn . ToString ( ) ) ;
264+ }
265+
266+ [ Fact ]
267+ public void TestSignedLoadRegOffset ( )
268+ {
269+ var insn = DisassembleAndCheckMnemonic ( 0x38A36841 , Arm64Mnemonic . LDRSB ) ;
270+ Assert . Equal ( "0x00000000 LDRSB X1, [X2, X3]" , insn . ToString ( ) ) ;
271+
272+ insn = DisassembleAndCheckMnemonic ( 0x38E34841 , Arm64Mnemonic . LDRSB ) ;
273+ Assert . Equal ( "0x00000000 LDRSB W1, [X2, W3, UXTW]" , insn . ToString ( ) ) ;
274+
275+ insn = DisassembleAndCheckMnemonic ( 0x78AB7949 , Arm64Mnemonic . LDRSH ) ;
276+ Assert . Equal ( "0x00000000 LDRSH X9, [X10, X11, LSL #1]" , insn . ToString ( ) ) ;
277+
278+ insn = DisassembleAndCheckMnemonic ( 0x78EBD949 , Arm64Mnemonic . LDRSH ) ;
279+ Assert . Equal ( "0x00000000 LDRSH W9, [X10, W11, SXTW #1]" , insn . ToString ( ) ) ;
280+
281+ insn = DisassembleAndCheckMnemonic ( 0xB8A57883 , Arm64Mnemonic . LDRSW ) ;
282+ Assert . Equal ( "0x00000000 LDRSW X3, [X4, X5, LSL #2]" , insn . ToString ( ) ) ;
283+
284+ insn = DisassembleAndCheckMnemonic ( 0xB8A55883 , Arm64Mnemonic . LDRSW ) ;
285+ Assert . Equal ( "0x00000000 LDRSW X3, [X4, W5, UXTW #2]" , insn . ToString ( ) ) ;
286+ }
287+
288+ [ Fact ]
289+ public void TestSignedLoadFromImm ( )
290+ {
291+ var insn = DisassembleAndCheckMnemonic ( 0x39801441 , Arm64Mnemonic . LDRSB ) ;
292+ Assert . Equal ( "0x00000000 LDRSB X1, [X2 + 0x5]" , insn . ToString ( ) ) ;
293+
294+ insn = DisassembleAndCheckMnemonic ( 0x39C01441 , Arm64Mnemonic . LDRSB ) ;
295+ Assert . Equal ( "0x00000000 LDRSB W1, [X2 + 0x5]" , insn . ToString ( ) ) ;
296+
297+ insn = DisassembleAndCheckMnemonic ( 0x79800C83 , Arm64Mnemonic . LDRSH ) ;
298+ Assert . Equal ( "0x00000000 LDRSH X3, [X4 + 0x6]" , insn . ToString ( ) ) ;
299+
300+ insn = DisassembleAndCheckMnemonic ( 0x79C00C83 , Arm64Mnemonic . LDRSH ) ;
301+ Assert . Equal ( "0x00000000 LDRSH W3, [X4 + 0x6]" , insn . ToString ( ) ) ;
302+
303+ insn = DisassembleAndCheckMnemonic ( 0xB9804107 , Arm64Mnemonic . LDRSW ) ;
304+ Assert . Equal ( "0x00000000 LDRSW X7, [X8 + 0x40]" , insn . ToString ( ) ) ;
305+
306+ //LDRSB X5, [X6], #-16 (post-index)
307+ insn = DisassembleAndCheckMnemonic ( 0x389F04C5 , Arm64Mnemonic . LDRSB ) ;
308+ Assert . Equal ( "0x00000000 LDRSB X5, [X6], #-0x10" , insn . ToString ( ) ) ;
309+
310+ //LDRSB W5, [X6, #-16]! (pre-index)
311+ insn = DisassembleAndCheckMnemonic ( 0x38DF0CC5 , Arm64Mnemonic . LDRSB ) ;
312+ Assert . Equal ( "0x00000000 LDRSB W5, [X6 - 0x10]!" , insn . ToString ( ) ) ;
313+ }
314+
315+ [ Fact ]
316+ public void TestUnscaledLoadsStores ( )
317+ {
318+ var insn = DisassembleAndCheckMnemonic ( 0x3C1FD041 , Arm64Mnemonic . STUR ) ;
319+ Assert . Equal ( "0x00000000 STUR B1, [X2 - 0x3]" , insn . ToString ( ) ) ;
320+
321+ insn = DisassembleAndCheckMnemonic ( 0x7C4070A4 , Arm64Mnemonic . LDUR ) ;
322+ Assert . Equal ( "0x00000000 LDUR H4, [X5 + 0x7]" , insn . ToString ( ) ) ;
323+
324+ insn = DisassembleAndCheckMnemonic ( 0xBC1F70E6 , Arm64Mnemonic . STUR ) ;
325+ Assert . Equal ( "0x00000000 STUR S6, [X7 - 0x9]" , insn . ToString ( ) ) ;
326+
327+ insn = DisassembleAndCheckMnemonic ( 0xFC40B128 , Arm64Mnemonic . LDUR ) ;
328+ Assert . Equal ( "0x00000000 LDUR D8, [X9 + 0xB]" , insn . ToString ( ) ) ;
329+
330+ insn = DisassembleAndCheckMnemonic ( 0x3C9F316A , Arm64Mnemonic . STUR ) ;
331+ Assert . Equal ( "0x00000000 STUR V10, [X11 - 0xD]" , insn . ToString ( ) ) ;
332+
333+ insn = DisassembleAndCheckMnemonic ( 0x3CC0F1AC , Arm64Mnemonic . LDUR ) ;
334+ Assert . Equal ( "0x00000000 LDUR V12, [X13 + 0xF]" , insn . ToString ( ) ) ;
335+
336+ insn = DisassembleAndCheckMnemonic ( 0xB81EF1EE , Arm64Mnemonic . STUR ) ;
337+ Assert . Equal ( "0x00000000 STUR W14, [X15 - 0x11]" , insn . ToString ( ) ) ;
338+
339+ insn = DisassembleAndCheckMnemonic ( 0xF8413230 , Arm64Mnemonic . LDUR ) ;
340+ Assert . Equal ( "0x00000000 LDUR X16, [X17 + 0x13]" , insn . ToString ( ) ) ;
341+
342+ insn = DisassembleAndCheckMnemonic ( 0x381EB272 , Arm64Mnemonic . STURB ) ;
343+ Assert . Equal ( "0x00000000 STURB W18, [X19 - 0x15]" , insn . ToString ( ) ) ;
344+
345+ insn = DisassembleAndCheckMnemonic ( 0x784172B4 , Arm64Mnemonic . LDURH ) ;
346+ Assert . Equal ( "0x00000000 LDURH W20, [X21 + 0x17]" , insn . ToString ( ) ) ;
347+
348+ insn = DisassembleAndCheckMnemonic ( 0x389E72F6 , Arm64Mnemonic . LDURSB ) ;
349+ Assert . Equal ( "0x00000000 LDURSB X22, [X23 - 0x19]" , insn . ToString ( ) ) ;
350+
351+ insn = DisassembleAndCheckMnemonic ( 0x38DE72F6 , Arm64Mnemonic . LDURSB ) ;
352+ Assert . Equal ( "0x00000000 LDURSB W22, [X23 - 0x19]" , insn . ToString ( ) ) ;
353+
354+ insn = DisassembleAndCheckMnemonic ( 0x7881B338 , Arm64Mnemonic . LDURSH ) ;
355+ Assert . Equal ( "0x00000000 LDURSH X24, [X25 + 0x1B]" , insn . ToString ( ) ) ;
356+
357+ insn = DisassembleAndCheckMnemonic ( 0x78C1B338 , Arm64Mnemonic . LDURSH ) ;
358+ Assert . Equal ( "0x00000000 LDURSH W24, [X25 + 0x1B]" , insn . ToString ( ) ) ;
359+
360+ insn = DisassembleAndCheckMnemonic ( 0xB89E337A , Arm64Mnemonic . LDURSW ) ;
361+ Assert . Equal ( "0x00000000 LDURSW X26, [X27 - 0x1D]" , insn . ToString ( ) ) ;
362+ }
363+
364+ [ Fact ]
365+ public void TestLoadStorePairs ( )
366+ {
367+ var insn = DisassembleAndCheckMnemonic ( 0x29010861 , Arm64Mnemonic . STP ) ;
368+ Assert . Equal ( "0x00000000 STP W1, W2, [X3 + 0x8]" , insn . ToString ( ) ) ;
369+
370+ insn = DisassembleAndCheckMnemonic ( 0xA97F14C4 , Arm64Mnemonic . LDP ) ;
371+ Assert . Equal ( "0x00000000 LDP X4, X5, [X6 - 0x10]" , insn . ToString ( ) ) ;
372+
373+ insn = DisassembleAndCheckMnemonic ( 0x2D01A127 , Arm64Mnemonic . STP ) ;
374+ Assert . Equal ( "0x00000000 STP S7, S8, [X9 + 0xC]" , insn . ToString ( ) ) ;
375+
376+ insn = DisassembleAndCheckMnemonic ( 0x6D7EAD8A , Arm64Mnemonic . LDP ) ;
377+ Assert . Equal ( "0x00000000 LDP D10, D11, [X12 - 0x18]" , insn . ToString ( ) ) ;
378+
379+ insn = DisassembleAndCheckMnemonic ( 0xAD0139ED , Arm64Mnemonic . STP ) ;
380+ Assert . Equal ( "0x00000000 STP V13, V14, [X15 + 0x20]" , insn . ToString ( ) ) ;
381+
382+ insn = DisassembleAndCheckMnemonic ( 0x697FC650 , Arm64Mnemonic . LDPSW ) ;
383+ Assert . Equal ( "0x00000000 LDPSW X16, X17, [X18 - 0x4]" , insn . ToString ( ) ) ;
384+
385+ insn = DisassembleAndCheckMnemonic ( 0xA9C152B3 , Arm64Mnemonic . LDP ) ;
386+ Assert . Equal ( "0x00000000 LDP X19, X20, [X21 + 0x10]!" , insn . ToString ( ) ) ;
387+
388+ insn = DisassembleAndCheckMnemonic ( 0xA8BE5F16 , Arm64Mnemonic . STP ) ;
389+ Assert . Equal ( "0x00000000 STP X22, X23, [X24], #-0x20" , insn . ToString ( ) ) ;
390+
391+ insn = DisassembleAndCheckMnemonic ( 0x69008861 , Arm64Mnemonic . STGP ) ;
392+ Assert . Equal ( "0x00000000 STGP X1, X2, [X3 + 0x10]" , insn . ToString ( ) ) ;
393+ }
394+
395+ [ Fact ]
396+ public void TestLoadStoreNoAllocatePairs ( )
397+ {
398+ var insn = DisassembleAndCheckMnemonic ( 0x28010861 , Arm64Mnemonic . STNP ) ;
399+ Assert . Equal ( "0x00000000 STNP W1, W2, [X3 + 0x8]" , insn . ToString ( ) ) ;
400+
401+ insn = DisassembleAndCheckMnemonic ( 0xA87F14C4 , Arm64Mnemonic . LDNP ) ;
402+ Assert . Equal ( "0x00000000 LDNP X4, X5, [X6 - 0x10]" , insn . ToString ( ) ) ;
403+
404+ insn = DisassembleAndCheckMnemonic ( 0x2C01A127 , Arm64Mnemonic . STNP ) ;
405+ Assert . Equal ( "0x00000000 STNP S7, S8, [X9 + 0xC]" , insn . ToString ( ) ) ;
406+
407+ insn = DisassembleAndCheckMnemonic ( 0x6C7EAD8A , Arm64Mnemonic . LDNP ) ;
408+ Assert . Equal ( "0x00000000 LDNP D10, D11, [X12 - 0x18]" , insn . ToString ( ) ) ;
409+
410+ insn = DisassembleAndCheckMnemonic ( 0xAC4139ED , Arm64Mnemonic . LDNP ) ;
411+ Assert . Equal ( "0x00000000 LDNP V13, V14, [X15 + 0x20]" , insn . ToString ( ) ) ;
412+ }
413+
414+ [ Fact ]
415+ public void TestRegOffsetUndefinedOption ( )
416+ {
417+ //option<1> == 0 is unallocated for register offset loads/stores
418+ Assert . Throws < Arm64UndefinedInstructionException > ( ( ) => Disassembler . DisassembleSingleInstruction ( 0xB8638841 ) ) ;
419+ }
167420}
0 commit comments