Search

컴퓨터구조 7강

Supporting Procedures in Computer Hardware

Six Steps in Execution of a Procedure

1.
Main routine(caller) 가 parameters(=arguments) 를 procedure(callee)가 접근할 수 있는 곳에 위치시킨다.
a.
caller : 함수를 부르는 루틴
b.
callee: 불러지는 함수
c.
$a0 - $a3이 register에서 arguments를 위한 곳 (four argument registers)
2.
Caller가 callee로 control을 넘긴다. (callee가 실행됨)
3.
Callee가 실행되면 실행하기 위해 필요한 스토리지 공간, 즉 메모리를 할당받는다.(보통 stack이라는 공간)
4.
Callee가 desired task를 수행한다.
5.
Callee는 task끝난 후 결과를 Caller가 접근할 수 있는 곳에 위치시킨다.
a.
$v0 - $v1이 result values를 위한 곳이다( two value registers for result values)
6.
Callee는 Caller에게 컨트롤을 넘긴다. (Caller 실행)
a.
이때는 $ra가 실행 - 리턴해야하는 주소값이 들어가있음.
b.
$ra가 pc(program counter)로 복사되어 6번 단계 실행 수에는 $ra에 담겨있는 명령어부터 수행하게 된다.

Register Usage

28~31 : special register

Procedure Call Instructions

1.
jal procedureLabel
procedure call: jump and link 명령어
실행시 procedureLabel에 있는 명령어로 이동
동시에 현재 그 명령어(procedurelabel) 다음에 있는 명령어를 $ra에 넣는다.
2.
jr $ra
procedure return: jump register 명령어
$ra 레지스터의 명령어를 Program Counter(PC)에 복사
case/switch statements같은 계산된 jump 명령어에서도 사용되기도 한다.

Leaf Procedure Example

C code :
int leaf_example (int g, h, i, j) { int f; f = (g+h) - (i+j); return f; }
Python
복사
arguments g, ..., j는 $a0, ..., $a3 에 있음
f 는 $s0에 있음 즉, stack의 $s0에 저장해야한다
result는 $v0에 들어있음
1.
stack pointer($sp) 에 4를 빼주는 연산 = stack값이 4만큼 감소 = stack 에 4바이트만큼 메모리 할당
2.
$s0값을 $sp에 복사 왜? s0의 원래의 값을 함수에서 쓰기전에 스택에 넣어뒀다가 다시 복원하기 위해서 즉, s0의 원래값을 보존하기 위해서
3.
$a0와 $a1 더해 $t0에 저장 → g+h
4.
$a2와 $a3 더해 $t1에 저장 → i+j
5.
$t0에서 $t1뺴 $s0에 저장 → (g+h)-(i+j)
6.
리턴값 $v0에 넣기 위해 $s0값을 zero와 더하는 방식으로 $v0에 넣어줌
7.
load word 명령어로 $sp에 저장해두었던 $s0의 원래 값을 복원
8.
sp값 다시 조정 → $sp 에 4 다시 더해줌 : 할당받은 4바이트 할당 해제
9.
$ra의 값을 pc(program counter)로 복사해 caller로 가게해준다. 이 명령어 후에는 caller가 동작

Non-Leaf Procedures

자신을 포함한 다른 procedures들을 호출함
procedure내에서 다른 procedure을 호출하는 nested call이기 때문에 caller는 stack에 필요한 것들(return address나 call이후에 필요한 arguments나 temporaries) 저장해야한다.
call 이후에는 stack으로부터 복원시켜야 함

Non-Leaf procedure Example

C code :
int fact (int n) { if (n < 1) return 1; else return n * fact(n-1); }
C
복사
argument n in $a0
result in $v0
MIPS Code
Lear Procedure보다 복잡한 모습
fact
1.
$sp(stack pointer)에 -8해주는 연산으로 stack memory에 8바이트 할당
2.
store word(sw) 명령어로 $ra레지스터 값을 4($sp) 즉, 스택에 넣는다
3.
store word(sw) 명령어로 $a0레지스터 값을 0($sp) 즉, 스택에 넣는다 ⇒ $ra와 $a0에 있는 값 보존을 위해
4.
$a0값이 1보다 작으면 $t0는 1, 그렇지 않으면 0
5.
$t0가 0(zero)이면 L1으로 이동
6.
$v0를 1로 설정하ㅗ
7.
stack pointer에 다시 + 9
8.
jump return : $ra 레지스터로 이동
L1
1.
$a0에 -1연산
2.
fact로 이동
3.
load word(lw)명령어로 0($sp)의 값을 $a0로 복원
4.
load word(lw)명령어로 4($sp)의 값을 $ra로 복원
5.
stack pointer값에 다시 +8
6.
$a0 와 $v0 곱해 $v0에 복사
7.
jump return : $ra 레지스터로 이동. caller 로 돌아감

Local Data on the Stack

frame pointer(fp)와 stack pointer(sp)
c프로그램에서 local data(지역변수)는 stack에 할당이 된다.
sp는 현재 stack의 top에 있는 값을 가리킨다
Procedure Frame(activation record)
함수 실행시 만들어지는 함수를 위한 frame
fp는 frame의 시작점을 가리킨다.
stack storage를 관리하기 위해 몇몇 compilers의해 이용된다.

Memory Layout

Text : program code (명령어)
Static data: global variables
e.g., static variables in C, constant arrays and strings
$gp(global pointer) initialized to address allowing ± offsets into this segment. 이 segment의 중간값을 가짐
Dynamic data: heap
e.g.., malloc in C, new in Java
Stack: automatic storage

Communicating with People

Character Data

Byte-encoded character sets
ASCII : 128 characters
95 graphic, 33 control
Latin-1 : 256 characters
ASCII, +96 more graphic characters
unicode: 32-bit character set
JAVA, C++등에서 사용
대부분의 알파벳이나 symbols 다 표현 가능
UTF-8, UTF-16 : variable-length encodings. 보통 UTF-16을 많이 사용

Byte/Haftword Operations

bitwise operations사용 가능
MIPS byte/halfword load/store
string processing is a common case sign extend to 32 bits in rt = 읽어서 sign extend해서 32bit로 확장해 넣음 lb rt, offset(rs) : lb=load byte - offset(rs)에서 한 바이트 읽어서 rt에 넣음 lh rt, offset(rs) : lh=load halfword - offset(rs)에서 word의 절반(메모리의 절반) 읽어서 rt에 넣음
zero extend to 32 bits in rt = 읽어서 zero extend해서 32bit로 확장해 넣음 lbu rt, offset(rs) : lbu=load byte unsigned lhu rt, offset(rs) : lhu=load byte unsigned
store just rightmost byte/halfword sb rt, offset(rs) : 하위 1바이트 읽어서 저장 sh rt, offset(rs) : word 하위 절반 읽어서 저장

String Copy Example

C code:
void strcpy (char x[], char y[]) { int i; i = 0; while ((x[i]=y[i])!='\0') i +=1; }
C
복사
addresses of x, y in $10, $a0
i in $s0
x[i]와 y[i]가 null이 아닐 때까지 x[i]에 y[i]를 복사, i는 1씩 증가
MIPS Code
strcpy:
1.
sp값 4만큼 빼줌 - 4바이트 할당
2.
$s0 값 sp 에 저장
3.
$s0를 0으로 초기화
L1:
1.
$s0와 $a1 더해서 $t1에 저장
2.
$t1 에서 한바이트 읽어 $t2에 저장
3.
$s0와 $a0 더해 $t3에 저장
4.
$t2에서 한 바이트 읽어 0($t3)으로 복사. 1,2로 읽은 y[i]값을 x[i]로 복사해주는 과정이다
5.
t2가 0이면 L2, 아니면 6으로
6.
$s0에 +1 (i+=1)해주고
7.
L1으로 점프!
L2:
1.
$s0값을 복원시키고
2.
sp값도 +4해서 복원시키고
3.
caller로 간다