Different asm on Windows x64 from a CS:APP x86-64 Linux example function for swapping a longProcess command line in Linux 64 bitTracing call stack in disassembled codeThere aren't enough registers in x86-64 processorWhat is the correct use of multiple input and output operands in extended GCC asm?Why are rbp and rsp called general purpose registers?Does AMD have different CPU registers? How is “rax” different from “eax”?How to access a parameter passed on the stack on entry to a dll?Assember prompt for user input doesn't workHow can I store 1byte value in 64bit register only using 64bit registers?Memory allocation and addressing in Assembly

Did 'Cinema Songs' exist during Hiranyakshipu's time?

Is "/bin/[.exe" a legitimate file? [Cygwin, Windows 10]

Bullying boss launched a smear campaign and made me unemployable

Placement of More Information/Help Icon button for Radio Buttons

How to compactly explain secondary and tertiary characters without resorting to stereotypes?

How to Prove P(a) → ∀x(P(x) ∨ ¬(x = a)) using Natural Deduction

Machine learning testing data

My ex-girlfriend uses my Apple ID to log in to her iPad. Do I have to give her my Apple ID password to reset it?

How to remove border from elements in the last row?

Why were 5.25" floppy drives cheaper than 8"?

Notepad++ delete until colon for every line with replace all

What reasons are there for a Capitalist to oppose a 100% inheritance tax?

Can someone clarify Hamming's notion of important problems in relation to modern academia?

Why was Sir Cadogan fired?

What is the fastest integer factorization to break RSA?

Are British MPs missing the point, with these 'Indicative Votes'?

Sums of two squares in arithmetic progressions

Should I tell management that I intend to leave due to bad software development practices?

files created then deleted at every second in tmp directory

How could indestructible materials be used in power generation?

Why is it a bad idea to hire a hitman to eliminate most corrupt politicians?

How to prevent "they're falling in love" trope

What is the most common color to indicate the input-field is disabled?

Unlock My Phone! February 2018



Different asm on Windows x64 from a CS:APP x86-64 Linux example function for swapping a long


Process command line in Linux 64 bitTracing call stack in disassembled codeThere aren't enough registers in x86-64 processorWhat is the correct use of multiple input and output operands in extended GCC asm?Why are rbp and rsp called general purpose registers?Does AMD have different CPU registers? How is “rax” different from “eax”?How to access a parameter passed on the stack on entry to a dll?Assember prompt for user input doesn't workHow can I store 1byte value in 64bit register only using 64bit registers?Memory allocation and addressing in Assembly













0















i am reading CS:APP 3rd edition (Ch3. pic 3.7 GAS assembly code)



long exchange(long* xp, long y)

long x = *xp;
*xp = y;
return x;


exchange:
movq (%rdi), %rax
movq %rsi, (%rdi)
ret


i wonder why below assembly code(1. asm : which is converted to nasm) does not work?



i had diassembled working c function to nasm assembly source code using c2nasm. it is quite different to original assembly.



main.cpp :



int main()

long a = 4;
// long b = exchange(&a, 3);
long b = exchange2(&a, 3);

printf("[a: %ld] [b: %ld]n", a, b);

return 0;



1.asm :



BITS 64

; default rel
default abs

global exchange2
section .text

exchange2:
;;; this code does not works
;;; program output -> [a: 4] [b: 0]
mov rax, [rdi]
mov [rdi], rsi
ret

;;; this code works, generated by c2nasm.
;;; program output -> [a: 3] [b: 4]
; push rbp
; mov rbp, rsp
; sub rsp, 16
; mov qword [rbp+10H], rcx
; mov dword [rbp+18H], edx
; mov rax, qword [rbp+10H]
; mov eax, dword [rax]
; mov dword [rbp-4H], eax
; mov rax, qword [rbp+10H]
; mov edx, dword [rbp+18H]
; mov dword [rax], edx
; mov eax, dword [rbp-4H]
; leave
; ret



EDIT: thanks!

working version for Windows x64 long long exchange(long long*, long long):



BITS 64

default rel

global _exchange2 ; Windows name-mangling prepends _ to C names
section .text

_exchange2:
mov rax, [rcx]
mov [rcx], rdx
ret









share|improve this question



















  • 1





    Windows uses a different calling convention than x86-64 System V ABI (used on BSD and Linux).Your version of exchange2 doesn't work because it is not compatible with Windows.64-bit calling convention. In that convention the first 4 integer class parameters are passed through RCX, RDX, R8, R9. Try mov eax, [rcx] mov [rcx], edx ret .On win64 longs are 32-bit so you can use the 32-bit registers instead of RAX and RDX

    – Michael Petch
    Mar 21 at 6:38







  • 1





    Your "working" version does a 64-bit copy, so it's only correct for long long, not long. Your current version writes 4 extra bytes outside the long destination. Also, there's no reason to use default abs, but it has no effect anyway because you aren't using any [symbol] addressing modes.

    – Peter Cordes
    Mar 21 at 14:02






  • 1





    default rel is preferred, I'd recommend always using that. IDK why you commented it out and used default abs (which is the default anyway). If c2nasm includes that by default, then it's just reminding you that you probably want to change the NASM default.

    – Peter Cordes
    Mar 22 at 1:50
















0















i am reading CS:APP 3rd edition (Ch3. pic 3.7 GAS assembly code)



long exchange(long* xp, long y)

long x = *xp;
*xp = y;
return x;


exchange:
movq (%rdi), %rax
movq %rsi, (%rdi)
ret


i wonder why below assembly code(1. asm : which is converted to nasm) does not work?



i had diassembled working c function to nasm assembly source code using c2nasm. it is quite different to original assembly.



main.cpp :



int main()

long a = 4;
// long b = exchange(&a, 3);
long b = exchange2(&a, 3);

printf("[a: %ld] [b: %ld]n", a, b);

return 0;



1.asm :



BITS 64

; default rel
default abs

global exchange2
section .text

exchange2:
;;; this code does not works
;;; program output -> [a: 4] [b: 0]
mov rax, [rdi]
mov [rdi], rsi
ret

;;; this code works, generated by c2nasm.
;;; program output -> [a: 3] [b: 4]
; push rbp
; mov rbp, rsp
; sub rsp, 16
; mov qword [rbp+10H], rcx
; mov dword [rbp+18H], edx
; mov rax, qword [rbp+10H]
; mov eax, dword [rax]
; mov dword [rbp-4H], eax
; mov rax, qword [rbp+10H]
; mov edx, dword [rbp+18H]
; mov dword [rax], edx
; mov eax, dword [rbp-4H]
; leave
; ret



EDIT: thanks!

working version for Windows x64 long long exchange(long long*, long long):



BITS 64

default rel

global _exchange2 ; Windows name-mangling prepends _ to C names
section .text

_exchange2:
mov rax, [rcx]
mov [rcx], rdx
ret









share|improve this question



















  • 1





    Windows uses a different calling convention than x86-64 System V ABI (used on BSD and Linux).Your version of exchange2 doesn't work because it is not compatible with Windows.64-bit calling convention. In that convention the first 4 integer class parameters are passed through RCX, RDX, R8, R9. Try mov eax, [rcx] mov [rcx], edx ret .On win64 longs are 32-bit so you can use the 32-bit registers instead of RAX and RDX

    – Michael Petch
    Mar 21 at 6:38







  • 1





    Your "working" version does a 64-bit copy, so it's only correct for long long, not long. Your current version writes 4 extra bytes outside the long destination. Also, there's no reason to use default abs, but it has no effect anyway because you aren't using any [symbol] addressing modes.

    – Peter Cordes
    Mar 21 at 14:02






  • 1





    default rel is preferred, I'd recommend always using that. IDK why you commented it out and used default abs (which is the default anyway). If c2nasm includes that by default, then it's just reminding you that you probably want to change the NASM default.

    – Peter Cordes
    Mar 22 at 1:50














0












0








0








i am reading CS:APP 3rd edition (Ch3. pic 3.7 GAS assembly code)



long exchange(long* xp, long y)

long x = *xp;
*xp = y;
return x;


exchange:
movq (%rdi), %rax
movq %rsi, (%rdi)
ret


i wonder why below assembly code(1. asm : which is converted to nasm) does not work?



i had diassembled working c function to nasm assembly source code using c2nasm. it is quite different to original assembly.



main.cpp :



int main()

long a = 4;
// long b = exchange(&a, 3);
long b = exchange2(&a, 3);

printf("[a: %ld] [b: %ld]n", a, b);

return 0;



1.asm :



BITS 64

; default rel
default abs

global exchange2
section .text

exchange2:
;;; this code does not works
;;; program output -> [a: 4] [b: 0]
mov rax, [rdi]
mov [rdi], rsi
ret

;;; this code works, generated by c2nasm.
;;; program output -> [a: 3] [b: 4]
; push rbp
; mov rbp, rsp
; sub rsp, 16
; mov qword [rbp+10H], rcx
; mov dword [rbp+18H], edx
; mov rax, qword [rbp+10H]
; mov eax, dword [rax]
; mov dword [rbp-4H], eax
; mov rax, qword [rbp+10H]
; mov edx, dword [rbp+18H]
; mov dword [rax], edx
; mov eax, dword [rbp-4H]
; leave
; ret



EDIT: thanks!

working version for Windows x64 long long exchange(long long*, long long):



BITS 64

default rel

global _exchange2 ; Windows name-mangling prepends _ to C names
section .text

_exchange2:
mov rax, [rcx]
mov [rcx], rdx
ret









share|improve this question
















i am reading CS:APP 3rd edition (Ch3. pic 3.7 GAS assembly code)



long exchange(long* xp, long y)

long x = *xp;
*xp = y;
return x;


exchange:
movq (%rdi), %rax
movq %rsi, (%rdi)
ret


i wonder why below assembly code(1. asm : which is converted to nasm) does not work?



i had diassembled working c function to nasm assembly source code using c2nasm. it is quite different to original assembly.



main.cpp :



int main()

long a = 4;
// long b = exchange(&a, 3);
long b = exchange2(&a, 3);

printf("[a: %ld] [b: %ld]n", a, b);

return 0;



1.asm :



BITS 64

; default rel
default abs

global exchange2
section .text

exchange2:
;;; this code does not works
;;; program output -> [a: 4] [b: 0]
mov rax, [rdi]
mov [rdi], rsi
ret

;;; this code works, generated by c2nasm.
;;; program output -> [a: 3] [b: 4]
; push rbp
; mov rbp, rsp
; sub rsp, 16
; mov qword [rbp+10H], rcx
; mov dword [rbp+18H], edx
; mov rax, qword [rbp+10H]
; mov eax, dword [rax]
; mov dword [rbp-4H], eax
; mov rax, qword [rbp+10H]
; mov edx, dword [rbp+18H]
; mov dword [rax], edx
; mov eax, dword [rbp-4H]
; leave
; ret



EDIT: thanks!

working version for Windows x64 long long exchange(long long*, long long):



BITS 64

default rel

global _exchange2 ; Windows name-mangling prepends _ to C names
section .text

_exchange2:
mov rax, [rcx]
mov [rcx], rdx
ret






assembly x86-64 nasm calling-convention win64






share|improve this question















share|improve this question













share|improve this question




share|improve this question








edited Mar 22 at 2:01







sailfish009

















asked Mar 21 at 6:22









sailfish009sailfish009

722816




722816







  • 1





    Windows uses a different calling convention than x86-64 System V ABI (used on BSD and Linux).Your version of exchange2 doesn't work because it is not compatible with Windows.64-bit calling convention. In that convention the first 4 integer class parameters are passed through RCX, RDX, R8, R9. Try mov eax, [rcx] mov [rcx], edx ret .On win64 longs are 32-bit so you can use the 32-bit registers instead of RAX and RDX

    – Michael Petch
    Mar 21 at 6:38







  • 1





    Your "working" version does a 64-bit copy, so it's only correct for long long, not long. Your current version writes 4 extra bytes outside the long destination. Also, there's no reason to use default abs, but it has no effect anyway because you aren't using any [symbol] addressing modes.

    – Peter Cordes
    Mar 21 at 14:02






  • 1





    default rel is preferred, I'd recommend always using that. IDK why you commented it out and used default abs (which is the default anyway). If c2nasm includes that by default, then it's just reminding you that you probably want to change the NASM default.

    – Peter Cordes
    Mar 22 at 1:50













  • 1





    Windows uses a different calling convention than x86-64 System V ABI (used on BSD and Linux).Your version of exchange2 doesn't work because it is not compatible with Windows.64-bit calling convention. In that convention the first 4 integer class parameters are passed through RCX, RDX, R8, R9. Try mov eax, [rcx] mov [rcx], edx ret .On win64 longs are 32-bit so you can use the 32-bit registers instead of RAX and RDX

    – Michael Petch
    Mar 21 at 6:38







  • 1





    Your "working" version does a 64-bit copy, so it's only correct for long long, not long. Your current version writes 4 extra bytes outside the long destination. Also, there's no reason to use default abs, but it has no effect anyway because you aren't using any [symbol] addressing modes.

    – Peter Cordes
    Mar 21 at 14:02






  • 1





    default rel is preferred, I'd recommend always using that. IDK why you commented it out and used default abs (which is the default anyway). If c2nasm includes that by default, then it's just reminding you that you probably want to change the NASM default.

    – Peter Cordes
    Mar 22 at 1:50








1




1





Windows uses a different calling convention than x86-64 System V ABI (used on BSD and Linux).Your version of exchange2 doesn't work because it is not compatible with Windows.64-bit calling convention. In that convention the first 4 integer class parameters are passed through RCX, RDX, R8, R9. Try mov eax, [rcx] mov [rcx], edx ret .On win64 longs are 32-bit so you can use the 32-bit registers instead of RAX and RDX

– Michael Petch
Mar 21 at 6:38






Windows uses a different calling convention than x86-64 System V ABI (used on BSD and Linux).Your version of exchange2 doesn't work because it is not compatible with Windows.64-bit calling convention. In that convention the first 4 integer class parameters are passed through RCX, RDX, R8, R9. Try mov eax, [rcx] mov [rcx], edx ret .On win64 longs are 32-bit so you can use the 32-bit registers instead of RAX and RDX

– Michael Petch
Mar 21 at 6:38





1




1





Your "working" version does a 64-bit copy, so it's only correct for long long, not long. Your current version writes 4 extra bytes outside the long destination. Also, there's no reason to use default abs, but it has no effect anyway because you aren't using any [symbol] addressing modes.

– Peter Cordes
Mar 21 at 14:02





Your "working" version does a 64-bit copy, so it's only correct for long long, not long. Your current version writes 4 extra bytes outside the long destination. Also, there's no reason to use default abs, but it has no effect anyway because you aren't using any [symbol] addressing modes.

– Peter Cordes
Mar 21 at 14:02




1




1





default rel is preferred, I'd recommend always using that. IDK why you commented it out and used default abs (which is the default anyway). If c2nasm includes that by default, then it's just reminding you that you probably want to change the NASM default.

– Peter Cordes
Mar 22 at 1:50






default rel is preferred, I'd recommend always using that. IDK why you commented it out and used default abs (which is the default anyway). If c2nasm includes that by default, then it's just reminding you that you probably want to change the NASM default.

– Peter Cordes
Mar 22 at 1:50













1 Answer
1






active

oldest

votes


















2














Your example is for the x86-64 System V ABI, used on Linux, OS X, and other non-Windows platforms (64-bit long, args in RDI, RSI, ...)



You compiled for Windows x64, which uses a different calling convention (args in RCX, RDX), and long is a 32-bit type.




Also you compiled with optimization disabled so the asm is full of store/reload noise. With optimization it would be basically the same but with different registers.



BTW, you can use gcc -O3 -masm=intel to get Intel-syntax assembly which is a lot closer to NASM syntax. (It's not NASM syntax though; it's MASM-like for addressing modes, and still uses GAS directives.)






share|improve this answer























    Your Answer






    StackExchange.ifUsing("editor", function ()
    StackExchange.using("externalEditor", function ()
    StackExchange.using("snippets", function ()
    StackExchange.snippets.init();
    );
    );
    , "code-snippets");

    StackExchange.ready(function()
    var channelOptions =
    tags: "".split(" "),
    id: "1"
    ;
    initTagRenderer("".split(" "), "".split(" "), channelOptions);

    StackExchange.using("externalEditor", function()
    // Have to fire editor after snippets, if snippets enabled
    if (StackExchange.settings.snippets.snippetsEnabled)
    StackExchange.using("snippets", function()
    createEditor();
    );

    else
    createEditor();

    );

    function createEditor()
    StackExchange.prepareEditor(
    heartbeatType: 'answer',
    autoActivateHeartbeat: false,
    convertImagesToLinks: true,
    noModals: true,
    showLowRepImageUploadWarning: true,
    reputationToPostImages: 10,
    bindNavPrevention: true,
    postfix: "",
    imageUploader:
    brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
    contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
    allowUrls: true
    ,
    onDemand: true,
    discardSelector: ".discard-answer"
    ,immediatelyShowMarkdownHelp:true
    );



    );













    draft saved

    draft discarded


















    StackExchange.ready(
    function ()
    StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f55274794%2fdifferent-asm-on-windows-x64-from-a-csapp-x86-64-linux-example-function-for-swa%23new-answer', 'question_page');

    );

    Post as a guest















    Required, but never shown

























    1 Answer
    1






    active

    oldest

    votes








    1 Answer
    1






    active

    oldest

    votes









    active

    oldest

    votes






    active

    oldest

    votes









    2














    Your example is for the x86-64 System V ABI, used on Linux, OS X, and other non-Windows platforms (64-bit long, args in RDI, RSI, ...)



    You compiled for Windows x64, which uses a different calling convention (args in RCX, RDX), and long is a 32-bit type.




    Also you compiled with optimization disabled so the asm is full of store/reload noise. With optimization it would be basically the same but with different registers.



    BTW, you can use gcc -O3 -masm=intel to get Intel-syntax assembly which is a lot closer to NASM syntax. (It's not NASM syntax though; it's MASM-like for addressing modes, and still uses GAS directives.)






    share|improve this answer



























      2














      Your example is for the x86-64 System V ABI, used on Linux, OS X, and other non-Windows platforms (64-bit long, args in RDI, RSI, ...)



      You compiled for Windows x64, which uses a different calling convention (args in RCX, RDX), and long is a 32-bit type.




      Also you compiled with optimization disabled so the asm is full of store/reload noise. With optimization it would be basically the same but with different registers.



      BTW, you can use gcc -O3 -masm=intel to get Intel-syntax assembly which is a lot closer to NASM syntax. (It's not NASM syntax though; it's MASM-like for addressing modes, and still uses GAS directives.)






      share|improve this answer

























        2












        2








        2







        Your example is for the x86-64 System V ABI, used on Linux, OS X, and other non-Windows platforms (64-bit long, args in RDI, RSI, ...)



        You compiled for Windows x64, which uses a different calling convention (args in RCX, RDX), and long is a 32-bit type.




        Also you compiled with optimization disabled so the asm is full of store/reload noise. With optimization it would be basically the same but with different registers.



        BTW, you can use gcc -O3 -masm=intel to get Intel-syntax assembly which is a lot closer to NASM syntax. (It's not NASM syntax though; it's MASM-like for addressing modes, and still uses GAS directives.)






        share|improve this answer













        Your example is for the x86-64 System V ABI, used on Linux, OS X, and other non-Windows platforms (64-bit long, args in RDI, RSI, ...)



        You compiled for Windows x64, which uses a different calling convention (args in RCX, RDX), and long is a 32-bit type.




        Also you compiled with optimization disabled so the asm is full of store/reload noise. With optimization it would be basically the same but with different registers.



        BTW, you can use gcc -O3 -masm=intel to get Intel-syntax assembly which is a lot closer to NASM syntax. (It's not NASM syntax though; it's MASM-like for addressing modes, and still uses GAS directives.)







        share|improve this answer












        share|improve this answer



        share|improve this answer










        answered Mar 21 at 6:32









        Peter CordesPeter Cordes

        133k18203341




        133k18203341





























            draft saved

            draft discarded
















































            Thanks for contributing an answer to Stack Overflow!


            • Please be sure to answer the question. Provide details and share your research!

            But avoid


            • Asking for help, clarification, or responding to other answers.

            • Making statements based on opinion; back them up with references or personal experience.

            To learn more, see our tips on writing great answers.




            draft saved


            draft discarded














            StackExchange.ready(
            function ()
            StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f55274794%2fdifferent-asm-on-windows-x64-from-a-csapp-x86-64-linux-example-function-for-swa%23new-answer', 'question_page');

            );

            Post as a guest















            Required, but never shown





















































            Required, but never shown














            Required, but never shown












            Required, but never shown







            Required, but never shown

































            Required, but never shown














            Required, but never shown












            Required, but never shown







            Required, but never shown







            Popular posts from this blog

            Kamusi Yaliyomo Aina za kamusi | Muundo wa kamusi | Faida za kamusi | Dhima ya picha katika kamusi | Marejeo | Tazama pia | Viungo vya nje | UrambazajiKuhusu kamusiGo-SwahiliWiki-KamusiKamusi ya Kiswahili na Kiingerezakuihariri na kuongeza habari

            Swift 4 - func physicsWorld not invoked on collision? The Next CEO of Stack OverflowHow to call Objective-C code from Swift#ifdef replacement in the Swift language@selector() in Swift?#pragma mark in Swift?Swift for loop: for index, element in array?dispatch_after - GCD in Swift?Swift Beta performance: sorting arraysSplit a String into an array in Swift?The use of Swift 3 @objc inference in Swift 4 mode is deprecated?How to optimize UITableViewCell, because my UITableView lags

            Access current req object everywhere in Node.js ExpressWhy are global variables considered bad practice? (node.js)Using req & res across functionsHow do I get the path to the current script with Node.js?What is Node.js' Connect, Express and “middleware”?Node.js w/ express error handling in callbackHow to access the GET parameters after “?” in Express?Modify Node.js req object parametersAccess “app” variable inside of ExpressJS/ConnectJS middleware?Node.js Express app - request objectAngular Http Module considered middleware?Session variables in ExpressJSAdd properties to the req object in expressjs with Typescript