0

I am trying to do a negative offset for memory addressing. This is to convert a number to a string and make sure that it doesn't print in reverse order since x86 is little endian. Here is what I'm trying to do:

 # (b) move the asci number to rbp-8-len (to print in reverse)
 movb %al,  -8(%rbp, %r12, -1)

I know -1 is not a valid size, but I've shown what I'm trying to do conceptually above. What would be the proper way to do this?


Currently, I am doing it like:

# (b) move the asci number to rbp-8-len (to print in reverse)
# store offset (8+len) in %r13
mov $-8,        %r13
sub %r12,       %r13
movb %dl,       (%rbp, %r13)
Peter Cordes
  • 328,167
  • 45
  • 605
  • 847
samuelbrody1249
  • 4,379
  • 1
  • 15
  • 58
  • You can’t subtract two registers in an addressing mode. You have to use a separate sub instruction. (Also a separate mov instruction, if you don’t want to clobber rbp.) – prl Sep 19 '20 at 04:52
  • @prl I see, thanks for the feedback, is the (updated) way I'm doing it the way that you would do it, or can it be done better? – samuelbrody1249 Sep 19 '20 at 04:52
  • ARM can negate an index register as part of the addressing mode, x86 can't; negate the value first. Look at compiler output. (Or start at the end of a the buffer and decrement a pointer or index). – Peter Cordes Sep 19 '20 at 04:53
  • I would do `mov %rbp, %rax; sub %r12, %rax; movb %dl, -8(%rax)`. But it would be even better to go back to where these values came from and avoid this, if it’s not too inconvenient. – prl Sep 19 '20 at 04:59
  • P.S. little endianness has nothing to do with this. – prl Sep 19 '20 at 05:02
  • 1
    The reasons for my suggestion are: a) don’t use a call-preserved register as a temporary. (It doesn’t need to be rax.) b) use a simpler addressing mode if it’s convenient. c) in the addressing mode, the -8 takes one byte instead of 4 bytes. (In the addressing mode you chose, you pay for the one-byte displacement even though you don’t use it.) – prl Sep 19 '20 at 05:07
  • @prl I see -- do you want to post an answer and I can accept it? I just mentioned little-endian as I need to move asci to the stack and instead of using positive indexing I was using negative indexing to move the chars in reverse order so I could print it properly at the end. btw (as you can tell) i've a beginner to asm so thanks for all the feedback – samuelbrody1249 Sep 19 '20 at 05:14
  • A big-endian machine storing 1 byte at a time still needs to decrement a point to convert an integer to digit-string in printing order. Endianness is only a factor when you store a while 32-bit integer and later read back its bytes (or vice versa). For int->string with a pointer-decrement, see [Printing an integer as a string with AT&T syntax, with Linux system calls instead of printf](https://stackoverflow.com/a/45851398) – Peter Cordes Sep 19 '20 at 05:17
  • Another, shorter option would be `neg %r12; movb %dl, -8(%rbp, %r12)`. – Nate Eldredge Sep 19 '20 at 05:17
  • @prl by the way, if helpful, here is what I was trying to do with the above instruction: https://codereview.stackexchange.com/questions/249563/printing-a-decimal-number-as-a-string. – samuelbrody1249 Sep 19 '20 at 05:21
  • @PeterCordes thanks for that link, that's very helpful. As a total aside, have you talked to the StackOverflow crew about getting syntax highlighting for assembly? It seems odd that so many languages are supported and yet there's zero syntax highlighting for any assembly on the site. – samuelbrody1249 Sep 19 '20 at 05:25
  • 1
    There used to be some syntax highlighting for asm. Maybe the new highlighting code doesn't support it anymore (see the recent meta Q&A: [Goodbye, Prettify. Hello highlight.js! Swapping out our Syntax Highlighter](https://meta.stackexchange.com/q/353983)) – Peter Cordes Sep 19 '20 at 05:27

0 Answers0