본문 바로가기
MCU 통신/이론

DMA(Direct memory access)

by [Akashic Records] 개발의선지자 2026. 8. 10.

개념

메모리와 주변장치 또는 메모리와 메모리 사이에서 CPU 점유없이 높은 전송 속도를 가진 데이터 전송 컨트롤러

(CPU가 개입하기에는 데이터 양이 너무 많거나 전송 주기가 너무 빈번하여 CPU 효율을 떨어뜨릴 때 사용하는 하드웨어 오버로드 방지 엔진)

 

메모리 : SRAM, Flash 등, 언제든지 Read/Write 가능하므로 DMA 요청 신호없이 바로 전송 가능

비메모리 주변 장치 : RX FIFO 데이터가 차거나 TX FFO가 빌 떄만 전송 가능, DMA에 "지금 데이터 송/수신" 신호를 보내야 한다.

 

Handshake Interface(DMA 요청 신호)

: 데이터를 옮길 때 "나 준비됐어!" <-> "데이터 가져갈게!" 하고 주변장치와 DMA가 주고받는 신호(signal)

종류

일반적으로 H/W Handshake 세팅

H/W Handshake : CPU 개입 없이 주변장치
Peripheral <-- H/W 신호선 --> DMAC <-- IRQ --> CPU

 

S/W Handshake : H/W 신호선이 없는 특수한 디바이스에 CPU가 직접 레지스터를 세팅하여 DMA 발생 

CPU -- (레지스토 쓰기 ReqSrcReg = 1) --> DMAC  <-- 전송 --> Peripheral

특징

mcu가 독립된 복수의 채널 설정 가능하다면 동시에 여러 주변장치가 DMA 사용할 수 있다.

또한 각 채널 별 독립 우선 순위 지정

 

대표적인 사용 상황

사용 원칙 : CPU는 제어/연산(Business Logic)에 집중하고, 단순한 메모리 복사 작업은 DMA에게 전담

 

1. 대용량 연속 데이터 전송 (High Throughout)

 

2. 높은 주기/연속 센서 데이터 수집 (High Rate Sampling)

 

3. 가변 길이의 비동기 통신 수신 (Uart Circular RX)

 

4.오디오/음성 입출력 (I2S/SAI Interface)

모드 (MH1903 경우)

Normal 모드 :

한번 지정된 길이만큼 전송이 끝나면 DMA가 멈추고 완료 인터럽트 발생 

그리고 나서 CPU가 인터럽트를 처리하고 다음 전송 메모리 주소와 크기를 DMA에 세팅 뒤 재시작

 

Multi-block 모드 :

대용량 데이터를 여러 개의 블록 전송 정보(LLI)를 메모리에 연결한다. 그 후 하나 블록 전송이 끝나면 DMA H/W가 CPU 개입 없이 스스로 다음 설정값을 즉각 읽어와 즉각 전송을 이어간다. CPU 개입없이 연속적으로 데이터 전송 가능.

 

Multi-block  사용 이유

예시)

만약 LCD 프레임버퍼 480 X 320 해상도, RGB565 bit = 307.2KB나 SPI Flash 전체 이미지 1MB를 DMA로 전송해야 한다고 가정

 

Single-Block 방식을 사용 시 문제점

307.2KB를 전송하려면 단일 레지스터의 한계인 8KB씩 나누어 약 38번의 DMA 인터럽트를 CPU가 수동으로 받아서 주소(SAR/DAR)와 BLOCK_TS를 재설정하고 다시 Enable 해주어야 합니다. 이 과정에서 CPU 잦은 개입과 Context Switching 오버헤드가 발생합니다.

 

Multi-Block 전송 방식을 사용 시

 

DMAC 내부의 Linked List (LLP - Linked List Pointer) 기능이나 연속적인 블록 체이닝 기법을 활용합니다.

  • CPU가 메모리 상에 다음 전송할 Descriptor 목록(다음 주소, 전송 크기 등)을 미리 구조체 배열로 만들어 둡니다.
  • DMA 컨트롤러가 첫 번째 블록 16KB 전송이 끝나면, CPU 개입 없이 하드웨어 스스로 LLP 레지스터가 가리키는 다음 Descriptor를 읽어와서 연속으로 남은 데이터들을 이송합니다.
  • 최종적으로 전체 데이터($307.2\text{ KB}$) 이송이 모두 끝난 시점에 CPU에 인터럽트를 딱 1번만 보냅니다.

3. 실무 요약

  • Single-Block 범위 (16KB 이하): 센서 패킷, 단발성 통신 버퍼, 소형 데이터 복사 $\rightarrow$ 단일 DMA 설정으로 충분
  • Multi-Block 범위 16KB 22,528 Byte , 0x5800 초과): LCD 디스플레이 프레임 버퍼, 오디오 스트리밍, 대용량 SPI/QSPI Flash 읽기/쓰기
  • Multi-Block (Linked List Descriptor) 전송 활용 필수

용어 

전송데이터 블록 사이즈(Block Transfer Size) : DMA 전송으로 옮길수 있는 총 데이터 개수

버스트 데이터 블록 사이즈(Burst Size) : DMA 요청 1번당 연속으로 쓸 데이터 개수

데이터 폭(Data WIDTH) : 한번에 컨트롤 가능한 데이터 폭

 

전송 이벤트 시퀀스

DMA 초기화 --> DMA 채널 선택 --> SRC/DST 주소 지정 -->

Data Width, Burst Size, Block Size 설정 \ Interrupt Mask 설정 (Block Complete 인터럽트 Enable)

 

전송 시작

Memory-to-Memory: DMA Channel Enable 즉시 전송 시작 \ Memory-to-Peripheral: 주변장치(UART/SPI)의 DMA TX/RX Enable 후 Handshake H/W 시 H/W 신호 대기

 

전송 완료

DMA가 백그라운드에서 Bus 점유하여 데이터 이송 \ 지정한 Block Size 이송 완료 시 DMAC가 CPU에 Interrupt 발생 \

ISR(인터럽트 서비스 루틴) 진입

Clear Register에 '1' 써서 플래그 지움

다음 작업 수행

 

 

인터럽트  예제 코드

void DMA0_IRQHandler(void)
{
    if (DMA_GetITStatus(DMA_Channel_0, DMA_IT_BlockTransferComplete))
    {
		DMA_ClearITPendingBit(DMA_Channel_0, DMA_IT_BlockTransferComplete);
		DCMITFC++;
    }
	else if (DMA_GetITStatus(DMA_Channel_0,DMA_IT_Error))
    {
		DMA_ClearITPendingBit(DMA_Channel_0,DMA_IT_Error);
		printf("DMA_IT_Error\r\n");
	}
	
}

 

'MCU 통신 > 이론' 카테고리의 다른 글

ISO/IEC 15693  (0) 2026.07.05
[RF-NFC] EMV(PayPass) VS MIFARE VS FELICA  (0) 2025.04.22
SPI  (0) 2024.07.07
NEC Protocol  (0) 2024.06.27
RS485 모드버스 이론  (0) 2024.06.27