Hi-Speed Serial TX Library for Seeeduino XIAO (ATSAMD21)

Seeeduino XIAO (ATSAMD21) の限界を試すべく、下記投稿のライブラリをポーティングし送信速度がどこまで出せるか試してみた。

Hi-Speed Serial TX Library for AVR Series

ちなみに、Seeeduino XIAO (ATSAMD21) のSERCOM-USARTでは送受信とも最大3Mbpsである。

ライブラリの最高速度は12Mbps16Mbpsだが、さすがに、16MbpsだとGPIOが追い付かなくて無理っぽい感じ...8Mbpsならなんとか行けそうな気もするが、Output Driver Strength = 1 は必須かも。

【16Mbps (Output Driver Strength = 0)】

【16Mbps (Output Driver Strength = 1)】

【8Mbps (Output Driver Strength = 0)】

【8Mbps (Output Driver Strength = 1)】

【4Mbps (Output Driver Strength = 0)】

【4Mbps (Output Driver Strength = 1)】

【サンプル・スケッチ】

【修正履歴】
2020-04-25
オシロで詳しく調べてみたらSingle-Cycle I/O の実行クロック数がヘンだ。連続でHIGH/LOWを繰り返すと確かに1サイクルなのだが、繰り返さない場合は+1サイクル余計にかかってしまう。つまり、普通に使う限り2サイクルかかるということだ。AHB-APB BridgeのWait stateが入るのかな...もしかしてだけど。ということで、ビット当たり3から4クロックへ変更しそれに合わせて通信速度定義を修正。delay cycle数も確認してみたが問題なさそう。でも、まだ計算通りのクロックにならないのはなぜだろう?詳しく観察してみると数サイクル毎に±1サイクル微調整されてるもよう。そもそも armというのは複雑なパイプラインを駆使するPC向けアーキテクチャーのものなので、それをダウングレードして組み込み用にも使えるよって歌い文句にしただけの製品だから命令の実行サイクル数など計算しても意味がないよということらしい...知らなかった。orz

2020-04-24
1Mbps超えでエラーになるのはクロックのズレが原因だった。オシロで見るかぎり命令の実行サイクル数がドキュメント通りでなく計算値とかなりかけ離れているようだ。だが、なぜかはわからないがどうやっても調整することができない。仕方ないのでよく使う通信速度をオシロで時間合わせした速度定義を追加しておいた。通信速度を直接指定せずHSTSerial_115200からHSTSerial_12Mまでの通信速度定義を利用するとうまくいくはずだ。
計算上では16Mbpsのはずが最高でも12Mbpsまでしか出なかったがFT232Hを受信相手に最大12Mbpsで送信できることを確認した。但し、12Mbpsでは連続送信で時々データ化けが発生。8Mbps程度が限界かも...

2020-04-23
1Mbpsを超える速度では受信エラーになることが発覚。ATtiny85でも8Mbpsで送信できたのに...相性の問題か、或いは、送信タイミングが微妙にズレてるのかも。調査が必要だ。

【ライブラリ】
ライブラリは、Cortex-M0+の命令実行サイクルとSingle-Cycle I/O Portに依存してるためCortex-M0を含む他のデバイスでは動作しないことに注意しよう。このライブラリはビットあたり3サイクルかかっているが、AVRのビット・テスト・スキップ命令、或いは、shiftとandの合成命令があれば2サイクルで実行できる。特にAND/OR/XORなどの論理演算と他の命令の組み合わせは頻繁に使われてるはずなのであったらいいなって感じの命令だ。CPUアーキテクチャー云々よりも使いやすいのが一番だと思うが。

ちなみに、Single-Cycle I/O PortのサポートがないCortex-M0に対応したところで限界値はかなり低いと思われるため対応する価値はないかな。たぶん...

【参照ライブラリ】
Seeeduino XIAO (ATSAMD21G18) のGPIO速度