3 분 소요

레지스터(Register)

먼저 레지스터란 CPU 내부의 작은 임시 저장 장치를 뜻한다. 말 그대로 필요한 값이나 주소 등을 '임시'로 저장한 장치. 용도에 따라 이름이 다양하고, 제조 회사별 명칭이 상이하다. 책에서 설명한 레지스터의 종류는 8가지!

인출 사이클에 쓰이는 기본 레지스터 4가지

  1. 프로그램 카운터(PC): 메모리에서 읽어 들일 명령어의 주소를 저장. 명령어 포인터(IP)
  2. 명령어 레지스터(IR): 방금 메모리에서 읽어 들인 명령어를 저장.
  3. 메모리 주소 레지스터(MAR): 메모리의 주소를 저장.
  4. 메모리 버퍼 레지스터(MBR): 메모리에 쓰고 싶은 값이나 메모리로부터 전달받은 값 저장. 메모리 데이터 레지스터(MDR)

즉 PC와 MAR은 주소를, IR과 MBR은 실질적인 값을 저장한다. 저장 내용물의 차이. 이 4개의 레지스터가 어떻게 쓰이는 지를 개략적으로 보기 위해, 인출 사이클(Fetch Cycle)을 먼저 살펴보자. 메모리에 있는 명령어를 CPU로 가져오는 단계를 '인출 사이클'이라고 하는데, 진행은 다음과 같다.

  1. 읽어올 명령어의 주소를 얻기 위해 프로그램 카운터(PC)에서 메모리 주소 레지스터(MAR)로 주소 버스를 내보냄.
  2. 제어 장치의 신호에 맞추어 MAR의 값이 각각 제어 버스와 주소 버스를 통해 메모리로 전달
  3. 해당 주소에 저장된 값(명령어)는 데이터 버스를 통해 메모리 버퍼 레지스터(MBR)로 전달
  4. PC의 값은 1 증가되어 다음 명령어를 읽어 들일 준비
  5. MBR에 저장된 값은 명령어 레지스터(IR)로 이동

이외의 레지스터 4가지

  1. 플래그 레지스터(flag register): ALU 연산 결과에 따른 플래그를 저장
    • 부호 플래그(sign flag): 연산 결과의 부호를 나타냄. 1이면 음수, 0이면 양수
    • 제로 플래그(zero flag): 연산 결과가 0인지 여부를 나타냄. 1이면 0, 0이면 0 아님
    • 캐리 플래그(carry flag): 연산 결과 올림수/빌림수 발생 여부를 나타냄. 1이면 발생, 0이면 아님
    • 오버플로우 플래그(overflow flag): 오버플로우 발생 여부를 나타냄. 1이면 발생, 0이면 아님
    • 인터럽트 플래그(interrupt flag): 인터럽트 가부 여부를 나타냄. 1이면 가능, 0이면 불가능
    • 슈퍼바이저 플래그(supervisor flag): 커널/사용자 모드를 나타냄. 1이면 커널, 0이면 사용자
  2. 범용 레지스터(general purpose register): 데이터와 주소를 모두 자유로이 저장 가능한 레지스터
  3. 스택 포인터(stack pointer): 스택의 꼭대기(마지막으로 저장한 값의 위치)를 가리키는 레지스터
  4. 베이스 레지스터(base register): 메모리의 '기준 주소'를 나타내는 레지스터

주소 지정 방식(addressing mode)

명령어(instruction)는 연산 코드(operation code, 연산자)와 오퍼랜드(operand, 피연산자)로 구성되는데, 이 오퍼랜드의 주소를 유효 주소(effective address)라 한다. 이 유효 주소를 찾는 방법이 '주소 지정 방식'이다.

기본 주소 지정 방식 5가지

  • 즉시 주소 지정 방식(Immediate Addressing): 연산에 사용할 데이터를 직접 명시
  • 직접 주소 지정 방식(Memory Direct Addressing): 유효 주소(메모리 주소)를 직접 명시
  • 간접 주소 지정 방식(Memory Indirect Addressing): 유효 주소의 주소를 명시
  • 레지스터 주소 지정 방식(Register Addressing): 유효 주소(레지스터 이름)를 명시
  • 레지스터 간접 주소 지정 방식(Register Indirect Addressing): 유효 주소를 저장한 레지스터를 명시

특정 레지스터를 이용한 주소 지정 방식

  • 스택 주소 지정 방식(Stack Addressing): 스택 포인터가 주소를 가리킴
  • 변위 주소 지정 방식(Displacement Addressing): 오퍼랜드 필드의 값(변위)과 특정 레지스터의 값을 더하여 유효 주소 계산
    • 상대 주소 지정 방식(PC Relative Addressing): 오퍼랜드와 프로그램 카운터(PC)의 값을 더하여 유효 주소 계산
    • 베이스 레지스터 주소 지정 방식(Base-register Addressing): 오퍼랜드와 베이스 레지스터의 값을 더하여 유효 주소 계산
이외에도 자동 증가 방식(Autoincrement)/자동 감소 방식(Autodecrement)/인덱스 방식(Indexed) 등이 있다.

명령어 사이클(Instruction Cycle)


기본적으로 메모리의 명령어를 CPU로 읽어들이는 '인출 사이클(Fetch Cycle)'과 이를 실행하는 '실행 사이클(Execution Cycle)'로 구성된다. 이때 간접주소방식 등 추가 메모리 접근이 필요한 경우 '간접 사이클(Indirect Cycle)'을, 인터럽트가 발생한 경우 '인터럽트 사이클(Interrupt Cycle)'로 들어간다. 이 중 인터럽트 사이클을 중심으로 봐보자.

  1. IO는 CPU에 인터럽트 요청 신호(INTR), CPU는 실행 사이클이 끝나고 명령어 인출 전에 항상 인터럽트 여부를 확인
  2. CPU가 인터럽트 요청을 확인하면, 인터럽트 가능 플래그(IE)를 통해 수용 여부를 확인
  3. AND(INTR, IE)==1인 경우 현재 실행하던 프로그램을 중단하고 CPU는 PC(프로그램 카운터)와 SR(상태 레지스터)를 스택에 저장
  4. CPU는 인터럽트 벡터(Interrupt Vector)를 참조해[도식 3번] 메모리에 저장된 인터럽트 서비스 루틴(ISR)을 실행[도식 4번]
  5. ISR이 끝나면 스택에서 작업을 복구해 실행을 재개[도식 5번]

인터럽트(Interrupt)

그럼 앞에서 계속 언급한 인터럽트는 뭘까? CPU가 작업을 잠시 중단해야하는, 즉 현재 작업보다 더 중요한 일이 있어서 작업을 방해하는 신호를 인터럽트(interrupt)라고 한다.

interrupts

먼저 동기 인터럽트(synchronous interrupts)는 CPU에 의해 발생하는 인터럽트로, 흔히 예외(exception)라고 부른다. 종류는 이하와 같음

  • 폴트(fault): 예외를 처리한 직후, 예외가 발생한 명령어부터 실행을 재개하는 예외
  • 트랩(trap): 예외를 처리한 직후, 예외가 발생한 명령어의 다음 명령어부터 실행을 재개하는 예외. 디버깅이나 주소 공간 침해 시 발생
  • 중단(abort): CPU가 실행 중인 프로그램을 강제로 중단시킬 수밖에 없는 심각한 오류 시 발생하는 예외
  • 소프트웨어 인터럽트(software interrupt): 사용자 모드의 프로그램이 OS 서비스를 제공받기 위해 시스템 호출(system call)을 할 때의 예외
다음으로 비동기 인터럽트(asynchronous interrupts)는 주로 IO unit에 의해 발생하는 인터럽트로, 일종의 알람을 담당한다. 하드웨어 인터럽트라 칭할 수 있다.
  • 무시 가능 인터럽트(maskable interrupt): IE==1일 때만 처리 가능한 인터럽트
  • 무시 불가 인터럽트(non maskable interrupt): IE가 0이더라도 강제로 처리하는, 가장 우선순위가 높은 인터럽트. 정전이나 HW 고장 시 발생

출처: [혼자 공부하는 컴퓨터구조+운영체제 Chapter 04]