您现在的位置是: 首页 > 教育比较 教育比较
函数高考题汇编,高考函数数学题
tamoadmin 2024-07-16 人已围观
简介1.求汇编中函数的调用方法2.vb 汇编 jmp 函数问题3.求易语言 调用函数()push()这类的汇编操作源码4.用汇编语言编写一个二次函数f(x)=3x^x+2x+6,然后嵌入到C++中5.汇编的问题在网上搜索Equ this type,会找到这个实验内容。其实认真读一下就知道这段代码做了一个连加,再除以10,并显示商和余数。第一段,REPT是宏汇编6.0之前的语法,之后改名为REPEAT,
1.求汇编中函数的调用方法
2.vb 汇编 jmp 函数问题
3.求易语言 调用函数()push()这类的汇编操作源码
4.用汇编语言编写一个二次函数f(x)=3x^x+2x+6,然后嵌入到C++中
5.汇编的问题
在网上搜索Equ this type,会找到这个实验内容。其实认真读一下就知道这段代码做了一个连加,再除以10,并显示商和余数。
第一段,REPT是宏汇编6.0之前的语法,之后改名为REPEAT,语法为:
REPEAT constexpr
statements
ENDM
如下rept宏代码定义了1到9(通过循环db count实现):
count=1
rept 9
db count
count=count+1
endm
至于Table EQU this type这一句,找遍了文档400多个this,没有一个是这样用的,代码中也未体现出这个Table的作用,因此暂且理解为一个无用的EQU。
第二段lea取得b(自己数一数,大小为21字节)的起始地址后,加21,这样直接跳到了db count,也就是到了db 1,db 2,....这些数据,做加法,除法,保存商和余数,把结果转化为ascii符,显示,退出程序,基本上就这么多了。
求汇编中函数的调用方法
图1
图2
既然你都没学过汇编,由何必纠结与这些内存里的内容?
高级语言看到的东西(语句)是无法详细说明内存内容的,
其中根本原因是,在函数调用与参数传递过程中,编译器会自行进行优化,即使是同一个调用语句,如果编译选项中优化等级不同,其发送的汇编指令就不同,操作内存就不同。
第一幅图没意思,说图2,显示中右侧有明显两个烫烫区域,高地址一块属於main主函数(过程)的栈帧,低地址属於man函数调用产生的栈帧,若不懂什麽是栈帧,去百度或找些资料看看,某些地方也称为“活动记录”,ebp寄存器为活动记录指针。
对於函数max栈帧的产生过程也即函数max的调用过程如下:
一、参数入栈,如图2中的x,y值,入栈顺序c编译器默认是从右至左,其为值传递,做事是a、b值的拷贝;
二、返回地址入栈,
三、ebp入栈,即保存主函数的栈帧指针,
四、ebp栈帧寄存器值改为指向保存“三”中ebp内存其中,以此为界,低地址为max的局部变量等内存区域,高地址部份除了一、二步的内容为当前栈帧也属於max的栈帧内容外,其他为main函数的栈帧内容。
可见max局部变量只有z一个,x、y为何不是局部变量(高级语言而言,其是,但严格而言其不是,其只是函数接收的参数,各种缘由要解释也一大堆理论,编译器不同也会不同)
至於返回时为何有两个z值的拷贝,一个值z局部变量,另一份值拷贝,要看编译器发送代码的规则而定,也即有些是通过寄存器返回值的也就不必那麼麻烦,有些是通过堆栈返回结果的等等,可通过汇编指令窗口分析其返回结果的机制。
vc有反汇编窗口,可以一目了然。
若不学汇编就不必纠结与底层与细节,即使你学了汇编还是得有相关理论才知道是怎麼一回事,
可以刨根问题,但要有多大锅,放多少米,多涉略,阿门。。。
vb 汇编 jmp 函数问题
我也是查找的,请别介意:
准备执行
在主程序中每次调用函数时,先依次把各参数以相反的顺序入栈;
然后call func_name, 这里call要做两件事: 一是把函数的返回地址入栈,二是让指令执行指针%eip指向函数开始处。
开始执行
现在函数要开始执行了,但它执行函数代码前还要做一点小事,首先把原来的基地址寄存器%ebp值入栈,因为在程序执行中%ebp要另作它用, 接着堆栈指针%esp的值复制给%ebp, 此后在函数执行中%ebp一直保持不变,可以由此寻址获得函数参数。
pushl %ebp
movl %esp, %ebp
下面开始执行函数代码了。函数先要把它的局部变量保存在栈中,这很简单。比如要保存一个long型数据,只要把%esp指针向下移动4个字节(因为栈增长方向是由高地址到低地址),再根据%esp把该数据移入. 下面是保存两个局部变量long后的堆栈内容:
Parameter #N <--- N*4+4(%ebp)
...
Parameter 2 <--- 12(%ebp)
Parameter 1 <--- 8(%ebp)
Return Address <--- 4(%ebp)
Old %ebp <--- (%ebp)
Local Variable 1 <--- -4(%ebp)
Local Variable 2 <--- -8(%ebp) and (%esp)
从上可以看出通过%ebp基地址寻址可以访问所有的函数参数和局部变量. 当然也可以不用
%ebp而用其它的寄存器进行同样的基地址寻址。但对于x86结构使用%ebp寄存器可能会更
快一点。
执行结束:
现在函数执行要结束了,在它返回之前,还要做下面几件事:
1. 把函数的返回值存放在通用寄存器%eax中,供外部使用
2. 把%esp指向函数开始执行的位置, 即movl %ebp,%esp
3. 在函数返回ret之前,要还原ebx, 即popl %ebp
movl %ebp, %esp
popl %ebp
ret
从上也可以看出,当%esp指向函数开始执行的位置后,局部变量也就没有意义了(因为此时
esp指向的栈地址高于那些局部变量的地址)。
函数执结束ret返回后,要把call时push的所有函数参数也pop出来(或者直接在%esp上加参数的个数的4倍,如果不需要再使用这些参数值的话)。
addl $8, %esp # 因为有两个参数8个字节
下面是一段代码power.s,计算2^3+5^2
# ==================== asm code begin ===================
#PURPOSE: Program to illustrate how functions work. This program will compute
#the value of 2^3+5^2
.section .data
.section .text
.global _start
_start:
pushl $3
pushl $2
call power # 调用power(2,3)函数
addl $8, %esp # 函数结束后,堆栈指针%esp要返回到参数之前,即加上4*2
pushl %eax # 把第一次计算的power(2,3)的结果(保存在%eax中),入栈保存
pushl $2
pushl $5
call power #调用power(5,2)
addl $8, %esp # 函数结束后,堆栈指针%esp要返回到参数之前,即加上4*2
popl %ebx #从堆栈中取出第一次计算的power(2,3)结果,放在%ebx中
addl %eax, %ebx # 两者相加保存在%ebx中
movl $1,%eax
int $0x80
#系统调用结束,调用号保存在%eax中(为1),返回值保存在%ebx中(为计算结果33)
# function long power(long a,long b) =a^b
.type power, @function
power:
pushl %ebp # %ebp入栈
movl %esp, %ebp # %ebp中保存%esp值,用作下面的基地址寻址
subl $4, %esp
movl 8(%ebp) ,%ebx #把参数a的值赋给%ebx
movl 12(%ebp) ,%ecx #把参数b的值赋给%ecx
movl %ebx, -4(%ebp) #下面是对a做b次循环计算,把 中间结果存放在-4(%ebp) 中
power_loop_start:
cmpl $1, %ecx
je end_power
movl -4(%ebp),%eax
imull %ebx, %eax
movl %eax, -4(%ebp)
decl %ecx
jmp power_loop_start
end_power:
movl -4(%ebp), %eax # 返回值给%ebx
movl %ebp, %esp # %esp回到函数执行开始位置
popl %ebp # ret前要还原函数执行初的%ebp值
ret
#================= asm code end ====================
#as power.s -o power.o
#ld power.o -o power
#./power
#echo $?
33
求易语言 调用函数()push()这类的汇编操作源码
好厉害!
VB可以用ASM语言吗?
第一次听说
有 With asm 。。。这样的语句
具体没做过,没有发言权。
不过,一般 asm的调用都是用的 INVOKE 伪代码,(具体可能还根据传递参数声明的方式而定)
PUSH 。。。。来压栈传递参数,方式的,
JMP 。。。
之前,汇编要生成,链接等操作。不是简单一个语句就OK的。
所以,VB有一个 Declare 语句,专门为dll调用准备的。MSDN 有语法大全。不必买书。
如果用的是 VB9.0 (VB.NET),还有其他方式。
用汇编语言编写一个二次函数f(x)=3x^x+2x+6,然后嵌入到C++中
超级模块源码。
置汇编代码()
push(0)
push(1)
push(十六到十(“428E0000”))
push(十六到十(“431D0000”))
mov_ecx(十六到十(“77758788”))
mov_eax(十六到十(“00442840”))
call_eax()
ret()
调用函数(进程ID,取汇编代码())
扩展资料:
函数作为另一个函数调用的实际参数出现。这种情况是把该函数的返回值作为实参进行传送,因此要求该函数必须是有返回值的。例如: printf("%d",max(x,y)); 即是把max调用的返回值又作为printf函数的实参来使用的。
在函数调用中还应该注意的一个问题是求值顺序的问题。所谓求值顺序是指对实参表中各量是自左至右使用呢,还是自右至左使用。对此,各系统的规定不一定相同。介绍printf 函数时已提到过,这里从函数调用的角度再强调一下。
百度百科-函数调用
汇编的问题
#include<iostream.h>
int mycall(int x)
{
_asm
{
mov eax,x
imul eax,x
imul eax,3
mov ebx,x
imul ebx,2
add eax,ebx
add eax,6
mov x,eax
}
return x;
}
int main()
{
int a;
cin>>a;
cout<<mycall(a)<<endl;
}
希望能帮到你!
push ebp //保存ebp,
sub esp,80h //在堆栈中分配局部变量,大小是80h
mov ebp,esp //用ebp来指示当前函数局部变量、当前函数参数和当前函数返回地址
mov [ebp+04h],eax //[ebp+04h]保存当前函数的返回地址,这里修改了返回地址,执行完当前函数后,会返回到eax所指向的地址继续执行。
push 0 //压入函数参数
push 'Ayra' //压入函数参数
push 'rbiL' //压入函数参数
push 'daoL' //压入函数参数
push esp //压入函数参数
push edi //压入函数参数
call dword ptr ss:[ebp+04h] //Call(eax)。调用函数,该函数的地址是eax指示,[ebp+04h]=eax
mov [ebp+08h],eax //得到call(eax)的返回结果,写入到[ebp+08h]中,这个是当前函数的参数。由于参数值被修改,因此该参数是一个指针或者引用。
1:如果push ebp,sub esp,80h是函数的开头(即是call指令跳转到这里的),则使用寄存器来传递函数参数,eax,edi都是函数参数。
2:由于破坏了当前函数的返回地址,那么在后面应该有修复操作(A:平衡堆栈并跳转 B:重新改写[ebp+04] C:其他操作来修复)
3:这是否是壳程序(极可能是win32汇编写的)?这段代码得到的信息太少,需要根据上下文来判断,只能分析这么多。