/ #기타

명령어 사이클과 인터럽트

명령어 사이클(Instruction Cycle)

CPU는 프로그램 명령어를 클럭에 따라 일정한 주기를 반복하여 실행하는데, 이 주기를 명령어 사이클(Instruction Cycle)이라고 합니다.

명령어 사이클은 CPU가 하나의 명령어를 실행하는 데 필요한 전체 처리 과정으로서, CPU가 프로그램을 실행한 순간부터 전원을 끄거나 오류가 발생하여 프로그램이 중단될 때까지 반복됩니다.

명령어 사이클은 주 기억 장치로부터 명령어를 읽어오는 단계인 인출 사이클(Fetch Cycle)과 명령어를 실행하는 단계인 실행 사이클(Execution Cycle)로 분리할 수 있습니다.

img079

인출 사이클(Fetch Cycle)

인출 사이클의 진행은 다음과 같습니다.

img080

t0 : MAR <- PC
t1 : MBR <- M[MAR], PC <- PC + 1
t2 : IR <- MBR

첫 번째 주기 t0에서는 프로그램 카운터(PC)에 저장된 명령어 주소를 CPU 내부 버스를 통해 메모리 주소 레지스터(MAR)로 보냅니다.

두 번째 주기 t1에서는 MAR가 지정하는 기억장치 주소로부터 명령어를 읽어서 데이터 버스를 통해 메모리 버퍼 레지스터(MBR)에 저장합니다. 동시에 프로그램 카운터가 1 증가합니다.

세 번째 주기 t2에서는 MBR에 저장된 명령어를 명령어 레지스터(IR)에 저장합니다.

실행 사이클(Execution Cycle)

실행 사이클 동안에는 CPU가 명령어 코드를 해독(decode)하고, 그 결과에 따라 필요한 연산들을 수행합니다. CPU가 수행하는 연산에는 데이터 이동, 데이터 처리, 데이터 저장, 프로그램 제어가 있습니다.

명령어는 연산 코드(Operation Code)와 오퍼랜드(operand)로 구성됩니다.

img081

실행 사이클에서 수행되는 마이크로 연산들은 명령어의 연산 코드에 의해 결정되며, 명령어 실행에 필요한 데이터가 저장된 주소는 오퍼랜드에 의해 결정됩니다.

데이터 이동: Load addr 명령어

Load ddr 명령어은 기억장치에 저장되어 있는 데이터를 CPU 내부 누산기(AC)에 저장하는 명령어 입니다.

t0 : MAR <- IR(addr)
t1 : MBR <- M[MAR]
t2 : AC <- MBR

첫 번째 주기 t0에서는 명령어 레지스터(IR)에 있는 오퍼랜드를 메모리 주소 레지스터(MAR)에 저장합니다.

두 번째 주기 t1에서는 MAR가 지정하는 기억장치 주소로부터 데이터를 읽어서 메모리 버퍼 레지스터(MBR)에 저장합니다.

세 번째 주기 t2에서는 MBR에 저장된 데이터를 누산기(AC)에 저장합니다.

데이터 저장: STA addr 명령어

STA addr 명령어은 누산기(AC)에 저장된 데이터를 기억장치에 저장하는 명령어 입니다.

t0 : MAR <- IR(addr)
t1 : MBR <- AC
t2 : M[MAR] <- MBR

첫 번째 주기 t0에서는 명령어 레지스터(IR)에 있는 오퍼랜드를 메모리 주소 레지스터(MAR)에 저장합니다.

두 번째 주기 t1에서는 누산기(AC)에 저장된 데이터를 메모리 버퍼 레지스터(MBR)에 저장합니다.

세 번째 주기 t2에서는 MBR에 저장된 데이터를 MAR가 지정하는 기억장치 주소에 저장합니다.

데이터 처리: ADD addr 명령어

ADD addr 명령어은 기억장치에 저장된 데이터를 누산기(AC)에 저장된 값에 더하여 그 결과를 다시 누산기에 저장하는 명령어 입니다.

img082

t0 : MAR <- IR(addr)
t1 : MBR <- M[MAR]
t2 : AC <- AC + MBR

첫 번째 주기 t0에서는 명령어 레지스터(IR)에 있는 오퍼랜드를 메모리 주소 레지스터(MAR)에 저장합니다.

두 번째 주기 t1에서는 저장할 데이터를 MAR가 지정하는 기억장치 주소로부터 읽어서 메모리 버퍼 레지스터(MBR)에 저장합니다.

세 번째 주기 t2에서는 MBR에 저장된 데이터를 산술논리연산장치(ALU)에서 연산하여 그 결과값을 누산기(AC)에 저장합니다.

프로그램 제어: JUMP addr 명령어

JUMP addr 명령어은 오퍼랜드가 가리키는 주소의 명령어로 실행 순서를 변경하는 분기(branch) 명령어 입니다.

t0 : PC <- IR(addr)

명령어 레지스터(IR)에 저장된 오퍼랜드를 PC에 저장하여 명령어 순서를 변경합니다.

인터럽트(Interrupt)

인터럽트는 컴퓨터 내부나 외부에서 발생하는 갑작스러운 사건에 대응하는 기능입니다. 인터럽트 요청이 발생하면 CPU는 현재 처리 순서를 중단하고 요구된 인터럽트 서비스 프로그램을 먼저 수행하게 됩니다.

img083

위에 그림처럼 명령어 사이클은 인출(fetch)과 실행(execution) 사이클이 반복되는데, 실행 사이클이 끝날때마다 CPU는 반복적으로 인터럽트 요청이 발생했는지 확인합니다.

img084

인터럽트 요청이 발생했다면 프로그램 실행을 중단하고 인터럽트 처리를 합니다. 인터럽트 요청을 처리한 이후에는 다시 프로그램을 재실행합니다.

인터럽트 종류

인터럽트는 크게 내부 인터럽트와 외부 인터럽트로 나눌 수 있습니다.

내부 인터럽트는 다음과 같은 상황에서 발생합니다.

1. 하드웨어 고장 : 정전, 패리티 비터 오류 등
2. 실행할 수 없는 명령어 : 정의되지 않은 명령어
3. 명령어 실행 오류 : 0으로 나눈 경우
4. 사용 권한 위배

주로 긴급한 상황에 발생하기 때문에 상태 레지스터의 인터럽트 플래그를 통한 제어가 불가능합니다.


외부 인터럽트는 주로 입출력 장치에 의해 발생하며, 여기에는 타이머 인터럽트와 입출력 인터럽트가 있습니다.

1. 타이머 인터럽트 : 일정한 시간 간격으로 CPU에게 인터럽트를 요청합니다.
2. 입출력 인터럽트 : 속도가 비교적 느린 입출력장치의 사용 준비가 완료되었음을 알리기 위해 인터럽트를 요청합니다.

외부 인터럽트는 인터럽트 플래그를 통해 제어할 수 있습니다.

인터럽트 처리 순서

img087

1. 입출력장치에서 CPU에 인터럽트 요청 신호(Interrupt Request, INTR)를 보냅니다.

img085

2. CPU는 실행 사이클을 끝내고 인터럽트 요청신호를 확인합니다. 인터럽트 요청을 확인 후 인터럽트 가능 플래그(Interrupt Enable Flag, IE)를 통해 현재 인터럽트를 받아들일 수 있는지 확인합니다.

img086

3. 인터럽트를 받아들일 수 있다면 현재 실행하던 프로그램을 중단하고, PC(Program Counter)SR(Status Register)를 스택에 저장합니다.

4. CPU는 인터럽트 벡터(Interrupt Vector)를 참조하여 인터럽트 서비스 루틴(Interrupt Service Routine, ISR)을 실행합니다.

ISR는 인터럽트가 발생한 경우 인터럽트를 처리하기 위한 프로그램으로, 일반적으로 메모리에 저장되어 있습니다.

5. ISR 실행이 끝나면 스택에 저장한 PC와 SR값을 복구하여 프래그램 실행을 재개합니다.