CSAPP第四章家庭作业参考答案
(CSAPP第三版系列)
4.46
A. 这段代码序列没有正确描述指令popq %rsp的⾏为。该段代码序列使%rsp的值为(%rsp)+8,⽽指令popq%rsp执⾏后,%rsp的值应为(%rsp)。 B. 改写代码序列:
addq $8 , %rsp
movq-8(%rsp) , REG
4.48
if(data[i+1] < data[i]){
/*Swap adjacent elements*/
long t = data[i+1];
data[i+1] = data[i];
data[i] = t;
}
对应的Y86-64代码修改为条件转移,代码如下:
mrmovq (%rdx), %r8
rrmovq %rdx, %rsi
addq %r10, %rsi
mrmovq (%rsi), %rcx
rrmovq %rcx, %r10
subq %r8, %r10
rrmovq %rcx, %r10
cmovl %r8, %r10
rmmovq %r10, (%rsi)
rrmovq %r8, %r10
cmovl %rcx, %r10辟天
rmmovq %r10, (%rdx)
4.50
Y86-64代码如下:
# Execution begins at address 0
.pos 0
irmovq stack, %rsp # Set up stack pointer
call main # Execute main program
halt # Terminate program
# Array of 8 elements
.align 8
vals:
.quad 0x000000000000
.quad 0x000000000000
.quad 0x000000000000
.quad 0x000000000000
可比产品成本降低率.quad 0x000000000000
.quad 0x000000000000
.
quad 0x000000000000
.quad 0x000000000000
jump_table:
.quad L1
.quad L4
.quad L2
.quad L3
.quad L4
.quad L2
main:
irmovq vals, %r12
irmovq $-1,%rdi
call switchv
rmmovq %rax, (%r12)
irmovq $0,%rdi
call switchv
rmmovq %rax, 0x8(%r12)
irmovq $1,%rdi
call switchv
rmmovq %rax, 0x10(%r12)
irmovq $2,%rdi
call switchv
盐酸利多卡因rmmovq %rax, 0x18(%r12)
irmovq $3,%rdi
call switchv
rmmovq %rax, 0x20(%r12)
irmovq $4,%rdi
call switchv
rmmovq %rax, 0x28(%r12)
irmovq $5,%rdi
call switchv
rmmovq %rax, 0x30(%r12)
irmovq $6,%rdi
call switchv
rmmovq %rax, 0x38(%r12) ret
# long switchv(long idx)
# idx in %rdi
switchv:
rrmovq %rdi, %r8
irmovq $5, %r9
subq %r9, %r8
jg L4
andq %rdi, %rdi
jl L4
远程教育论坛
irmovq jump_table, %r8
irmovq $8, %r9
irmovq $1, %r10
loop:
subq %r10, %rdi
jl endloop
addq %r9, %r8
jmp loop
endloop:
mrmovq (%r8), %r8
pushq %r8
ret
L1:
irmovq 0xaaa, %rax
ret
L2:
irmovq 0xbbb, %rax
ret
L3:
irmovq 0xccc, %rax
ret
L4:
irmovq 0xddd, %rax #default
ret
# Stack starts here and grows to lower addresses
stack:
pdsc
测试结果截图:
4.52
设计思想:
分析seq-full.hcl,需要对Instr_valid, need_regids, need_valC, srcB, dstE, aluA, aluB进⾏修改。bool Instr_valid = icode in{…}; ⼤括号中所列指令需加上IIADDQ
bool need_regids = icode in{…}; ⼤括号中所列指令需加上IIADDQ
bool need_valC = icode in{…}; ⼤括号中所列指令需加上IIADDQ
word srcB = [
icode in {…} : rB; ⼤括号中所列指令需加上IIADDQ
…
];
word dstE = [
…
icode in {…} : rB; ⼤括号中所列指令需加上IIADDQ
…
];
word aluA = [
…
icode in {… } : valC; ⼤括号中所列指令需加上IIADDQ
…
];
word aluB = [
icode in { … } : valB; ⼤括号中所列指令需加上IIADDQ
…
]
;
添加IIADDQ指令后seq-full.hcl⽂件:
#/* $begin seq-all-hcl */
>>>>>>>>>>>>>### # HCL Description of Control for Single Cycle Y86-64 Processor SEQ ## Copyright (C) Randal E. Bryant, David R. O'Hallaron, 2010 #
>>>>>>>>>>>>>##### Your task is to implement the iaddq instruction
## The file contains a declaration of the icodes
## for iaddq (IIADDQ)
## Your job is to add the rest of the logic to make it work
>>>>>>>>>>>>>### # C Include's. Don't alter these #>>>>>>>>>>>>>###quote '#include <stdio.h>'
quote '#include "isa.h"'
quote '#include "sim.h"'
quote 'int sim_main(int argc, char *argv[]);'
quote 'word_t gen_pc(){return 0;}'
quote 'int main(int argc, char *argv[])'
quote ' {plusmode=0;return sim_main(argc,argv);}'
>>>>>>>>>>>>>### # Declarations. Do not change/remove/delete any of these #>>>>>>>>>>>>>###> Symbolic representation of Y86-64 Instruction Codes >>### wordsig INOP 'I_NOP'wordsig IHALT 'I_HALT'
wordsig IRRMOVQ 'I_RRMOVQ'
wordsig IIRMOVQ 'I_IRMOVQ'
wordsig IRMMOVQ 'I_RMMOVQ'
wordsig IMRMOVQ 'I_MRMOVQ'
wordsig IOPQ 'I_ALU'
wordsig IOPQ 'I_ALU'
wordsig IJXX 'I_JMP'
wordsig ICALL 'I_CALL'
wordsig IRET 'I_RET'
wordsig IPUSHQ 'I_PUSHQ'
wordsig IPOPQ 'I_POPQ'基督教圣歌
# Instruction code for iaddq instruction
wordsig IIADDQ 'I_IADDQ'
> Symbolic represenations of Y86-64 function codes >wordsig FNONE 'F_NONE' # Default function code
> Symbolic representation of Y86-64 Registers referenced explicitly > wordsig RRSP 'REG_RSP' # Stack Pointerwordsig RNONE 'REG_NONE' # Special value indicating "no register"
> ALU Functions referenced explicitly >wordsig ALUADD 'A_ADD' # ALU should add its arguments
> Possible instruction status values >wordsig SAOK 'STAT_AOK' # Normal execution
wordsig SADR 'STAT_ADR' # Invalid memory address
wordsig SINS 'STAT_INS' # Invalid instruction
wordsig SHLT 'STAT_HLT' # Halt instruction encountered
> Signals that can be referenced by control logic >>>>> Fetch stage inputs >wordsig pc 'pc' # Program counter
> Fetch stage computations >wordsig imem_icode 'imem_icode' # icode field from instruction memory
wordsig imem_ifun 'imem_ifun' # ifun field from instruction memory
wordsig icode 'icode' # Instruction control code
wordsig ifun 'ifun' # Instruction function
wordsig rA 'ra' # rA field from instruction
wordsig rB 'rb' # rB field from instruction
wordsig valC 'valc' # Constant from instruction
wordsig valP 'valp' # Address of following instruction
boolsig imem_error 'imem_error' # Error signal from instruction memory
boolsig instr_valid 'instr_valid' # Is fetched instruction valid?
> Decode stage computations >wordsig valA 'vala' # Value from register A port
wordsig valB 'valb' # Value from register B port
> Execute stage computations >wordsig valE 'vale' # Value computed by ALU
boolsig Cnd 'cond' # Branch test
> Memory stage computations >wordsig valM 'valm' # Value read from memory
boolsig dmem_error 'dmem_error' # Error signal from data memory
>>>>>>>>>>>>>### # Control Signal Definitions. #>>>>>>>>>>>>>### >>># Fetch Stage >>>>>>># Determine instruction code
word icode = [
imem_error: INOP;
1: imem_icode; # Default: get from instruction memory
];