首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

通过一篇文章让你了解什么函数

函数,也可以称为函数调用计算机在执行函数为其分配一块内存区域。每当一个函数被调用时,一个新就会被创建并压入调用中。...函数销毁 函数执行完毕并准备返回,其对应就会被销毁。销毁过程主要包括以下几个步骤: 释放内存:将所占用内存释放回系统。...ebp寄存器值被用作参考点,用于定位局部变量和参数。 ebp一般被用来指向当前函数底部。指在函数调用时,函数局部变量、参数和返回地址等保存在一块连续内存空间。...一个函数被调用时,它局部变量和函数参数等信息会被压入中。ESP寄存器指向地址,即最后被压入数据所在内存地址。使用ESP寄存器,可以轻松地在分配和释放内存。...在函数执行过程中,ESP寄存器会不断向下移动,以便为新局部变量分配空间。函数返回ESP寄存器会回到调用函数前位置,以释放内存空间。

15810

函数创建和销毁介绍

函数通过来实现控制转移、参数传递、局部变量分配和释放3个功能。 计算机有专门一块内存区域作为,每个函数都可以在申请一块内存区域作为函数存储空间,而该存储空间则被称为函数。...编写代码 详细解释创立和销毁过程 如下图所示,在区(计算机专门内存空间),每个函数在区申请一块内存空间,称为函数。在调用哪个函数,espebp就跑去维护哪个函数。...esp指向移动8个字节,上面的空间不属于。再把eax值放到ebp-20h当中。eax值就是出add函数委托到eax当中和,和放到局部变量c当中,这样返回值就带回来了。...函数调用时参数如何传递没有调用函数时候已经pushpush把两个参数从右向左开始压压进去了,当真的进入形参函数时候,其实在add函数里,通过指针偏移量找回了形参。...函数返回值如何带会调用之前就把call指令下一条指令地址记住了,往回返时候,就可以跳转到call指令下一条指令地址,返回值通过寄存器方式调用回来。 欢迎交流!

10310
您找到你想要的搜索结果了吗?
是的
没有找到

函数调用如何变化

大家都知道函数调用是通过来实现,而且知道在中存放着该函数局部变量。但是对于实现细节可能不一定清楚。本文将介绍一下在Linux平台下函数如何实现。...结构 函数在调用时候都是在空间开辟一段空间以供函数使用,所以,我们先来了解一下通用结构。...函数空间主要是由这两个寄存器来确定程序运行时,指针rsp可以移动指针和指针rbp一次只能存储一个地址,所以,任何时候,这一对指针指向同一个函数结构。...而指针rbp移动,访问元素可以用-4(%rbp)或者8(%rbp)访问%rbp指针下面或者上面的元素。...首先,函数开辟了16字节空间,存储定义3个int型变量,建立了main函数。 接着,会给三个变量进行赋值。 以下4行代码进行参数传递。

3.1K21

深入理解计算机系统(3.7)------过程(函数调用原理)

也就是说寄存器 %ebp指针,寄存器 %esp指针。   程序执行时,指针可以移动,因此大多数信息访问都是相对于指针。 ?   ...各位需要知道,每一个都建立在调用下方(也就是地址递减方向),调用者执行完毕,这一段会被释放。...还有一点很重要,%ebp和%esp值指示着两端,而指针会在运行时移动,所以大部分时候,在访问存储器时候会基于指针访问,因为在一直移动指针无法根据偏移量准确定位一个存储器位置。   ...相反,如果将指针加上一定值,也就是向上移动,那么就相当于压缩了长度,也就是说内存释放了。需要注意,上面的一切内容,都基于一个前提,那就是指针在过程调用当中不会移动。...pushl %ebp movl %esp, %ebp   ②、建立起来就是为被调用者准备调用者使用,需要给临时变量分配预留内存,这一步一般经过下面这样汇编代码处理

1.4K50

初识函数创建与销毁(笔记)

函数调用另一个函数调用者会将一些数据(如函数参数)压入堆栈中,ESP寄存器会随之向下移动,指向新堆栈顶部。在函数返回后,又会通过调整ESP寄存器值来释放堆栈空间。 4....函数被调用时,编译器会在动态创建函数,并在其中分配存储局部变量和参数空间。...Add函数被调用时,编译器会执行以下步骤来创建函数: 1. 首先,编译器将函数返回地址和旧指针(EBP)保存在。 2....调整顶指针 紧接着,通过执行 MOV 指令,让顶指针(ESP)指向 EBP 原先指向位置。这样做目的是为了释放函数所占用内存空间。 3....调用函数,在调用之前,用push把参数从右向左压, 进入形参函数,在函数桢里通过指针偏移量找到形参 4.形参和实参是什么关系?

14510

指针&& 指针详解

在函数执行过程中,指针esp会随着数据和出移动,因此函数中对大部分数据访问都基于指针%ebp进行。?对于函数A调用函数B情况,传递给B参数包含在A中。...A调用B,函数A返回地址(调用返回后继续执行指令地址)被压入中,中该位置也明确指明了A结束处。而B则从随后部分开始,即图中保存指针(ebp地方开始。...调用指令CALL作用是把返回地址压入中并且跳转到被调用函数开始处执行。返回地址程序中紧随调用指令CALL后面一条指令地址。因此被调函数返回就会从该位置继续执行。...(执行完此指令后,指针esp会向下移动,指向保存原ebp空间地方)4 movl %esp,%ebp (把数据(原ebp值)压入后,指针esp会向下移动4个字节指向放原ebp空间,执行此句指令意义就...从以上分析可知,C语言在调用函数在堆栈临时存放被调函数参数值,即C语言传值类语言,没有直接方法可用来在被调用函数中修改调用者变量值。

8.2K30

【C语言加油站】函数创建与销毁

为什么创建局部变量如果不初始化,局部变量值会是随机值? 函数怎么传参?传参顺序又是什么? 形参和实参有什么关系? 函数如何调用调用结束后又是如何返回?...*[bp]: 基址指针寄存器 *[sp]: 堆栈指针寄存器 *[ebp]: 底指针 *[esp]: 顶指针 接下来我们就通过下面这个代码来介绍一下 ebpesp 它们如何创建和维护函数...——四个字节 //dword ptr——内存单元为四个字节长度 //ebp-8——地址名 //2——移动对象 这里意思就是将2这个值移动ebp-8这个地址; 变量b dword ptr [ebp...-14h],3 //dword——四个字节 //dword ptr——内存单元为四个字节长度 //ebp-14h——地址名 //3——移动对象 这里意思就是将3这个值移动ebp-14h这个地址;...,这样我们在调用完函数后能够通过pop指令在释放Add函数函数找到main函数底地址。

48830

X86如何实现函数调用

| <----- esp |----------------------| low address 三、x86函数调用 需要调用另一个函数...调用函数发生,caller执行逻辑会跳转到callee,拿到结果后,在跳转会caller。这就需要改变下面几个寄存器值: eip指令指针,需要改成指向callee指令。...ebpesp 当前分别指向caller顶部和底部。两个寄存器都需要更新为 指向callee顶部和底部。 函数返回,需要恢复寄存器中旧值,才可以返回caller。...请注意,当我们将参数压入堆栈esp 会递减。参数以相反顺序压入堆栈。(上面高地址) step2:旧eip入eip(rip)压入堆栈。...step4:将旧ebp step5:ebp向下移动指向新顶部 这就是mov %esp %ebp含义: step6:esp向下移动 通过sub espesp地址–) 来为新分配新空间

2.7K20

X86函数调用模型分析

| <----- esp |----------------------| low address 三、x86函数调用 需要调用另一个函数...ebpesp 当前分别指向caller顶部和底部。两个寄存器都需要更新为 指向callee顶部和底部。 函数返回,需要恢复寄存器中旧值,才可以返回caller。...请注意,当我们将参数压入堆栈esp 会递减。参数以相反顺序压入堆栈。(上面高地址) image.png step2:旧eip入eip(rip)压入堆栈。...image.png step4:将旧ebp step5:ebp向下移动指向新顶部 这就是mov %esp %ebp含义: image.png step6:esp向下移动 通过sub...image.png step11:从堆栈中删除参数 继续讲堆栈参数弹出到寄存器,然后删除esp顶以下元素。顶以下元素已经不在中,没有意义。

1.1K20

恶意样本对抗回溯检测机制套路浅析

这样,无论 ESP 如何变化,以 EBP 值为基准能够安全访问到相关函数局部变量、参数、返回地址,这就是 EBP 寄存器作为指针作用。...根据上面结构和 CALL 指令操作可知,在将属于调用函数 EBP 值压之前,ESP 指向地址存储由 CALL 指令压调用函数中调用位置下一条指令地址(原 EIP)。...和 ESP 值均不在该线程堆栈范围之中,也就是说:要么 TEB 中堆栈范围被修改了,要么当前所处堆栈被移动到自己分配内存里了,也就是说,被“截断”并“移动”了。...在 ShellCode 代码执行即将完成,应会再将 ESPEBP 值还原回原来真正地址,避免弹进入上面未知内存区域导致程序异常。...mov [eax], ebx ; 修正调用ebp中位置 } // 执行正式函数体代码 simplesubfunc(); // 恢复指针到原位置并释放内存

75620

C语言函数详解

一个由系统自动分配内存空间,譬如调用函数、创建临时变量内存空间创建与销毁。 用于存储函数内部局部变量、方法调用、函数传参数值等。 由高地址向低地址生长。...每调用一次函数便会创建一个独立中存放函数中必要信息,如局部变量、函数传参、返回值等。 函数运行完毕将会销毁。 ​ 下面进入主题,图解函数创建与销毁过程。...在调试过程中将转到反汇编,便能直观看到main函数创建过程。首先需明确,函数由寄存器esp,ebp维护。...2.esp值传递给ebp。 3.esp减去0E4h:由于先使用高地址后使用低地址,减去一个值意味着esp指针向低地址移动了0E4h个地址,此处便开辟了main函数。...,ebx,随后将ebp赋给esp并弹出ebp,最后执行ret指令返回到调用Add函数call指令下一地址,在执行ret指令实际已弹出After call,以执行指令 add esp,8,此时esp

2K20

论 : 递归与式访问,如何实现所有递归操作(函数调用底层篇)

一篇 : 论 : 递归与式访问,如何实现所有递归操作(基础知识篇) 2.函数调用底层篇(了解递归调用硬件实现) 一开始,main函数没有调用add之前他如下图,当然,下面只是简略介绍...调用add函数时候main 将 自己变量拷贝后压入中,我们称之为“形参” ?...上图中变量c 和变量d拷贝就是所谓”形参“ 接下来将main函数ebp地址压入中保存,以便add函数调用完之后恢复main在内存 ?...2.让esp = esp - X ; X一个位移量,表示esp移,esp这个位移量差不多是add函数大小。(还有一些寄存器之类会占用空间,忽略不计) 如图: ?...而从 ebp + 8 和 ebp + 12 读取到正好main函数形参 ? 通信总结1. 子函数直接调用父函数形成,访问父函数 这是子向父索求信息,那么父向子索取信息呢?

85530

C语言函数调用结构

地址空间与物理内存 (1)地址空间与物理内存两个完全不同概念,真正代码及数据都存在物理内存中。...状态值:保存前顶部和底部(实际只保存前底部,前顶部可以通过平衡计算得到),用于在本被弹出后恢复出上一个。...(1)这里首先main函数建立自己结构;main()函数由__tCRTStartup()函数调用,所以mainCRTStratup()函数调用__tmainCRTStra()函数时候就会从为...这其中也许有进、出动作,指针ESP也会上下移动,但EBP保持不变。这意味着我们可以一直用[EBP+…]找到第一个参数,而不管在函数中有多少进出动作。...紧接着调用者执行完毕将消除结构,调用pop指令。 在把程序控制权返还给调用者前,被调用者foo必须先把返回值保存在EAX寄存器中。其次,foo必须恢复EBX,ESI和EDI寄存器值。

1.4K30

汇编角度看函数堆栈调用

从头开始还是从调用之后开始? (3)返回值如何带出来?...esp:专门用作堆栈指针,被形象称为顶指针,堆栈顶部地址小区域,压入堆栈数据越多,esp就越来越小。在32位平台esp每次减少4个字节。 ebp:堆栈底指针。...2.0040104E mov esp,ebp使得被调用函数回退。此时空间内容还存在。 3.pop ebp 两个动作,出,并将出值赋给ebp。...(3)返回值如何带出来? 答: (1)形参内存空间开辟和清理调用方执行。 (2)主函数调用函数后执行执行调用之后代码,是因为调用方在进行调用过程中,将下一行指令地址压。...所以调用完成之后调用之后开始,不会从头开始。 (3)返回值由累加寄存器eax带出来返回值字节数小于等于四个自己)。

60820

你知道函数创建和销毁吗?

一、概述 函数内存区为被调函数开辟一块空间,里面用来存放该函数中定义变量等东西,函数运行完毕将被销毁。...edx "数据寄存器’,在进行乘、除法运算,可作为默认操作数参数参与运算 esp 指针寄存器,存放函数顶地址 ebp 指针寄存器,存放函数底地址 espebp这两个寄存器中存放地址...a,即b指向a sub a num a值减去num,即a向低地址移动 lea(load effective adress) 加载有效地址(在示例中理解) 四、函数创建 所有函数调用都会在内存里面的区创建函数...赋值给ebp,即将esp移动ebp位置 sub esp,0E4h //将esp向低地址移动0E4h个字节位置 push ebx...首先看main函数 使用空间由高地址到低地址 正在调用哪个函数,espebp就维护哪个函数,在这里,我们调用main函数,那么就维护main函数。

11810

C函数原理

, 在函数实现位置,首先将ebp,这个时候ebp保存调用底地址。...然后进行了一句pop ebp将之前存储ebp内容还原,这个时候ebp指向调用函数底位置。...函数调用完成后,ebp还原到调用底部,这个时候不可能再使用ebp间接寻址方式来找到在上一个函数中定义局部变量了,及时我们及时保存了这个变量地址,也有可能在调用下一个函数,这个地址所在内存变成了下一个函数函数...首先在调用这个函数方式也是从右至左一次压,但是函数调用完毕,返回只要一句ret,而在main函数中多了一句add esp, 8从这个地方可以很明显看出,最后参数所在空间释放由main函数释放...,也就是函数释放调用方来完成。

58330

5.5 汇编语言:函数调用约定

说到函数我们必须要提起调用约定这个名词,而调用约定离不开支持,内存一块特殊存储空间,遵循先进后出原则,使用push与pop指令对空间执行数据压入和弹出操作。...顶指针esp小于底指针ebp,就形成了中可以寻址数据有局部变量,函数返回地址,函数参数等。...不同两次函数调用,所形成也不相同,由一个函数进入另一个函数,就会针对调用函数开辟出其所需空间,形成此函数独有,而调用结束,则清除掉它所使用空间,关闭,该过程通俗讲叫做平衡...首先先来写一段非函数版堆栈使用案例,案例中模拟了编译器如何生成Main函数以及如何初始化和使用流程,笔者通过自己理解写出了Debug版本一段仿写代码。...函数并不会被释放所以它也是稳定调用function函数只需要将首地址通过push eax方式传递给function函数内,并在函数内通过mov ecx,dword ptr [ ebp +

24320

C语言——F函数创建和销毁

3、函数调用时参数如何传递?传参顺序怎样? 4、函数形参和实参分别是怎样实例化? 5、函数返回值如何带回? 三、函数创建和销毁解析 1、什么?...2、这块空间维护使用了2个寄存器: espebpebp 记录地址, esp 记录地址。 3、函数创建和销毁过程,在不同编译器实现方法大同小异。...将求出和放在 eax 寄存器中准备带回。 3.5、函数销毁 函数调用要结束返回时候,前面创建函数也开始销毁。 那具体怎么销毁呢?我们看一下反汇编代码。...1、局部变量如何创建? 答:一个新函数被创建,并将局部变量推入到函数空间,然后为其分配内存空间。 2、为什么局部变量不初始化内容随机?...同时,初始化为确切内容可以说成覆盖掉了0xCC。 3、函数调用时参数如何传递?传参顺序怎样

8410

你一定要搞明白C函数调用方式与原理

正文 这篇blog试图讲明一个c函数被调用时,一个(stack frame)如何被建立,又如何被消除。...让我们一步步地看一下在c函数调用过程中,一个如何建立及消除。 函数调用调用动作 在我们例子中,调用main,它准备调用函数foo。...图 2 被调用者在函数调用动作 函数foo,也就是被调用者取得程序控制权,它必须做3件事:建立它自己,为局部变量分配空间,最后,如果需要,保存寄存器EBX,ESI和EDI值...首先foo必须建立它自己EBP寄存器现在正指向main某个位置,这个值必须被保留,因此,EBP。然后ESP内容赋值给了EBP。...图 4 foo函数体现在可以执行了。这其中也许有进、出动作,指针ESP也会上下移动,但EBP保持不变

3.2K30

5.5 汇编语言:函数调用约定

说到函数我们必须要提起调用约定这个名词,而调用约定离不开支持,内存一块特殊存储空间,遵循先进后出原则,使用push与pop指令对空间执行数据压入和弹出操作。...顶指针esp小于底指针ebp,就形成了中可以寻址数据有局部变量,函数返回地址,函数参数等。...不同两次函数调用,所形成也不相同,由一个函数进入另一个函数,就会针对调用函数开辟出其所需空间,形成此函数独有,而调用结束,则清除掉它所使用空间,关闭,该过程通俗讲叫做平衡...V:类Linux系统默认约定,前八个参数放入(RDI,RSI, RDX, RCX, R8, R9),剩下参数压保存.首先先来写一段非函数版堆栈使用案例,案例中模拟了编译器如何生成Main函数以及如何初始化和使用流程...函数并不会被释放所以它也是稳定调用function函数只需要将首地址通过push eax方式传递给function函数内,并在函数内通过mov ecx,dword ptr [ ebp +

26520
领券