오늘 끝나면
CPU+GPU를 하나의 SoC로
- ✓CPU+GPU를 하나의 SoC로의 핵심 문제를 한 문장으로 설명한다
- ✓오른쪽 실습에서 CPU+GPU를이 어떻게 움직이는지 관찰한다
- ✓다음 강의와 이어지는 한계를 말할 수 있다
실습 미션
command buffer→DMA→GPU 실행→interrupt 이 문장이 실제로 무슨 뜻인지 실습에서 한 번 손으로 확인한다.
성공 조건
- □실습의 기본값을 먼저 관찰
- □입력값이나 모드를 한 번 이상 바꿔 결과 비교
- □왜 결과가 바뀌었는지 한 문장으로 설명
반도체 설계 · 33
CPU+GPU를
하나의 SoC로
CPU와 GPU는 따로 노는 칩이 아니다.
한 SoC 안에서 손발을 맞춘다.
CPU가 일감을 적어 넘기면 GPU가 처리하고, 끝나면 알림을 보낸다.
SoC, 한 칩 위에 다 올린다
SoC는 System on a Chip이다. CPU와 GPU, 메모리, bus를 따로 사지 않고 한 다이 위에 다 올린 것이다.
지금까지 만든 16비트 CPU와 4 lane GPU도 결국 한 칩 안에 같이 들어간다.
두 코어는 같은 bus를 공유하고, 같은 shared memory를 들여다본다.
물리적으로 붙어 있으니 둘 사이를 오가는 길이 짧고 빠르다.
문제는 역할이 다르다는 점이다.
CPU는 순서와 판단, 제어에 강해서 분기 많은 일을 맡는다.
GPU는 같은 연산을 수천 칸에 흩뿌리는 데 강해서 데이터가 많은 일을 맡는다.
그래서 CPU가 지휘하고 GPU가 무거운 계산을 떠받치는 분업이 된다.
command buffer로 일감을 적어 넘긴다
CPU는 GPU를 직접 조종하지 않는다. 일감을 글로 적어 큐에 쌓아둘 뿐이다.
이 큐가 command buffer다. 메모리 한 칸에 명령들을 줄줄이 적는다.
‘이 입력을, 이 연산으로, 결과는 여기에’ 같은 일감을 한 줄씩 기록한다.
CPU는 적기만 하고 자기 일을 계속한다. GPU는 준비되면 큐에서 꺼내 읽는다.
왜 직접 안 시키고 큐를 두는가. 둘의 속도가 다르기 때문이다.
CPU가 명령 하나 적는 사이 GPU는 앞 일감을 처리 중일 수 있다.
큐가 둘 사이의 박자 차이를 흡수한다. CPU는 밀어넣고 GPU는 자기 페이스로 비워간다.
이 비동기 전달이 통합의 핵심이다.
doorbell과 DMA로 깨우고 끌어온다
큐에 적기만 하면 GPU는 모른다. 적었다는 신호를 따로 줘야 한다.
그 신호가 doorbell이다. CPU가 GPU의 START 레지스터에 1을 쓴다.
레지스터 한 칸 값이 바뀌는 순간 GPU가 ‘일감 왔다’를 알아챈다.
초인종을 누르듯 한 번 두드려 깨우는 것이다.
깨어난 GPU는 입력을 직접 끌어온다. 이걸 DMA가 한다.
DMA는 CPU를 거치지 않고 메모리와 GPU 사이를 통째로 옮기는 전용 길이다.
단, DMA가 bus를 잡는 동안엔 CPU의 메모리 접근이 잠깐 막힌다. 이게 contention이다.
그래서 입력을 한 타일씩 끊어 옮기며 bus를 너무 오래 잡지 않게 설계한다.
레지스터 한 칸 값이 바뀌면 GPU가 일감을 알아챈다
직접 STEP으로 통합 흐름을 돌린다
오른쪽에서 CPU와 command, bus, GPU, 메모리를 한 화면으로 잇고, 전체 흐름을 STEP으로 한 단계씩 돌려본다.
돌리기 전에 먼저 찍어본다. 입력 길이와 lane 수를 보고 GPU 처리에 몇 박자(compute STEP)가 걸릴지 예측한다.
STEP을 누르면 일감이 cmd 큐에 적히고, START가 켜지고, DMA가 입력을 끌어오고, lane이 동시에 처리하고, 마지막에 DONE이 서며 interrupt가 뜬다.
지금 일하는 블록만 진하게 보이고 노는 블록은 흐리다.
DMA 박자엔 bus가 빨개지며 GPU가 점유하고, 그 박자엔 CPU가 대기하는 contention이 눈에 보인다.
이 통합 흐름(command buffer, doorbell, DMA, interrupt)이 최종 MyChip의 CPU와 GPU 연결로 들어간다.
START 누르면 CPU가 cmd 큐에 일감을 적는 1단계부터 진행한다.
compute 단계에 들어가면 lane이 켜진다. 다른 단계엔 GPU 코어가 놀고 DMA·CPU가 일한다.
START를 누르면 CPU가 command buffer에 일감을 적는 것부터 시작한다.
이 통합 흐름, command buffer + START doorbell + DMA + DONE interrupt, 이 최종 MyChip의 CPU↔GPU 연결로 들어간다.
interrupt로 끝났다고 알린다
GPU가 다 끝내도 CPU가 모르면 소용없다. 끝났다는 신호를 거꾸로 올려야 한다.
GPU는 결과를 shared memory에 되쓴 뒤 DONE 레지스터를 세운다.
그리고 CPU에 interrupt를 쏜다. 하던 일을 멈추고 이리 보라는 신호다.
초인종이 CPU에서 GPU로 향했다면, interrupt는 GPU에서 CPU로 거꾸로 누르는 초인종이다.
왜 굳이 interrupt인가. CPU가 DONE을 계속 들여다보면(polling) 그 시간을 통째로 버린다.
interrupt면 CPU는 다른 일을 하다가 신호가 올 때만 잠깐 깨어나 결과를 회수한다.
깨어난 CPU는 ISR로 들어가 DONE을 확인하고 shared memory의 결과를 가져온다. 한 사이클이 닫힌다.
Q. CPU가 GPU에 일을 시키는 방식은?
정답은 command buffer에 일감을 적고 DMA와 interrupt로 주고받는다이다.CPU는 command buffer에 일감을 적고 START 레지스터(doorbell)로 GPU를 깨운다.
GPU는 DMA로 입력을 끌어와 처리한 뒤 결과를 shared memory에 되쓰고, DONE을 세워 interrupt로 CPU에 알린다.
즉 메모리에 적어 넘기고(command buffer), 신호로 깨우고(doorbell, interrupt), 데이터는 DMA로 옮기는 비동기 분업이다.
CPU가 DONE을 계속 들여다보다가 그 시간을 통째로 버린다
신호 올 때만 깨어나서 그 사이 CPU는 다른 일을 한다