Why the C language (function call) requires a stack, and assembly language does not require

Source: Internet
Author: User
Tags stack pop

Turn from: Uboot in Start.s Source code of the instruction level of the detailed analysis Green-waste
Why the C language (function call) requires a stack, and assembly language requires a stack
Before looking at a lot of uboot analysis, which has said to the C language to run, ready to stack.
And in Uboot's START.S assembly code, we also see a stack pointer initializing this action for system initialization. However, it was never seen that the system initialized to initialize the stack, which correctly assigned the stack pointer sp, but never saw anyone explain why the stack was initialized. So, the next step is to try to explain why the stack is initialized, namely:
Why does a C-language function call use the stack, but the assembly does not need to initialize the stack.
To understand this problem, first understand the role of the stack.
The role of the stack, to be explained in detail, to a very long length, so here is just a brief introduction.
In general, the function of a stack is to save the field/context and pass parameters.
4.6.1. Save Site/Context
Scene, meaning is equivalent to the crime scene, there are always some scene situation, to record down, otherwise destroyed by others, you will not be able to restore the scene. And here said the scene, refers to the CPU when running, using some registers, such as R0,R1, and so on, for these register values, if you do not save and jump directly to the child function to execute, it is likely to be destroyed, because other function execution also need to use these registers. Therefore, before the function call, these registers and so on should be kept in the field temporarily, and so on after the call function is finished returning, then restore the scene. This allows the CPU to continue to execute correctly. In the computer, you can often see the word context, the corresponding English is the context.
4.6.1.1. What's called context contexts
Save the scene, also called the Save context.
Context, English is called context, is the above article, and the following article, that is, with you at the moment, the current CPU operation has a relationship to the content, that is, those you use to register. So, and above the scene, is a meaning.
Save the value of the register, generally with the push instruction, the corresponding value of some registers, one by one onto the stack, the corresponding value is pressed into the stack, that is, the so-called pressure stack. Then when the child function is called to complete the execution, then call the pop, the stack of values, assigned to the corresponding ones you just started to use the register, the corresponding value from the stack popped out, called the stack.
The stored register, also includes the value of LR (because the BL command to run the jump, then the value of the previous PC is present in the LR), and then after the completion of the subroutine, the value of the LR in the stack pop out, assigned to the PC, so that the child function to achieve the correct return.
4.6.2. Passing Parameters
C language running function calls, often passed to the function called some parameters, for these C-level parameters, the compiler is translated into assembly language, it is necessary to find a place to store, and let the called function can access, otherwise it will not be able to implement the parameters passed. To find a place to put, in two cases.
One case is that the parameters passed by itself are very few, and the parameters can be passed through the register.
Because in the previous save the scene of the action, has been saved the corresponding register value, then, these registers is idle, can let us use, that can put parameters, and the parameters of the situation attaining, enough to store parameters, such as the parameters have 2, then use R0 and R1 storage can. (for parameter 1 and parameter 2, which one is in R0, which is placed in R1, and APCs in the "Pass/return parameters between function calls" related, APCs there will be a detailed convention.) Interested in themselves to study. )
But if there are too many arguments and the registers are not enough, then you have to put the extra arguments in the stack. That is, you can use the stack to pass all the extra parameters that the registers don't fit.
4.6.3. An example of how the C-language function call uses the stack's
The effect of the stack on the above explanation is somewhat abstract, and here is an example to illustrate briefly, it is easy to understand:
Arm-inux-objdump–d u-boot > Dump_u-boot.txt
You can get the Dump_u-boot.txt file. The file is in, containing the executable assembly code of the program in U-boot, where we can see the source code of the C language function, which corresponds to those assembly code.
The following is a compilation code of two functions,
One is Clock_init,
The other is not clock_init in the same C source file, and the other one is Copycode2ram:
33D0091C <copycode2ram>:
33d0091c:e92d4070 Push {r4, R5, R6, LR}
33d00920:e1a06000 mov r6, r0
33D00924:E1A05001 mov R5, r1
33D00928:E1A04002 mov r4, r2
33D0092C:EBFFFFEF BL 33d008f0 <bBootFrmNORFlash>
... ...
33d00984:ebffff14 BL 33D005DC <nand_read_ll>
... ...
33d009a8:e3a00000 mov r0, #0; 0x0
33d009ac:e8bd8070 Pop {r4, R5, R6, PC}
33d009b0 <clock_init>:
33d009b0:e3a02313 mov r2, #1275068416; 0x4c000000
33D009B4:E3A03005 mov r3, #5; 0x5
33d009b8:e5823014 STR R3, [R2, #20]
... ...
33D009F8:E1A0F00E mov pc, LR
(1) Clock_init part of the code
You can see the first row of the number of Taipa:
33d009b0:e3a02313 MOVR2, #1275068416; 0x4c000000
There is no push instruction that we expect, not to put the value of some registers on the stack. This is because we clock_init back part of the content, the use of R2,R3 and other registers, and the previous call Clock_init used before the register r0, there is no conflict, so here can not push to save the value of the return class register, but there is a register to note that is R14 , that is, LR, which is called Clock_init in front of the time, with the BL instruction, so it will automatically transfer the value of the PC to the value of the LR, so do not need the push command to save the value of the PC to the stack. And the last line of the Clock_init code:
33d009f8:e1a0f00e MOVP C, LR
Is our common MOV pc, LR, puts the value of LR, that is, the value of the PC before saving the number of Taipa calls, assigns the value to the current PC,
This enables the correct return of the number of the Taipa, which returns to the location of the next instruction when the number of the Taipa is called.
This way the CPU can continue to execute the rest of the code in the previous number of Taipa.
(2) Copycode2ram part of the code
Its first line:
33d0091c:e92d4070 Push {r4, R5, R6, LR}
It is what we expect, with the push command, to save the r4,r5,r and LR.
Use push to save R4,R5,R6, that is because the so-called preservation site, after the subsequent function return time to restore the scene,
and using push to save LR, that's because there are other number of Taipa calls in this number of Taipa:
33D0092C:EBFFFFEF BL 33d008f0 <bBootFrmNORFlash>
... ...
33d00984:ebffff14 BL 33D005DC <nand_read_ll>
... ...
It also uses the BL directive, which changes the value of LR when we first daemons into clock_init, so we'll use push to save it for the time being.
And correspondingly, the last line of Copycode2ram:
33d009ac:e8bd8070 Pop {r4, R5, R6, PC}
is to put the value of the previous push, to pop out, Christmas to the corresponding register, where the last one is to start the value of the LR of the push, pop out to assign to the PC, because the function returned.
In addition, we note that the penultimate line in Copycode2ram is:
33d009a8:e3a00000 Movr0, #0; 0x0
is to assign 0 to the R0 register, this is what we call the return value of the pass, is through the R0 register.
The return value here is 0 and corresponds to "return 0" in the source code of C astonished.
For which register is used to pass the reusing return value: Of course you can also use other temporarily idle unused registers to pass the return value, but these processing methods, itself is based on the arm of the APCs register of the use of the contract design, you'd better not casually change the way of use, preferably in accordance with its agreement to deal with, This procedure is more consistent with the specification.

Attached: what is APCS
The Apcs,arm procedure invocation standard (ARM Procedure call standards) provides a mechanism for a compact authoring routine that can be interwoven with other routines. The most significant point is that there is no clear limit to where these routines come from. They can be compiled from C, Pascal, or it can be written in assembly language.
The APCS defines:
>> restrictions on the use of registers.
>> conventions for using stacks.
>> Pass/Return parameters between function calls.
>> can be a "backtracking" format of a stack-based structure to provide a list of functions (and given parameters) from the point of failure to the entry of the program.

Why the C language (function call) requires a stack, and assembly language does not require

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.