1.はじめに
組み込みシステムでデータ転送を効率化し、マイコンを本来の制御処理に専念させるための代表的技術がDMA(Direct Memory Access)です。ここでは、DMAの基本概念からメリット・デメリット、代表的な用途、設計上の注意点、評価指標までをわかりやすく整理します。
2.DMAとは?
各メーカーのほとんどのマイコンには、ちょっと便利な機能があります。
その名をDMA(Direct Memory Access)といいます。ひとことで言うと、「マイコンの代わりに、マイコンの中でデータを自動で運んでくれる機能」になります。
例えば・・・
・UARTで文字をたくさん受信 → マイコンが一文字ずつ拾うのは大変
・ADCでデータを連続で取得 → 毎回マイコンがコピーすると忙しい
こういう「データをひたすらコピーする仕事」を DMAが肩代わりしてくれます。
3.なぜDMAを使うのか?
イメージしやすいように、宅配便に例えてみます。
・DMAなし → マイコンが営業も配達も全部やります
・DMAあり → マイコンは営業に集中、配達はDMA(宅配員)がしてくれます
結果として、マイコンは暇になり、別の計算や処理に集中できます。よってDMAを使うことで、以下の効果が期待できます。
●マイコン負荷低減
大量データ転送をマイコンループで行う場合と比較して、転送に伴う命令実行が不要になりマイコン占有率が大幅に低下します。(例:1MByteのDMA転送があれば、マイコンでコピーに要する時間を改善できます)
●レイテンシ削減
割り込み/ポーリングの頻度を低減でき、他タスクの応答性が向上します。
●高スループット
バースト転送やペリフェラルデバイスのFIFO連携で継続的かつ高速なデータ流し込みが可能です。
●電力効率
マイコンのアクティブ時間短縮により消費電力削減につながることがあります。(※実際の改善度合いはMCUのアーキテクチャ・バス幅・クロックに依存するため、導入時にベンチマーク推奨)
4.DMAの基本要素と主要モード
●DMAコントローラ(チャネル)
同時に複数チャネルを持つことが多いです。
各チャネルに転送元・転送先アドレス、転送サイズ、転送幅、インクリメント設定、トリガ条件を設定します。
●トリガ(開始条件)
ソフトウェア起動、ペリフェラルイベント(UART受信完了、ADC変換完了、タイマ比較など)を使用します。
●転送モード例
1)メモリ→メモリ(ブロック転送)
2)ペリフェラル→メモリ(受信データ蓄積)
3)メモリ→ペリフェラル(送信バッファ供給)
4)サーキュラ(リング)モード:バッファを循環して連続転送
5)ワンショット/連続(ブロックごと/常時)
●転送幅設定
8/16/32bit等、ペリフェラルのFIFO幅やメモリアライメントに合わせることができます。
5.代表的なユースケース(実務でよく使う例)
1)ADCサンプリング→メモリ(波形取込み、信号処理の前段)
2)UART受信→メモリ(割り込み削減、長データ受信)
3)SPI/I2S/I2Cデータのバースト取得
4)メモリブロックコピー(フラッシュ→RAM、RAM→RAM)
5)DAC出力用バッファ供給(オーディオ再生など)
6)画像/センサデータのストリーミング(カメラ→メモリ)
6.設計のポイントと注意点
DMAを効果的に活用するためには、以下の点に注意して設計を進めることが重要です。
●バス競合と優先度
DMAがバスを占有すると他ペリフェラルやマイコンのアクセスが遅延します。そのためDMA優先度やバースト長、スルーリングを調整する必要があります。
●キャッシュとの整合性(キャッシュを搭載するMCU/MPUの場合)
キャッシュがある場合、DMAとキャッシュの整合を取ります。(キャッシュフラッシュ/無効化、ノーキャッシュ領域の利用)
●アライメントと転送幅
転送サイズは転送幅の倍数に揃えます。未揃えの場合、余分な転送やバスエラーが発生することがあります。
●バッファ設計
シングルバッファ/ダブルバッファ/リングバッファの選択をします。連続受信やリアルタイム処理ではダブル/リングが有効です。
●エラーハンドリング
転送エラー検出(バスエラー、CRC不整合等)と回復(リトライ、再初期化)を設計しておきます。
●割り込み設計
DMA完了割り込みは必要最小限にします。チャンク完了通知やエラー通知のみで処理を起動するようにします。
●セキュリティ
DMAはメモリ領域を直接操作するため、不正な設定で機密領域へ書き込み可能です。そのためアクセス制御/保護機構を利用するようにします。
●電源・低消費電力設計
低電力モードでDMAが動作可能か、ウェイクアップ方法はどうなるかを確認しておきます。
7.実装イメージ

①初期化
以下などを設定します。
・転送元アドレス
・転送先アドレス
・転送サイズ(転送バイト数)
・転送幅(8/16/32/64bit)
・アドレスインクリメント(転送元/転送先)
・転送モード
②トリガ設定
・マイコンペリフェラル機能の設定レジスタに、DMA有効化の設定
・マイコンDMA機能の設定レジスタに、ペリフェラル機能の使用設定
③DMAスタート
・DMA起動(DMA EN または、ペリフェラル機能のトリガで自動起動)
④転送中
・バースト転送/FIFO連携で継続転送
・中途イベント発生: 必要なら割り込み
⑤完了(割り込み処理)
割り込みハンドラ: ・転送完了フラグセット
・後段処理起動(データ処理タスクへ通知)
⑥エラーハンドリング(必要時)
転送エラー/バスエラー検知 → ログ/再試行/DMA再初期化など
8.よくある落とし穴と対処法
●ポインタ設定ミス(転送先/元の不一致)
→ 転送サイズと幅、アドレス境界をチェックするテストを自動化します。
●キャッシュ未調整でデータが更新されない
→ DMA前後でキャッシュフラッシュ/無効化を必須にします。
●割り込み過多で他処理が遅れる
→ チャンク完了ではなく大きめブロック完了で通知する設計に変更します。
●バス負荷でリアルタイム性が悪化
→ DMAバースト長や優先度、スケジューリングを調整します。
9.導入判断のための簡易チェックリスト
以下、「はい」が複数あればDMA導入を推奨します。
□データ転送量が多くマイコン負荷が高いか?
□転送の頻度・リアルタイム性(瞬間的な処理不要)に合うか?
□MCUにDMAコントローラがあり、必要チャネル数が足りるか?
□キャッシュやメモリ保護の要件は満たせるか?
□デバッグ/評価環境を用意できるか?


