计算机系统第三章答案.docx

上传人:b****9 文档编号:25288110 上传时间:2023-06-07 格式:DOCX 页数:16 大小:198.98KB
下载 相关 举报
计算机系统第三章答案.docx_第1页
第1页 / 共16页
计算机系统第三章答案.docx_第2页
第2页 / 共16页
计算机系统第三章答案.docx_第3页
第3页 / 共16页
计算机系统第三章答案.docx_第4页
第4页 / 共16页
计算机系统第三章答案.docx_第5页
第5页 / 共16页
点击查看更多>>
下载资源
资源描述

计算机系统第三章答案.docx

《计算机系统第三章答案.docx》由会员分享,可在线阅读,更多相关《计算机系统第三章答案.docx(16页珍藏版)》请在冰豆网上搜索。

计算机系统第三章答案.docx

计算机系统第三章答案

 

计算机系统第三章答案

习题

3.参考答案:

(1)后缀:

w,源:

基址+比例变址+偏移,目:

寄存器

(2)后缀:

b,源:

寄存器,目:

基址+偏移

(3)后缀:

l,源:

比例变址,目:

寄存器

(4)后缀:

b,源:

基址,目:

寄存器

(5)后缀:

l,源:

立即数,目:

(6)后缀:

l,源:

立即数,目:

寄存器

(7)后缀:

w,源:

寄存器,目:

寄存器

(8)后缀:

l,源:

基址+变址+偏移,目:

寄存器

4.参考答案:

(1)源操作数是立即数0xFF,需在前面加‘$’

(2)源操作数是16位,而长度后缀是字节‘b’,不一致

(3)目的操作数不能是立即数寻址

(4)操作数位数超过16位,而长度后缀为16位的‘w’

(5)不能用8位寄存器作为目的操作数地址所在寄存器

(6)源操作数寄存器与目操作数寄存器长度不一致

(7)不存在ESX寄存器

(8)源操作数地址中缺少变址寄存器

5.参考答案:

表题5用表

src_type

dst_type

机器级表示

char

int

movsbl%al,(%edx)

int

char

movb%al,(%edx)

int

unsigned

movl%eax,(%edx)

short

int

movswl%ax,(%edx)

unsignedchar

unsigned

movzbl%al,(%edx)

char

unsigned

movsbl%al,(%edx)

int

int

movl%eax,(%edx)

6.参考答案:

(1)xptr、yptr和zptr对应实参所存放的存储单元地址分别为:

R[ebp]+8、R[ebp]+12、

R[ebp]+16。

(2)函数func的C语言代码如下:

voidfunc(int*xptr,int*yptr,int*zptr)

{

inttempx=*xptr;

inttempy=*yptr;

inttempz=*zptr;

*yptr=tempx;

*zptr=tempy;

*xptr=tempz;

}

7.参考答案:

(1)R[edx]=x

(2)R[edx]=x+y+4

(3)R[edx]=x+8*y

(4)R[edx]=y+2*x+12

(5)R[edx]=4*y

(6)R[edx]=x+y

8.参考答案:

(1)指令功能为:

R[edx]←R[edx]+M[R[eax]]=0x00000080+M[0x8049300],寄存器EDX中内容改变。

改变后的内容为以下运算的结果:

00000080H+FFFFFFF0H

因此,EDX中的内容改变为0x00000070。

根据表可知,加法指令会影响OF、SF、ZF和CF标志。

OF=0,ZF=0,SF=0,CF=1。

(2)指令功能为:

R[ecx]←R[ecx]-M[R[eax]+R[ebx]]=0x00000010+M[0x8049400],寄存器ECX中内容改变。

改变后的内容为以下运算的结果:

00000010H-H

因此,ECX中的内容改为0x。

根据表可知,减法指令会影响OF、SF、ZF和CF标志。

OF=1,ZF=0,SF=1,CF=10=1。

(3)指令功能为:

R[bx]←R[bx]orM[R[eax]+R[ecx]*8+4],寄存器BX中内容改变。

改变后的内容为以下运算的结果:

0x0100orM[0x8049384]=0100HorFF00H

因此,BX中的内容改为0xFF00。

由节可知,OR指令执行后OF=CF=0;因为结果不为0,故ZF=0;因为最高位为1,故SF=1。

(4)test指令不改变任何通用寄存器,但根据以下“与”操作改变标志:

R[dl]and0x80

由节可知,TEST指令执行后OF=CF=0;因为结果不为0,故ZF=0;因为最高位为1,故SF=1。

(5)指令功能为:

M[R[eax]+R[edx]]←M[R[eax]+R[edx]]*32,即存储单元0x8049380中的内容改变为以下运算的结果:

M[0x8049380]*32=0x908f12a8*32,也即只要将0x908f12a8左移5位即可得到结果。

10010000100011110001001010101000<<5

=00010001111000100101010100000000

因此,指令执行后,单元0x8049380中的内容改变为0x11e25500。

显然,这个结果是溢出的。

但是,根据表可知,乘法指令不影响标志位,也即并不会使OF=1。

(6)指令功能为:

R[cx]←R[cx]-1,即CX寄存器的内容减一。

因此,指令执行后CX中的内容从0x0010变为0x000F。

由表可知,DEC指令会影响OF、ZF、SF,根据上述运算结果,得到OF=0,ZF=0,SF=0。

9.参考答案:

movl12(%ebp),%ecx11执行

5testb$0x80,%dl11执行

7addb%dl,(%eax)1:

因为C语言if语句中的条件表达式可以对多个条件进行逻辑运算,而汇编代码中一条指令只能进行一种逻辑运算,并且在每条逻辑运算指令生成的标志都是存放在同一个EFLAGS寄存器中,所以,最好在一条逻辑指令后跟一条条件转移指令,把EFLAGS中标志用完,然后再执行另一次逻辑判断并根据条件进行转移的操作。

(2)按照书中图给出的“if()goto…”语句形式写出汇编代码对应的C语言代码如下:

1voidcomp(charx,int*p)

2{

3if(p!

=0)

4if(x<0)

5*p+=x;

6}

13.参考答案:

1intfunc(intx,inty)

2{

3intz=x*y;

4if(x<=-100){

5if(y>x)

6z=x+y;

7else

8z=x-y;

9}elseif(x>=16)

10z=x&y;

11returnz;

12}

14.参考答案:

(1)每个入口参数都要按4字节边界对齐,因此,参数x、y和k入栈时都占4个字节。

1movw8(%ebp),%bx1:

5movw%si,%dx22

13cmpw%cx,%si11

15.L2:

16movswl%bx,%eax&0x1,因此f1用于检测x的奇偶性,当x中有奇数个1,则返回为1,否则返回0。

16.参考答案:

函数sw只有一个入口参数x,根据汇编代码的第2~5行指令知,当x+3>7时转标号.L7处执行,否则,按照跳转表中的地址转移执行,x与跳转目标处标号的关系如下:

x+3=0:

.L7

x+3=1:

.L2

x+3=2:

.L2

x+3=3:

.L3

x+3=4:

.L4

x+3=5:

.L5

x+3=6:

.L7

x+3=7:

.L6

由此可知,switch(x)中省略的处理部分结构如下:

case-2:

case-1:

……2标号处指令序列对应的语句

break;

case0:

……3标号处指令序列对应的语句

break;

case1:

…….4标号处指令序列对应的语句

break;

case2:

……5标号处指令序列对应的语句

break;

case4:

……6标号处指令序列对应的语句

break;

default:

……7标号处指令序列对应的语句

17.参考答案:

根据第2、3行指令可知,参数a是char型,参数p是指向short型变量的指针;根据第4、5行指令可知,参数b和c都是unsignedshort型,根据第6行指令可知,test的返回参数类型为unsignedint。

因此,test的原型为:

unsignedinttest(chara,unsignedshortb,unsignedshortc,short*p);

18.参考答案:

每次执行pushl指令后,R[esp]=R[esp]-4,因此,第2行指令执行后R[esp]=0xbc00001c。

(1)执行第3行指令后,R[ebp]=R[esp]=0xbc00001c。

到第12条指令执行结束都没有改变EBP的内容,因而执行第10行指令后,EBP的内容还是为0xbc00001c。

执行第13行指令后,EBP的内容恢复为进入函数funct时的值0xbc000030。

(2)执行第3行指令后,R[esp]=0xbc00001c。

执行第4行指令后R[esp]=R[esp]-40=0xbc00001c-0x28=0xbbfffff4。

因而执行第10行指令后,未跳转到scanf函数执行时,ESP中的内容为0xbbfffff4

-4=0xbbfffff0;在从scanf函数返回后ESP中的内容为0xbbfffff4。

执行第13行指令后,ESP的内容恢复为进入函数funct时的旧值,即R[esp]=0xbc000020。

(3)第5、6两行指令将scanf的第三个参数&y入栈,入栈的内容为R[ebp]-8=0xbc000014;第7、8两行指令将scanf的第二个参数&x入栈,入栈的内容为R[ebp]-4=0xbc000018。

故x和y所在的地址分别为0xbc000018和0xbc000014。

(4)执行第10行指令后,funct栈帧的地址范围及其内容如下:

19.参考答案:

第1行汇编指令说明参数x存放在EBX中,根据第4行判断x=0则转.L2,否则继续执行第5~10行指令。

根据第5、6、7行指令可知,入栈参数nx的计算公式为x>>1;根据第9、10、11行指令可知,返回值为(x&1)+rv。

由此推断出C缺失部分如下:

1intrefunc(unsignedx){

2if(x==0)

3return0;

4unsignednx=x>>1;

5intrv=refunc(nx);

6return(x&0x1)+rv;

7}

该函数的功能为计算x的各个数位中1的个数。

20.参考答案:

在IA-32中,GCC为数据类型longdouble型变量分配12字节空间,实际上只占用10个字节。

数组

元素大小(B)

数组大小(B)

起始地址

元素i的地址

charA[10]

1

10

&A[0]

&A[0]+i

intB[100]

4

400

&B[0]

&B[0]+4i

short*C[5]

4

20

&C[0]

&C[0]+4i

short**D[6]

4

24

&D[0]

&D[0]+4i

longdoubleE[10]

12

120

&E[0]

&E[0]+12i

longdouble*F[10]

4

40

&F[0]

&F[0]+4i

21.参考答案:

表达式

类型

汇编代码

S

short*

AS

leal(%edx),%eax

S+i

short*

AS+2*i

leal(%edx,%ecx,2),%eax

S[i]

short

M[AS+2*i]

movw(%edx,%ecx,2),%ax

&S[10]

short*

AS+20

leal20(%edx),%eax

&S[i+2]

short*

AS+2*i+4

leal4(%edx,%ecx,2),%eax

&S[i]-S

int

(AS+2*i-As)/2=i

movl%ecx,%eax

S[4*i+4]

short

M[AS+2*(4*i+4)]

movw8(%edx,%ecx,8),%ax

*(S+i-2)

short

M[AS+2*(i-2)]

movw-4(%edx,%ecx,2),%ax

22.参考答案:

根据汇编指令功能可以推断最终在EAX中返回的值为:

M[a+28*i+4*j]+M[b+20*j+4*i],因为数组a和b都是int型,每个数组元素占4B,因此,M=5,N=7。

23.参考答案:

执行第11行指令后,a[i][j][k]的地址为a+4*(63*i+9*j+k),所以,可以推断出M=9,N=63/9=7。

根据第12行指令,可知数组a的大小为4536字节,故L=4536/(4*L*M)=18。

24.参考答案:

(1)常数M=76/4=19,存放在EDI中,变量j存放在ECX中。

(2)上述优化汇编代码对应的函数trans_matrix的C代码如下:

1voidtrans_matrix(inta[M][M]){

2inti,j,t,*p;

3intc=(M<<2);

3for(i=0;i

4p=&a[0][i];

5for(j=0;j

6t=*p;

7*p=a[i][j];

8a[i][j]=t;

9p+=c;

10}

11}

12}

25.参考答案:

(1)node所需存储空间需要4+(4+4)+4=16字节。

成员p、、和next的偏移地址分别为0、4、8和12。

(2)np_init中缺失的表达式如下:

voidnp_init(structnode*np)

{

np->=np->;

np->p=&(np->;

np->next=np;

}

26.参考答案:

表达式EXPR

TYPE类型

汇编指令序列

uptr->

int

movl(%eax),%eax

movl%eax,(%edx)

uptr->

short

movw4(%eax),%ax

movw%ax,(%edx)

&uptr->

short*

leal6(%eax),%eax

movw%eax,(%edx)

uptr->

short*

movl%eax,(%edx)

uptr->[uptr->]

short

movl4(%eax),%ecx

movl(%eax,%ecx,2),%eax

movl%eax,(%edx)

*uptr->

char

movl8(%eax),%eax

movb(%eax),%al

movb%al,(%edx)

27.参考答案:

(1)S1:

scid

0248总共12字节,按4字节边界对齐

(2)S2:

iscd

0467总共8字节,按4字节边界对齐

(3)S3:

csid

0248总共12字节,按4字节边界对齐

(4)S4:

sc

06总共8字节,按2字节边界对齐

(5)S5:

cside

0481216总共24字节,按4字节边界对齐(Linux下double型按4字节对齐)

(6)S6:

csd

03640总共44字节,按4字节边界对齐

28.参考答案:

Windows平台要求不同的基本类型按照其数据长度进行对齐。

每个成员的偏移量如下:

cdisplgv

08162024283240

结构总大小为48字节,因为其中的d和g必须是按8字节边界对齐,所以,必须在末尾再加上4个字节,即44+4=48字节。

变量长度按照从大到小顺序排列,可以使得结构所占空间最小,因此调整顺序后的结构定义如下:

struct{

doubled;

longlongg;

inti;

char*p;

longl;

void*v;

shorts;

charc;

}test;

dgiplvsc

08162024283234结构总大小为34+6=40字节。

29.参考答案:

(1)执行第7行和第10行指令后栈中的信息存放情况如下图所示。

其中gets函数的入口参数为buf数组首

地址,应等于getline函数的栈帧底部指针EBP的内容减0x14,而getline函数的栈帧底部指针EBP的内容应等于执行完getline中第2行指令(push%ebp)后ESP的内容,此时,R[esp]==0xbffc07f0-4=0xbffc07ec,故buf数组首地址为R[ebp]-0x14=R[esp]-0x14=0xbffc07ec-0x14=0xbffc07d8。

(2)当执行到getline的ret指令时,假如程序不发生段错误,则正确的返回地址应该是0x80485c8,发生段错误是因为执行getline的ret指令时得到的返回地址为0x8413938,这个地址所在存储段可能是不可执行的数据段,因而发生了段错误(segmentationfault)。

(3)执行完第10行汇编指令后,被调用者保存寄存器EBX、ESI和EDI在P中的内容已被破坏,同时还破坏了EBP在P中的内容。

(4)getline的C代码中malloc函数的参数应该为strlen(buf)+1,此外,应该检查malloc函数的返回值是否为NULL。

30.参考答案:

x86-64过程调用时参数传递是通过通用寄存器进行的,前三个参数所用寄存器顺序为RDI、RSI、RDX。

abc的4种合理的函数原型为:

viodabc(intc,long*a,int*b);

viodabc(unsignedc,long*a,int*b);

viodabc(longc,long*a,int*b);

viodabc(unsignedlongc,long*a,int*b);

根据第3、4行指令可知,参数b肯定指向一个32位带符号整数类型;根据第5行指令可知,参数a指向64位带符号整数类型;而参数c可以是32位,也可以是64位,因为*b为32位,所以取RDI中的低32位R[edi](截断为32位),再和*b相加。

同时,参数c可以是带符号整数类型,也可以是无符号整数类型,因为第2行加法指令addl的执行结果对于带符号整数和无符号整数都一样。

31.参考答案:

(1)汇编指令注释如下:

1movl8(%ebp),%edx3:

6movl%edi,%eax33

13movl%esi,%eaxnext->n1.ptr)–uptr->n2.data2;

34.参考答案:

(1)函数trace的入口参数tptr通过RDI寄存器传递。

(2)函数trace完整的C语言代码如下:

longtrace(tree_ptrtptr)

{

longret_val=0;

tree_ptrp=tptr;

while(p!

=0){

ret_val=p->val;

p=p->left;

}

returnret_val;

}

(3)函数trace的功能是:

返回二叉树中最左边叶子节点中的值val。

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 工程科技 > 材料科学

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1