您的位置:首页 > 理论基础

深入理解计算机系统(第二版) 家庭作业 第四章

2013-06-23 22:53 459 查看
4.43

没有正确执行pushl %esp,pushl %esp是将esp当前的内容入栈。
如果REG是esp,那么代码是先减去了esp,然后将减了4以后的REG移入了esp。
修改:(我只能想到利用其它的寄存器)
movl REG, %eax
subl $4, %esp
movl %eax, (%esp)

4.44
也没有正确执行popl %esp,因为popl %esp是将当前栈顶的值放入esp。
如果REG是esp,那么最后得到esp是栈顶值减4之后的值。
movl (%esp), %eax
addl $4, %esp
movl %eax, REG

4.45

我没有按书上给的例子写,而是自己写了一个冒泡。
void bubble(int *data, int count)

{

if(count == 0) return;

int i, j;

int *p, *q;

for(i=count-1; i!=0; i--){

p = data, q = data + 1;

for(j=0; j!=i; ++j)

{

if( *p > *q )

{

int t = *p;

*p = *q;

*q = t;

}

p++, q++;

}

}

}

Y86:(movl就没有区分那么细了,因为太麻烦了。。。)

data:#(从地地址往高地址)
$5, $2, $7, $4, $3, $6, $1, $8

movl $8, %ecx
pushl %ecx #count = 8
movl data, %ecx
pushl %ecx #push data
call bubble
halt

bubble:
pushl %ebp
movl %esp, %ebp
pushl %esi
pushl %ebx
pushl %edx

movl 8(%ebp), %edx #edx == data
movl 12(%ebp), %esi #esi == count
andl %esi, %esi
je bubbleEnd #count==0
movl $1, %eax

subl %eax, %esi #count--
je bubbleEnd #count==1

OuterLoop:
movl %edx, %ecx # p = data (ecx)
pushl %esi# to save one reg

InnerLoop:
movl (%ecx), %eax
movl 4(%ecx), %ebx
subl %eax, %ebx
movl 4(%ecx), %ebx

jg NoSwap
movl %eax, %ebx #swap, so ebx is greater
movl 4(%ecx), %eax

NoSwap:
movl %eax, (%ecx)
movl %ebx, 4(%ecx)
movl $4, %eax

addl %eax, %ecx
movl $1, %eax

subl%eax, %esi
jne InnerLoop

popl %esi
movl $1, %eax

subl %eax, %esi
jne OuterLoop

bubbleEnd:
popl %edx
popl %ebx
popl %esi
movl %ebp, %esp
popl %ebp
ret

4.46

InnerLoop内改成:(edx是循环利用)

movl (%ecx), %edx

InnerLoop:
movl %edx, %eax
movl 4(%ecx), %ebx
subl %ebx, %eax # compare *p and *(p+1)
cmovl %ebx, %edx #edx is max
movl (%ecx), %eax
cmovg %ebx, %eax #%eax is min

movl %edx, 4(%ecx)
movl %eax, (%ecx)
movl $4, %eax
addl %eax, %ecx
movl $1, %eax
subl %eax, %esi
jne InnerLoop

4.47
我们可以明确的是,这条指令完成的任务为,
ebp <- M4[cur_ebp]
esp <- cur_ebp + 4

取指阶段 icode:ifun = D:0
valP <= PC + 1

译码阶段 valB <= R[%ebp]

执行阶段 valE <= valB + 4

访存阶段 valM <= M4[valB]

写回阶段 R[%esp] <= valE
R[%ebp] <= valM

4.48

取指阶段 icode:ifun = M1[PC] = C:0

rA:rB <= M1[PC+1]

valC <= M4[PC+2]

valP <= PC + 6

译码阶段 valB <= R[rB]

执行阶段 valE <= valB + valC
SetCC

访存阶段

写回阶段 R[rB] <= valE

4.49
4.50

取指

bool need_regids =
icode in { IRRMOVL, IOPL, IPUSHL, IPOPL,
IIRMOVL, IRMMOVL, IMRMOVL, IADDL };

bool need_valC =
icode in { IIRMOVL, IRMMOVL, IMRMOVL, IJXX, ICALL, IADDL };

译码和写回

int srcA = [
icode in { IRRMOVL, IRMMOVL, IOPL, IPUSHL } : rA;
icode in { IPOPL, IRET } : RESP;
1 : RNONE; # Don’t need register
];

int srcB = [

icode in { IOPL, IRMMOVL, IMRMOVL, IADDL } : rB;

icode in { IPUSHL, IPOPL, ICALL, IRET } : RESP;
icode in { ILEAVE } : REBP;

1 : RNONE; # Don’t need register

];

int dstE = [

icode in { IRRMOVL} && Cnd : rB;
icode in { IIRMOVL, IOPL, IADDL } : rB;
icode in { IPUSHL, IPOPL, ICALL, IRET, ILEAVE } : RESP;
1 : RNONE; # Don’t write any register

];

int dstM = [
icode in { IMRMOVL, IPOPL}:rA;
icode in { ILEAVE }: REBP;

1 : RNONE; # Don’t write any register
];

执行

int aluA = [

icode in { IRRMOVL, IOPL } : valA;
icode in { IIRMOVL, IRMMOVL, IMRMOVL, IADDL } : valC;
icode in { ICALL, IPUSHL}:-4;
icode in { IRET, IPOPL, ILEAVE}:4;
# Other instructions don’t need ALU

];

int aluB = [

icode in { IRMMOVL, IMRMOVL, IOPL, ICALL,
IPUSHL, IRET, IPOPL, ILEAVE, IADDL } : valB;
icode in { IRRMOVL, IIRMOVL}:0;

# Other instructions don’t need ALU
];

bool set_cc = icode in { IOPL, IADDL };

访存

int mem_addr = [

icode in { IRMMOVL, IPUSHL, ICALL, IMRMOVL } : valE;
icode in { IPOPL, IRET } : valA;
icode in { ILEAVE } : valB;
# Other instructions don’t need address

];

bool mem_read = icode in { IMRMOVL, IPOPL, IRET, ILEAVE };

4.51 -- 4.56
感觉蛮麻烦的,不想写啊。。。

4.57
A.
发现加载/使用冒险的逻辑公式:
( E_icode in {IMRMOVL, IPOPL} && E_dstM in {d_srcA, d_srcB})
&&
!(E_icode == IMRMOVL && D_icode == IPUSHL);

B.
e_valA = [ (E_icode==IPUSH) && (M_dstM==E_srcA) : m_valM;
1 : E_valA;
];

4.58
版本1,在预测正确的情况下执行7条指令,预测错误时执行9条指令并插入一个bubble。
版本2,执行8条指令,但是在外部循环需要多执行3条指令,否则就需要多用一个寄存器。
暂时没有想到好的办法。
光从内循环看来,版本2平均执行次数比版本1要少,因为可以假设预测错误的概率是50%。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: