CS 공부/[강의] 혼공 컴퓨터구조 + 운영체제

[8/28] 명령어 병렬 처리 기법

달려라 태깅이 2023. 8. 28. 00:42

 

컴퓨터 공학 기초강의

 

 

 

시간을 알뜰히 쓰며 메모리의 명령어들을 처리하는 방법

멀티코어와 멀티스레드를 이용해 CPU를 설계함도 중요하지만,

어떻게 CPU가 시간분배를 잘하여 메모리의 명령어들을 빠르게 실행하느냐도 중요하다.

 

 

 

방법 1.  명령어 파이프라인

명령어파이프라인(라이닝)은 동시에 여러개의 명령어를 겹쳐 실행하는 기법.

명령어파이프라인은 CPU에서 명령어들이 순차적으로 처리되는 단계들의 연속으로 구성됨. 각 단계는 다음명령어를 처리하기 위해 파이프라인 내의 이전단계를 기다리지 않아 병령처리가 가능하며 전체적인 성능향상을 도모한다. 명령어파이프라인을 사용하지 않으면 CPU의 작업시간이 길어진다. 

 

 

→ 하나의 명령어가 처리되는 과정을 시간간격으로 나눠보자.

    전공서에 따라 [인출 → 실행] / [명령어해석 → 명령어실행 → 명령어접근 → 결과저장] 으로 나누기도 함

 

1. 명령어 인출 Instruction Fetch ( 메모리로부터 명령어 가져오기 )

2. 명령어 해석 Instruction Decode

3. 명령어 실행 Execute Instruction

4. 결과저장  Write Back ( 필요하다면 결과값을 메모리에 다시 저장 )

 

 

 같은 단계가 겹치지만 않는다면 CPU는 각 단계를 동시에 실행할 수 있다.

 즉,  명령어를 동시에 병렬적으로 처리하는 명령어 파이프라이닝이 가능하다.

________________________________________________________

 

                       t0       t1       t2       t3       t4       t5     

명령어1          인출 - 해석 - 실행 - 저장

명령어2                    인출 - 해석 - 실행 - 저장

명령어3                              인출 - 해석 - 실행 - 저장

 

________________________________________________________

t2 순간에는 명령어 1 (실행) , 명령어 2 (해석) , 명령어 3 (인출) 로,

병렬적으로 명령어가 처리되고 있다.

 

 

 

 

파이프라인 위험

명령어파이프라인이 성능향상에 실패하는 경우 (파이프라인 해저드)

항상 이상적으로 동시에 명령어를 처리할 수 없는 상황 (병렬로 올바르게 명령어가 실행되지 않는 상황) 이 있다. 이러한 파이프라인 위험발생시 파이프라이닝이 제대로 작동하지 않아 성능향상에 실패한다.

 

 

 

파이프라인 위험의 3가지 종류  

 

- 데이터 위험 (Data Hazard) : 명령어간 의존성에 의해 발생

이전 명령어를 끝까지 실행해야만 비로소 실행이 가능한 경우가 있다. 만약 명령어 1 (R1 <- R2 + R3) , 명령어 2 (R4 <- R1 + R5) 라면 ,

명령어 1의 R1이 업데이트 된 후에 2를 실행할 수 있기에 명령어 1 을 해석할 동안 명령어 2의 인출이 불가하다.

 

 

 

 

- 제어위험 (Control Hazard) : 프로그램 카운터의 갑작스러운 변화로 발생

프로그램카운터가 갑자기 특정메모리 주소로 바뀌는 경우가 있다. 즉, CPU가 실행하고자 하는 메모리 주소번지가 갑자기 다른 특정 메모리 주소 번지로 실행의 흐름을 바꾸게 되는 명령어 들이 존재한다(JUMP, 인터럽트 등) . 기본적으로 명령어들을 순차적으로 실행하는데, 10번지의 명령어를 실행해보니 60번지로 분기해야 한다면 프로그램 카운트가 갑자기 변경되는 상황이 된다. 그럼 10번지 명령어 아래에 병렬적으로 수행되고 있던 11번지,12번지...등의 작업들은 프로그램 카운트의 갑작스런 변경으로 헛수고가 된다. 

 

분기예측 branch prediction

: 이런상황을 방지하기 위해 프로그램카운터가 어디로 JUMP할 것인지 미리 예측하는 기술도 존재한다.

 

 

 

 

- 구조적위험(Structural Hazard)

: 서로 다른 명령어가 같은 CPU 부품(ALU, 레지스터) 을 사용하려고 할때 발생

구조적 위험은 CPU가 필요한 자원(예 : 메모리, 함수유닛) 이 다른 명령어에 의해 사용중일 때 발생한다. 즉, 두 개 이상의 명령어가 동시에 같은 자원을 사용하려 시도할 때 발생하는 충돌을 말한다. 예를 들어, 만약 파이프라인의 특정 단계에서 메모리에 접근해야하는데 해당 메모리가 다른 명령어에 의해 이미 사용중이면, 해당 단계는 메모리가 사용 가능해질때까지 기다려야 한다. 이로인해 파이프라인의 다른 단계들도 대기상태로 전환되어 성능저하가 발생한다.

 

자원복제

구조적위험을 해결하기 위한 방법 중 하나로, 예를들어 데이터를 동시에 읽을 수 있도록 메모리 포트를 더 추가하는 것이다. 하지만 이것은 하드웨어의 복잡성과 비용증가로 이어질 수 있어 아키텍처 설계시 이런 점을 고려해 효율적 방법을 찾아야 한다.

 

1. ALU 복제

: ALU는 산술 및 논리연산을 수행하는 유닛으로 몇몇 고성능 프로세서에는 여러 ALU를 가지고 있어 복수의 산술 및 논리 연산을 동시에 수행할 수 있다.

 

2. 메모리포트

: 메모리 접근충돌을 방지하기 위해, 데이터 캐시나 메모리에 여러포트를 가진 구조를 볼 수 있는데, 이렇게 함으로써 여러 명령어가 동시에 메모리에 접근하는 것이 가능하다.

 

3. FPU(Floating Point Unit) 복제 

: 부동소수점 연산을 담당하는 FPU도 복제될 수 있다. 특히 수치 연산 집약적인 작업에서 유용하게 활용된다.

 

4. 분기예측유닛

: 최신프로세서에서는 분기예측의 정확도를 높이기 위해 분기예측 유닛을 여러개 가질 수 있다.

 

 

 

 


 

 

방법 2.  슈퍼스칼라

CPU 내부에 여러개의 명령어 파이프라인을 포함한 구조로 프로세서의 성능을 향상시키는 아키텍처 기법(전략)이다. 슈퍼스칼라 아키텍처는 여러개의 명령어를 동시에 실행할 수 있는 프로세서로 이를위해 프로세서에는 여러개의 ALU, FPU와 같은 함수유닛을 포한한다. 이 아키텍처는 명령어 파이프라인에서 독립적인 여러 명령어들을 동시에 파이프라인의 다양한 단계에 할당함으로써 병렬처리를 증가시킨다. 또한 속도 부분에 있어서, 이론적으로는 파이프라인 개수에 비례해서 처리속도가 빨라지지만 파이프라인 위험도의 증가로, 개수에 비례해서 꼭 처리속도가 증가하는 것은 아니다. (관리해야 하는 파이프라인이 많아질수록 위험도 또한 증가)

 

 

오늘날의 멀티스레드 프로세스

슈퍼스칼라 멀티코어 프로세서는 각 코어내에서 병렬 명령어 실행 능력을 갖추고 있을 뿐 아니라, 각 코어가 하드웨어 스레딩을 지원할 수도 있다. 하드웨어 스레딩은 단일 프로세서 내에서 동시에 여러 스레드의 실행을 지원하는 것으로 각각의 코어가 동시에 수행할 수 있는 단위이다. 그것이 여러개 있는 스레드를 멀티스레드 프로세스라고 부른다.

 

정리하면, 현대의 많은 고성능 프로세서는 슈퍼스칼라와 멀티스레딩 기술을 통합하여 사용하고 있다. 이렇게 되면 프로세서는 동시에 여러 스레드를 실행할 수 있으면서 각 스레드 내의 명령어들도 병렬적으로 처리할 수 있게 된다.

 

 

 

 


 

 

방법 3.  비순차적 명령어 처리  OOOE

쉽게 말해 합법적인 명령어들 간의 새치기다. 파이프라인의 중단을 방지하기 위해 명령어를 순차적으로 처리하지 않는 명령어 병렬 처리 기법으로, 현대 CPU 발전에 많은 기여를 한 매우 중요한 기술이다.

 

지금까지 설명한 명령어파이프라이닝, 슈퍼스칼라는 모두 순차적으로 명령어를 처리하는 방식이다. 하지만 이전 명령어를 끝까지 실행해야만 비로소 실행이 가능한 경우에 이런 순차적 실행으로는 이상적인 명령어 병렬처리가 불가하다. 그런데 비순차적 명령어 처리를 지원하는 CPU는 순서를 바꿔도 전체 프로그램의 실행흐름에 영향이 없을 경우 (의존성이 없는 명령어일 경우) , 명령어의 순서를 바꿔 파이프라이닝이 좀 더 원활이 동작하도록 한다. 즉, 파이프라이닝의 중단을 방지할 수 있다.  물론 이런 판단은 비순차적 명령어 처리를 지원하는 CPU가 알아서 해준다.

 

 

 

 


 

 

명령어 병렬 처리기법은 컴퓨터의 성능향상을 위해 고안된 중요한 전략 중 하나

 

 

 

명령어 처리 기법이 필요한 이유

 

1. 성능향상

: 여러 명령어를 동시에 실행할 수 있어 프로세서의 처리능력 향상

 

2. 클럭속도의 한계

: 트랜지스터 크기의 축소와 함께 클럭속도를 계속 높이는 것이 점점 어려워지고 있다. 클럭속도만을 통한 성능향상에 한계가 오면 병렬처리를 통해 성능을 높이는 방향으로 전환된다.

 

3. 에너지 효율

: 병렬처리를 활용하면 높은 성능을 낮의 전력으로 달성할 수 있는데, 단일 명령어를 더 빠르게 처리하기 위한 높은 클럭속도는 상대적으로 더 많은 에너지를 소모하게 된다.

 

 

 

 

병렬처리 기법들의 오늘날 활용방식

 

1. 멀티코어 프로세서

: 대부분의 현대컴퓨터에는 여러개의 프로세서 코어가 포함돼 있다. 각 코어는 독립적인 연산을 수행할 수 있어 여러작업을 동시에 처리할 수 있다.

 

2. 슈퍼스칼라 아키텍처

: 현대의 고성능 프로세서는 슈퍼스칼라 설계원칙을 기반으로 하며, 동시에 여러명령어를 실행할 수 있는 여러 실행 유닛을 포함한다.

 

3. SIMD ( Single Instruction, Multiple Data ) 

: SIMD 명령어는 한번의 명령어로 여러 데이터에 동시에 연산을 수행한다. 그래픽처리유닛 GPU 와 같은 곳에서 주로 활용된다.

 

4. GPU ( Graphics Processing Unit ) 

: GPU는 병렬처리에 매우 특화된 하드웨어로, 수천개의 코어를 포함하고 있어 병령작업에 매우 효율적이다. 최근에는 그래픽 처리 뿐만 아니라 딥러닝, 과학계산 등 다양한 분야에서 활용된다.

 

5. 하드웨어 멀티스레딩

: Intel 의 Hyper-Threading 기술처럼, 싱글 코어에서 여러스레드를 거의 동시에 실행할 수 있게 해준다.

 

6. 명령어 레벨 병렬성

 : 최적화된 컴파일러와 함께 사용되어, 병렬로 실행될 수 있는 명령어를 자동으로 찾아낸다.