From: Bernd Gerber on
Hi,

I am learning assembler programming on 64-bit Linux.
The instruction "push edx" ends up with the error "instruction not
supported in 64-bit mode", the instrucion "push rdx" works fine.
What do I have to do to push edx?

Thanks,
Bernd
From: Jean-Claude Arbaut on
Le 21/12/2009 21:41, Bernd Gerber a écrit :
> Hi,
>
> I am learning assembler programming on 64-bit Linux.
> The instruction "push edx" ends up with the error "instruction not
> supported in 64-bit mode", the instrucion "push rdx" works fine.
> What do I have to do to push edx?
>
> Thanks,
> Bernd

Stack pointer must be aligned on a 64 bits boundary,
therefore you can't do a "push edx".
From: Alexei A. Frounze on
On Dec 21, 1:09 pm, Jean-Claude Arbaut <jeanclaudearb...(a)orange.fr>
wrote:
> Le 21/12/2009 21:41, Bernd Gerber a écrit :
>
> > Hi,
>
> > I am learning assembler programming on 64-bit Linux.
> > The instruction  "push edx" ends up with the error "instruction not
> > supported in 64-bit mode", the instrucion "push rdx" works fine.
> > What do I have to do to push edx?
>
> > Thanks,
> > Bernd
>
> Stack pointer must be aligned on a 64 bits boundary,
> therefore you can't do a "push edx".

Although, that may have been the original intention, one can PUSH DX
in 64-bit mode (DB 66H, 52H).

Alex
From: Rod Pemberton on
"Bernd Gerber" <BerndGerber(a)text2re.com> wrote in message
news:7pa4s7F817U1(a)mid.individual.net...
>
> I am learning assembler programming on 64-bit Linux.
> The instruction "push edx" ends up with the error "instruction not
> supported in 64-bit mode", the instrucion "push rdx" works fine.

There is no way to encode a "push edx" as a single instruction in 64-bit
mode. The stack size is 64-bits in 64-bit mode. What this means is that
the stack pointer is adjusted by 8 bytes. IMO, it should also push 8 bytes
onto the stack. That may or may not be the case, depending on the cpu, for
values less than 64-bits.

If pushing a value smaller than 64-bits where there is a valid instruction
encoding for it, e.g., for 16-bits (2 bytes), the push should push 8 bytes
after sign- or zero-extending the 16-bits to 64-bits. Unfortunately, as I
learned from 32-bit code, some processors don't push the exact number of
bytes matching the stack width. I.e., for 32-bit mode with a 16-bit push,
on some processors only push 2 bytes, instead of 4 bytes. But, they
correctly adjust esp by 4.

> What do I have to do to push edx?

Now, that is an _entirely_ different question from asking how to encode a
"push edx" instruction in 64-bit mode... That asks how to get the _value_
in EDX onto the stack. I have two responses. One solution gets the value
onto the stack without preserving the values size, and the other gets the
value onto the stack while preserving the size.

1) And RDX with 0xFFFFFFFF, then push onto the stack. EDX's _value_ will be
on the stack, as 64-bits... It's size won't be 32-bits, but neither is size
used by pop in 64-bit mode: 64-bits.

AND RDX, 0FFFFFFFFh
PUSH RDX

2) There may be valid situations where you need to place only 4-bytes onto
an 8-byte aligned stack. However, all push instructions should decrement
RSP by 8. So, you can't just use a push instruction. In theory, it should
be possible to push 4-bytes onto a stack with 8-byte alignment. I say in
theory, because I don't immediately see anything in the Intel or AMD manuals
to prevent it. *And,* I haven't used 64-bit mode much yet. The technique,
if it works, is: intentional stack misalignment.

2a) construction via push

PUSH RDX ; put 8-bytes onto stack
INC RSP ; (misalign) adjust (add) stack pointer by 4
INC RSP
INC RSP
INC RSP ; four bytes remaining on stack

You could also replace the four INC's with LEA RSP, [RSP+4]. EDX's value,
as 32-bits, should now be on the stack. The stack is now mis-aligned by 4.
If you use a pop, it will pull 64-bits from the stack... problem. So, the
on-stack EDX should only be used by 32-bit code. The byte order should be
correct for the EDX portion or RDX, but, if not, BSWAP can be used to
correct.

2b) construction via mov

LEA RSP,[RSP-4] ; (misalign) adjust (subtract 4) stack pointer for 32-bit
value
MOV [RSP],EDX ; store 32-bit value

But, you'll need to get someone familiar with 64-bit mode to confirm if
either are correct.

HTH,


Rod Pemberton


From: Alexei A. Frounze on
On Dec 21, 11:53 pm, "Rod Pemberton" <do_not_h...(a)nohavenot.cmm>
wrote:
> There is no way to encode a "push edx" as a single instruction in 64-bit
> mode.  The stack size is 64-bits in 64-bit mode.  What this means is that
> the stack pointer is adjusted by 8 bytes.  IMO, it should also push 8 bytes
> onto the stack.  That may or may not be the case, depending on the cpu, for
> values less than 64-bits.
>
> If pushing a value smaller than 64-bits where there is a valid instruction
> encoding for it, e.g., for 16-bits (2 bytes), the push should push 8 bytes
> after sign- or zero-extending the 16-bits to 64-bits.

Pushing 16-bit values in 64-bit mode adjusts RSP by 2. No extension is
done.

Alex
 |  Next  |  Last
Pages: 1 2
Prev: HLA Floating Point opcodes
Next: Pushad with GAS?