728x90
반응형
Registers
- 프로세서 안에 들어있는 하드웨어 구성 요소임
- CPU를 만들고나서, 사용가능한 레지스터의 개수를 바꾸지 못하는 이유임
- RISC-V 아키텍쳐에서는 32개의 integer 레지스터 이용 가능
- 0부터 31번까지 이름 붙여져 있음
- x0-x31
- 어셈블리에서 이름 사용 가능
- 32-bits wide
- x0 레지스터는 항상 0임
- x0에 다른 값을 쓰려고하면 무시됨
- Instruction architecture를 정의할 때, architecture가 제공하는 register를 먼저 정의해야 함
Two's complement operations
- Negate: 모든 bit를 invert하고 1을 더함
- 더 큰 bit 형태로 나타내는 법
- RISC-V에서는 the most significant bit(the sign bit)를 채우는 방식 사용
RISC-V arithmetic
- 모든 instruction은 3개의 operand로 이루어져 있음
- operand의 순서는 고정되어 있음
- arithmetic instruction의 경우, destination이 항상 먼저 온다
- 더 많은 operand를 제공하지 않는 이유는 Instruction이 복잡해지지 않게 하기 위해서임
- Design principle
- simplicity favors regularity
- Regularity는 실행을 더 간단하게 만듦 -> 하드웨어를 simple하게 만들 수 있음
- Simplicity는 낮은 비용으로 높은 성과를 가능하게 함
- Arithmetic 연산에서 operand는 register만 가능(memory는 안됨)
- 각 register는 32bit
- smaller is faster
- 레지스터가 더 많으면 더 많은 회로를 지나야하기 때문에 clock cycle time을 증가시켜서 더 느려질 수 있음 -> 레지스터 개수를 많이 안늘리는 이유
- 레지스터를 32(2^5)개보다 더 적게 하면 프로그램에서 사용하는 변수들을 모두 다 레지스터에 매핑할 수 없기에 더도말고 덜도말고 딱 32개를 씀
- 레지스터에 저장할 수 없으면 변수들을 메모리에 저장해야하는데 그렇게하면 성능이 떨어짐
- Make the common case fast
- 작은 constants(상수)들은 자주 쓰임 -> 사용할 가능성이 높은 상수들을 레지스터에 미리 하드웨어화 시킴
- 자주 쓰이는 것들이 메모리에 들어가 있으면 load instruction을 계속 사용해야해서 성능이 느려짐
- RISC-V Instruction
- Immediate operand 사용: operand에 레지스터가 아니라 하드웨어화 시켜 놓은 숫자를 사용
- Ex) add라는 32bit 명령어 안에 이미 상수값이 들어가 있어서 명령어를 fetch하면 그 안에 이미 값이 들어가 있어서 바로 연산 가능 -> 메모리로부터 load를 안해도 되기에 성능 향상
- 빼기 연산 같은 경우에는 instruction이 없음
- 빼기를 하는 것이 아니라 음수를 더하는 방식으로 사용
- 비슷하게 branch 도 blt(branch if less than)과 bge(branch if greater than or equal)은 있지만 bgt나 ble는 없음(argument 순서를 바꿔서 사용하면 되니까)
- 0번 레지스터는 항상 상수 0을 나타냄
- 0은 굉장히 많이 사용되기에 아예 Register에 고정시켜놓음
- Immediate operand 사용: operand에 레지스터가 아니라 하드웨어화 시켜 놓은 숫자를 사용
- 큰 상수의 경우에는 lui와 addi라는 Instruction을 조합하여 load upper immediate instruction 구현
- simplicity favors regularity
- Instruction 안에 constant 값을 적어주는 것은 32bit 명령어 안에 일부 자리를 할당하는 방식이기에 다른 정보도 담아야하여 많은 자리를 주지는 못함 -> 큰 숫자는 담을 수 없음
- 그래서 bit를 shift하는 방식을 활용해서 값을 저장함
- ex) addi는 imm에 해당하는 bit가 12개 밖에 안됨. lui연산은 20bit의 Input immediate값을 받고 그 값을 상위 20bit에 위치시킴. lui을 활용해서 rd의 31번째부터 12번째까지를 위치시키고 남은 12비트는 0의로 채운 다음에 그 남은 12비트에 addi를 덧셈하여 32bit짜리를 큰 수를 완성시킬 수 있음
- Pseudo-instruction은 가짜 instruction을 의미
- assembly code에서만 사용 가능
- 사용자의 편리성을 위해서 존재
- ex) li라는 pseudo instruction을 쓰면 내부적으로는 lui와 addi를 이용해서 동작함
Memory organization
- 주소를 가진 큰 1차원 배열이라고 생각
- Arrays, structures, dynamic data 등 composite data들을 위해 사용
- arithmetic operations을 위해서 메모리에서부터 데이터를 레지스터로 가져오고, 데이터를 arithmetic 연산 장치에 보내고 연산하고, 다시 memory에 그 값을 저장하는 방식 사용
- 메모리 주소는 array의 index라고 생각
- Byte addressing -> 1개의 Index가 1byte를 나타내는 주소 체계
- 실제로는 대부분 데이터는 word 단위를 사용하기 때문에 32bit architecture에서는 word 단위(32bit, 4 bytes)로 인덱싱하여 사용
- 2^32 bytes는 bytes address 0부터 2^32-1 사용
- 2^30 words는 byte address 0, 4, 8, ... 2^32-4 사용
- Words are aligned
- word의 주소는 word 사이즈인 4byte의 배수로 되어 있음
- word 주소 체계에서는 주소를 bit 단위로 나타냈을 때 마지막 두 비트는 의미가 없음
- 4의 배수이기 때문에 마지막 2 bit는 항상 00 이기 때문
Alignment(정렬)
- 각 object(data)가 그것의 사이즈의 배수에 해당하는 곳에 위치하고 있을 때 정렬되어 있다고 함
- 성능에 큰 영향을 줌
- alignment가 되어있다면 성능이 빠르지만, 그렇지 않다면 성능이 떨어짐
Byte ordering
- Endian: 컴퓨터 메모리와 같은 1차원 공간에 여러 개의 연속된 대상을 배열하는 방법
- Big Endian: Most significant byte를 먼저 배치
- Little Endian: Least significant byte를 먼저 배치
- 일종의 convention으로 big endian이나 little endian은 성능은 동일함 (type이 다를 뿐)
- RISC-V는 little endian 사용
Registers vs Memory
- Arithmetic instructions operands는 레지스터에 있음(메모리 주소를 operand로 줄 수 없음)
- only 32 registers provided
- 컴파일러는 레지스터에 변수를 연결 -> 컴파일러가 어떻게 변수를 mapping하는 지가 성능에 영향
- 레지스터는 메모리보다 접근하는데 속도가 빠름
- 메모리 데이터에 대한 작동은 load와 store이 필요하기 때문에 많은 instruction이 실행되어야 함
- 레지스터에 올라와 있는 데이터 중 잘 안쓰는 것은 메모리에 보내버리고 나중에 필요할 때 다시 읽어오는 식으로 작동
- 제한된 개수의 레지스터를 가지고 돌아가면서 사용
- 계산해놓은 값은 메모리에 저장했다가 나중에 사용할 때 다시 읽어오는 방식
- 성능을 높이기 위해서는 레지스터를 얼마나 효율적으로 사용하는지가 중요
RISC-V memory
* Store는 arithmetic instruction이 아님.
Sign-extension vs Zero-extension
- 만약 데이터가 8bit여도 레지스터가 32bit이기 때문에 32bit로 확장되어야 함
- signed이면 첫 번째 bit를 기준으로 채우고, unsigned라면 0으로 채움
Branch
- 2's complement range: [-2^n-1, 2^n-1 -1]
- PC-relative addressing tㅏ용
- 절대값이 따로 있는 것이 아니라 그 주소를 기준으로 +-2^11 byte 안의 범위에서 이동 가능
- Instruction은 4 byte이기 때문에, 현재 instruction 기준으로는 +-2^9 범위 안의 instructions으로 이동 가능
- 이 두 비트 값을 저장하지 않고 당연히 2비트라고 생각하고 계산하면 더 많은 범위를 이동 가능word 단위로 이동하기 때문에 instruction의 마지막 2비트는 항상 00임
- (PC + immediate)는 3개의 Instruction 또는 12 byte를 이동
- 정리하자면, 현재 PC를 기준으로 +-2^11 instructions(+-2^13 bytes)를 이동할 수 있음
- RISC-V에서는 16-bit comprressed instruction과 16bit의 배수의 길이의 variable-length instructions의 extension을 지원함
- 16-bit encoding 또한 지원해야 하기에, 마지막 2비트를 다 버리면 안됨. 1bit만 버릴 수 있음(마지막 1개 bit만 0이라고 가정하고 계산)
- 그래서 +-2^10 32-bit instructions(+-2^12 bytes) 범위 내에서만의 이동을 지원함
- C-extension 같은 경우에는 4byte아니라 2byte 기준으로 구분짓는데, 마지막 2bit를 버리면 이와도 호환이 안됨
- 그래서 [13:2]를 사용하는 것이 아니라 [12:1]를 사용해서 1개만 버리는 방식을 채택
728x90
반응형
'Computer Science > Computer Architecture' 카테고리의 다른 글
[Computer Architecture] Arithmetic for computers (0) | 2024.02.08 |
---|---|
[Computer Architecture] Instructions: Language of the computer - 2 (0) | 2024.02.07 |
[Computer Architecture] Performance (1) | 2024.01.23 |
[Computer Architecture] ISA(Instruction Set Architecture) (0) | 2024.01.10 |
[Computer Architecture] Computer improvement (0) | 2024.01.08 |