M5StickV で RISC-V での 開発 事始め (HW情報編)

# M5StickVとは?

※ 本項は、HWについての情報が主となります。[SW編はlink先です](https://qiita.com/hidenorly/items/4c3ce6afddd1eb908736)。

[公式](https://m5stack.com/products/stickv)、及び、[Switch Scienceの紹介ページ](https://www.switch-science.com/catalog/5700/)もご参照。 

好評を博しているESP32を利用したM5Stack, M5StickCとは違い、今話題のRISC-VをHost CPUとし、また、AI acceleratorも搭載したSoC Kendryte K210を利用したM5Stickシリーズの新シリーズです。

RISC-Vは、ARMのいわゆるCortexのとは別のCPUのアーキテクチャで、openなコアとして注目を集めています。

M5StickVは、ESP32とは違い、WiFi/BTは搭載していませんが、先の通り、RISC-VとAI engineを搭載しているのが特徴になっています。また、8MBitという広大な "SRAM" も搭載しています。

なお、Kendryte K210自体はQuad Coreみたいですが、M5StickVとしてはDual-Coreのようです。

特徴は、

* CPU (```Dual-Core 64-bit RISC-V RV64IMAFDC (RV64GC) CPU / 400Mhz(Normal)```)
* Flash 16MBit
* TFT : ST7789 135*240
* Camera!
* PMIC : AXP192 (M5StickCと共通ですね) もちろんLipo 200mAhも搭載！
* ```AI engine``` は0.8TOpsとのことです。
* ```Dual hardware 512-point 16bit Complex FFT``` (audio用だが、単体でも利用可能そう)
* AES-128/192/256, SHA256 accelerator のCrypt HW Engine内蔵
* Audio Codec with D class Power Amp : MAX98357

なお、TSCM 28n HPMで製造とのこと 
 
# HWについて

## Kendryte K210

https://kendryte.com/downloads/ から [Kendryte K210 datasheet](https://s3.cn-north-1.amazonaws.com.cn/dl.kendryte.com/documents/kendryte_datasheet_20181011163248_en.pdf)より参照可能です

### K210 Overview

<img src="https://github.com/kendryte/kendryte-doc-datasheet/raw/master/en/images/kendryte_arch.svg?sanitize=true" width=80%>

* 144pinあり、FPIOA (Field Programmable I/O Array)により、各種I/Oのpinアサインを自由に設定できます。(IO_0からIO_47まで)


### Host CPU : RISC-V RV64GC (IMFADC)

* Dual Core
* 400MHz
* I/D-cache: 32KB per core
* ISA
    * RV64 (64bit RISC-V)
    * I: Integer
    * M: Multiply and Divider
    * A: Atomic
    * F: Single Float
    * D: Double Float
    * C: Compression Instruction (thumb的なもの)

### PLIC (Platform Level Interrupt Controller)

* 64 external interrupts
* 7 priority level

### KPU (Netral Network Processor)

* convolution (1x1, 3x3)
* batch normalization
* activation
* pooling operaration
* FIXED point (not FLOAT!)
* max NN parameter size is 5Mbit (から5.9MBit) 
* SWで入れ替えるようにすれば、flash size - software sizeまでとありますが。

### Audio Processor

* 内部処理は16bit
* 12/16/24/32 bit inputをサポート
* 最大192KHzまでサポート
* 後述のFFTをサポート

### FFT accelerator

* 64, 128, 256, 512 pointでのFFT/IFFTが可能
* 1 pointは32bitまたは64bit
* DMA対応


### SRAM

| Region | Access | Start Address | End Address | Size |
| :--- | :--- | :--- | :--- | :--- |
| General-purpose SRAM | CPU cached | 0x80000000 | 0x805FFFFF | 0x600000 |
| AI SRAM | CPU cached | 0x80600000 | 0x807FFFFF | 0x200000 |
| General-purpose SRAM | CPU non-cached | 0x40000000 | 0x405FFFFF | 0x600000 |
| AI SRAM | CPU non-cached | 0x40600000 | 0x407FFFFF | 0x200000 |

SRAMは、

* 6MBitをRISC-VのHost CPU側に
* 2MBitをAI processor側に (このエリアはKPUが動作時はKPUが専有)

割り当てています。

そして、同一のメモリーに対して、２つのアドレス空間にmapしている

* CPUのcacheにcoherentにアクセスする
* CPUのcacheにnon-coherentにアクセスする

なので、HostCPUとやりとりをする部分に関しては、cache coherentがよいけど、
dataを渡した後、AI processorでだけ使う場合メモリーは、cache non-coherentとして
アクセスするほうが、Host CPUのcacheが荒らされないのでよい、ということでしょう。

(できる設計者がいる会社なんですね。kendryte!)

加えて、General-purpose SRAMエリアは、MEM0とMEM1の2 bankになっているそうです。

| Region | Access | Start Address | End Address | Size |
| :--- | :--- | :--- | :--- | :--- | :--- |
| MEM0 | CPU cached | 0x80000000 | 0x803FFFFF | 0x400000 |
| MEM1 | CPU cached | 0x80400000 | 0x805FFFFF | 0x200000 |
| MEM0 | CPU non-cached | 0x40000000 | 0x403FFFFF | 0x400000 |
| MEM1 | CPU non-cached | 0x40400000 | 0x405FFFFF | 0x200000 |

で、上のエリアは、DMACにより同時にアクセスできるそうです。

ようは、SRAMもbus(おそらくクロススイッチ)につながっているのですが、
なにかのIPがアクセスしていると(burst transferしている間は)他のIPのアクセスができなくなりますので、
最大限パフォーマンスを引き出そうとする場合には、上のバンクを意識する必要があります。

Bank:MEM1の2MBitのエリアをデータの受け渡し用に使って、bank:MEM0の4MBitのエリアは
演算エリアにするなどすれば、Host CPUであるRISC-Vがそのbank:MEM0のエリアをほぼ専有することができる、
などからです。

例えば、LCDの表示エリアを、Bank1の2MBitのエリアにしておけば、他のIPによって帯域が食われるなどにより
表示が乱れることが少なくなります。(優先度付きのバスの場合、優先度の高いものがアクセスするので、表示のような優先度の高いものが優先され、画乱れを防ぐなどをSoCの設計としてよくやります。このSoCがそうなっているかどうかは不明)

### OTP (One-Time Programmable Memory)

* 128KBitもの容量があるようです!
* 64bitは、SoCのバリエーションのためのfeature flag
* 他、128bitのAES用のkeyとしても利用されます。(Encrypted firmwareが対応できるため。でも128bitなんですね)

### HW crypto engine

* AES128/192/26 (ECB/CBC, GCM)
    * Enc/Dec
    * OTP written key (HW)も、SWからでも鍵設定は可能
    * DMA対応なので、よろしく、で動作可能
* SHA256 accelerator
    * 入力データに対して、DMA可能 (結果はレジスタ読めということかと)

### DVP (Digital Video Port)

* SCCB protocol
* Up to 640x480
* YUV422, RGB565 input
* KPU(AI (NN) processor)への流し込みと、displayへのoverlay対応
    * To KPU, RGBB888 and Y成分のみ of YUV422 (輝度成分だけ流せる)
    * To display, RGB565
* カメラの入力のVSyncの始まりまたは終わりで、割り込み可能


### UART

| UART | Max baudrate | DMA | mode |
| :--- | :--- | :--- | :--- |
| UART0 | 5Mbps | No DMA (8byte TX/RX FIFO only) | Async only |
| UART1-3 | 5Mbps | DMA w/8byte TX/RX FIFO | Async and Sync |

### I2C

* i2c-0,1,2の3 channelで、個々にmaster/slaveの設定が可能
* 100KBPSまでの標準速度モード
* 400KHzまでのFast mode
* 7bit/10bit Slave Address対応
* Bulk転送モードをサポート
* 割り込みでのアクセスと、ポーリングの両方をサポート 

sensor側に割り込み通知があるとき、SW介在でよく割り込みで読み出ししますが、HWとして割り込み通知での読み出しに対応している模様 (低消費電力に有利)

### SPI (Serial Peripheral Interface)

* 4つのSPI-0,1,2,3がある。
* 1/2/4/8 wire モードを対応 (full duplex可)
* DMA対応
* DDR転送対応

| Type | Master/Slave | Clock | XIP |
| :--- | :---: | ---: | :---: |
| SPI0 | master | 25MHz | No |
| SPI1 | master | 25MHz  | No |
| SPI2 | slave | 25MHz  | No |
| SPI3 | master | 100MHz | Yes |

ようは、SPI3にSPI-NORをつなげってことです。

* SPI-NOR : 8, 16, 32MBitをサポート
* SPI-NANDは、64MBit 128MBit, 256MBitをサポート


### I2S (Inter IC Sound)

* 3chのI2S Audio Interface
* 各chは、4 stereo channelをサポートしている
* 12/16/20/24/32 bitのaudio dataをサポート
* FIFO
    * I2S-0は64bytesのTX FIFOと8 byteのRX FIFO
    * I2S-1,2は8 byteのTX/RX FIFO
* DMA転送をサポート
* 他、I2S-0は、Audio Processorとの接続をサポート

### Timer

* 3つのtimerを内蔵 (/dev/timer0-11の12個設定可能。各タイマーには４つのチャネルがある)
* 32 bit counter
* count upとcount downの両方をサポート
* 独立クロック動作
* 割り込みの極性を設定可能
* 一括あるいは独立した割り込み出力を設定可能
* 個々のタイマーが独立した形のレジスター構成
* PWM出力として利用が可能で0-100%のduty cycleで設定が可能

### PWM (Pulse Width Modulation)

* pwm0-2の3ch (FreeRTOS SDKに記載あり)

| PWM | Timer |
| :--- | :--- |
| pwm0 | timer0-3と排他 |
| pwm1 | timer4-7と排他 |
| pwm2 | timer8-11と排他 |

結局、物理的にはtimerは３つあり、これを使って、PWMを実現している。
(各物理タイマー内にクロックを共有するlogical timerが４つあるので、PWMとして利用時には４つずつ使えなくなる)

### WDT (Watch Dog Timer)

* System Reset mode
* １回目は割り込みでそれがクリアされなければsystem resetするmode
がある。
* wdt0,1の２つある

### RTC (Real Time Clock)

* 外部クロック対応
* RTCでのAlarm interruptが可能
* 精度としては１秒以下も可能だが、外部のクロックに依存
* power-on/reset後にデータがクリアされる！(えっ、、、ということで、外部にRTC必要っぽい)

### 内蔵Mask ROM

* AES-128-CBCによる暗号firmwareをサポート
* Flashの書き込みをサポート (UOP mode)
* SHA256での改ざん検出
* OTPで、UOPモード、SHA256の改ざん検出、AESによる暗号化firmwareを無効化可能
* 起動時にTURBOモードで起動可能

### 特別なpinについて

| Pin | Desc | Trigger | mode 1 | mode 2 |
| :---: | :---: | :---: | :---: | :---: |
| IO_16 | boot mode selection | During power-on reset | High to boot from FLASH | Low to enter ISP mode |

| Pin | Desc | 
| :---: | :--- |
| IO_0, IO_1, IO_2, IO_3 | JATG pin |
| IO_4, IO_6 | ISP pin (記載なしだが、MaskROMでのFlash焼き込みモードのことか?) |

### GPIO (General Purpose Input Output)

| Type | count | I/O |  | Interrupt-able | Assignable |
| :--- | :--- | :--- | :--- | :---: | :---: |
| GPIOHS | 32 | I/O(PU/PD/HiZ) | 各ピンが独立割り込み (edge/level) | Yes to 48pin of FPIOA |
| GPIO | 8 | I/O(PU/PD/HiZ) | この８つを１つの割り込みとして共有 (edge/level) | Yes to 48 pin of FPIOA |

というわけで、GPIO1-8は、wake up interruptとかに使い、基本はlevel triggerとかにしたほうが良いかも (edgeの検出statusレジスタがあるかどうかは不明)

* drive能力は、DS[3:0]で設定可能で、Typical値で、
    * Low出力時： 5.4mAのモードから、23.4mAのモードまで
    * High出力時: 7.6mAのモードから、33.7mAのモードまで

* FPIOAは、8つのpower domainからなり、各ドメインごとに、3.3Vか、1.8Vかを設定可能




### DMAC (Direct Memory Access Controller)

* 8 ch (個々にsource, destinationを設定可能、チャンネル間のarbitration対応、個々にステータスや完了割り込み可能)

scatter-gatherではなく、独立した8つのDMACのようです。

## Schematics

* 公式情報は
https://docs.m5stack.com/#/en/core/m5stickv
では、
![schematic](https://docs.m5stack.com/assets/img/product_pics/core/minicore/m5stickv/m5stickv_04.jpg)
を回路図と称しておいてありますw

| K210 pin | Func | Type | Device |
| :--- | :--- | :--- | :--- |
| G34 | GPIO34 | I/O | Ext. G34 |
| G35 | GPIO35 | I/O | Ext. G35 |

* [Reference boardの回路図](https://s3.cn-north-1.amazonaws.com.cn/dl.kendryte.com/documents/Kendryte_test_board_V0_2.pdf)