● 実験テーマ96

「PIC32MX370Fファミリの試用実験」
(PIC32MXの最新シリーズ:370Fファミリを試用実験してみました。Lチカから始まり、今回の最終目標は、6CHロジアナの高速化ですが・・)

※ 
2017.910.12
→ 1回目の更新です。
   6CHロジアナ実験 ソフトを更新し、_V3としました。

   10月4日からの記事を参照してください。


以下、この実験の顛末記です。

■ 2017.9.9
  ・PIC32MXの新ファミリが出たようです。
   秋月で、「PIC32MX370F512H」のDIP変換基板実装済版が、販売(8月17日より販売開始)されています。
   従来使っていた、340Fファミリは、Fcy= 80MHz(max)でしたが、今回のは、Fcy= 100MHz(max)と、
   さらに高速です。他にアナログチャンネルが大幅に増えているのも特徴のようです。
   未だ出始めのPICなので、HPにこのPICに関連した記事は少ないですが、PIC32MXを使用したGAME機を
   紹介されている、「ケンケンのホームページ」の掲示板に、このPICの、T2割込みによる、Lチカのサンプル・
   プログラムが掲載されていました。


■ 2017.9.10
  ・調べたら従来自作で使っていた、QFP64の、PIC32MX340F256Hと、ポート番号及び、電源・リセットピンの並びが
   一緒(ピンコンパチ)のようです。
   自作PIC32MXトレーニング基板が、PIC差替えでそのまま使えそうな感じです。
   この
QFP64パッケージのDIP変換基板がなかなか抜けなくて、今迄諦めていたが、ドライバのシャフト側のヘッドが
   大き目(広め)で小型のドライバで、4隅をこじったら何とか抜けたではないか。


■ 2017.9.11
  ・秋月の「PIC32MX370F512HのDIP変換基板実装済版」の注文を済ませる。
  ・コンパイラは、XC32 v1.4.2が良さそうだが、GAME機の時、インストールしたのは、XC32 v1.32
   ケンケンのHP情報によると、このPICは、XC32 v1.32以下に対応するようである。
   但し、v1.33から仕様変更になり、plib.hを使用すると、ワーニングが出るそうです。

  ・まず手始めに、ケンケンのHPに記載されている、Lチカのサンプル・プログラムを動かしてみる。
   XC32 v1.32でビルド〜HEX準備〜秋月からPICが届いたら、従来のトレーニング基板のPICと
   差替えて動作確認してみる。


■ 2017.9.13
  ・HEXまで用意出来たところで、いざトレーニング基板に、370Fモジュールを差し込もうとしたら、ソケットコネクタと
   合わない。
   何と、前の、34OFモジュールは、DISEN製の変換基板で、今回の秋月のものより、若干サイズが大きかったのである。
   なんと、おばかなことに今頃気が付いた。

  ・このトレーニング基板で進めるのは諦めた。
   気を取り直して簡単な、370Fモジュールの実験基板を、ユニバーサルで作ることにした。
   回路は、以前の、簡易6CHロジアナの入力バッファなしの回路にしておく。
   最初は、Lチカを内蔵RC OSC=8MHzと、DIV+PLLによって、Fcy= 96MHzで動かす。


■ 2017.9.17
  ・実験基板の実装が済んだ。


■ 2017.9.18
  ・3点ほど配線ミス(電源・reset)があったが修正して、LEDチカのHEXを書込み、1秒毎のブリンクOKを確認。
   次に、外部X'tal= 8MHzの設定にして、同じことを確認し、これもOKになる。
   やはりこちらのが時間精度が良い。


   ソフトの注意点としては、アナログピンが26CHと大幅拡張されているので、R**との共用ピンのデジタル/アナログ
   ピン設定が、それぞれのレジスタで全て必要なピンをデジタルピンにする必要がある点である。
   (AN**と共用でない単純ポートピンも幾つかある。ここは気にしなくて良い。)


■ 2017.9.19〜 2017.9.20
  ・簡単な、I/O_TESTで、内部プルアップ設定の方法を確認した。(レジスタ名が変わっているだけで殆ど同じでOK)
   次に、QVGA_TEST(カラー液晶表示テスト)を試した。
   ポイントは、液晶タイミングに入れている時間調整の、遅延時間位だと思う。
   特に、Glcd_out関数で入れている、NOPの数調整である。現在(Fcy=80MHz)は、1個だが・・まずはそのままで・・
   HEXを書込んで、QVGA_TEST実行→ 問題無く動いているようである。(Fcy=96MHz)
   見た目、Fcy=80MHzの時より速く、小気味良く動いている感じ。

   ただ、ビルド作業の、make段階で、peripheralディレクトリ下のファイルに関してのワーニングが多数発生した。(XC32 v1.32使用)
   しかし、ビルドには成功している。
   この問題は、以下の修正でOKになる。
    @ メインの#include <plib.h>をコメントアウト。
    A QVGAライブラリファイル(*.cと、*.hの両方)の頭に、#include <xc.h>を追加


■ 2017.9.21
  ・次に、6CHロジアナの実験に進もうと、1uS以下のお試しサンプリング周期(T2周期)= 0.4u, 0.2uを
   作り出そうと、PR2値を検討していた時、変なことに気付く。
   ケンケンさんの、サンプルソースの、PR2値の設定であるが、カウント数:N= 37500になっている。
   カウンタは、0からカウントするので、PR2= N-1= 37499 が正解。
   つまり、タイマ周期:Tout= (1/Fcy) x PS x PR2 (但しPS=プリスケール値)で計算される。
   修正後、再度データを取直してみた。
   
内部RC OSC= 8MHzの場合→ (1/0.5025)/2= 0.9950秒→  前より若干良くなる。 
   外部X'tal OSC= 8MHzの場合→ (1/0.5002)/2= 0.9996秒→ 前と同じ。
     と殆ど変わらなかった。この辺は、桁数の多いカウンタで計測しないと違いが判別できない範疇と思う。  

  ・6CHロジアナの実験に戻る。
   Fcy= 96MHzでは適当な時間軸レンジに対応するPR2値(なるべく割切れた数にしたい)が得られない
   ので、Fcy= 100MHzに変更してみる。
   外部X'tal OSCを、10MHzに交換し、再度Lチカを試してみた。

  結果は、(1/0.4998)/2= 1.0004秒 でgood。
  Lチカ時の、5V入力消費電流は、60mAほど。


■ 2017.9.22
  ・SW(HOLD, READY, SLOPE)リードに、CN割込みを使うので、その設定方法と、CN割込み関数の書式
   をデータ・シートのレジスタ表を眺めながら調べる。
   PIC32MX340Fと比較し割込み関数のレジスタの扱い方に、若干の差異があり、とまどった。
   割り込み関数の各パラメータにマクロを使っているが、その意味を十分理解できてない。
   しかしそこは長年の勘?で記述し、一応基本的にはCN割込みを含め動いている。

  ・T2割込みの方だが、期待していた処理時間だが、従来の1uSminサンプルでの描画はOK
   だが、試しで増設した、0.4uS(20uS/D), 0.2uS/D(10uS/D)はNG。
   どちらも、100kHz入力で、周期5uの描画になってしまう。(20uS/Dに於いて、4山描画)


■ 2017.9.23
  ・クロック比= 100M/80M= 1.25だけ良くなるとしたら、1u/1.25= 0.8uSサンプル=40u/Dまで行くと考えたが、
   やってみたら、100kHz入力で1目盛で3山半の描画(4山が正しい)になってしまいNG。
   今迄のソフトのままだと、1uSサンプルが限界は変わらずが残念。描画は早くなったが・・

  ・T2割込み内での処理時間を極力少なくする方法を試してみる。
   現在、6CH分のデータ・バッファリング時、0x3Fのマスク処理(上位2bitマスク)も含めている。
   割込み処理の中では、生データのみ取得することにして、512データ格納後、T2 OFFし、格納データに対し
   あらためてメインで、生データにマスク処理をして格納し直すことにした。
   これによって、0.8uSサンプル(40uS/D)までレンジ拡大出来た。
   200kHz入力で、0.8uSサンプル後、MAGで、x2にして見ると、20uS/D相当で、1目盛4山(5u周期)と
   見易くはなった。


■ 2017.9.24
  ・T2割込みによるバッファリングでは限界そうなので、DMAを使えないかと考え始めていた。
   そんな中、昨日の
6CHロジアナの実験でのソースを、ふと眺めていたら、QVGAライブラリの定義ファイルの
   頭の、Fosc定義を、80→ 100に変えてなかった事に気が付く。
   そこで改めて遅延関数を眺めていたら、今更だが、PIC32MXの遅延関数に疑問を感じた。
   この遅延関数は、1命令実行速度を、複数回実行することによって実現している。
   元々QVGA液晶の、PIC32MX用ライブラリは、後閑さんは公開しておらず、RTOSを使った、MP3 PLAYERで
   使っているノキアの携帯用カラー液晶用のライブラリで、Foscに連動した、PIC32MX用の遅延関数を
   公開している。
   私はこれを借用している。

/**********************************
* ループ遅延関数 usec単位
**********************************/
void delay_us(unsigned short usec)
{
   unsigned short i, Max;

   Max = usec * 640/Fosc;
   for(i=0; i<Max; i++)
   {     }
}

   この式をよく見ると、Foscが高くなるほど(Toscが小さくなるほど)Max値は小さくなる。
   つまり、1単位の遅延タイムのループ数が少なくなる。
   逆に、Foscが低くなるほど(Toscが大さくなるほど)Max値は大きくなり1単位の遅延タイムのループ数が多くなる。
   これは逆でないと、おかしい??
   ここらの実機(実測)検証は一度もやったことがない。


■ 2017.9.25
  ・
いい機会なので実機(実測)検証をしてみた。
  <遅延関数精度検証結果 For PIC32MX>

   @ 現状の関数(↑)を使用しても、今迄の、Fosc= 80MHzで使う分には問題ない精度であることを確認した。
     (※ Foscを可変して使った場合は、ループmax値と、Foscの増減関係が反転している式に

        なっているので、あくまで
Fosc= 80MHz固定限定で使うこと。)

   A 後閑さんが、その後、更新した関数使用の場合(これに当初は気が付かなかった。)
        式は異なっているが、
Foscを分母から分子へ置換えることによって、ループmax値と、Foscの増減関係
         の整合を取って、
Fosc= 80MHzの時に、上式結果の、Max= usec * 8となるように割り数を、10に調整している
         だけなので、@と全く同じ結果となり仕様上問題なし。

      ※ Foscが高くなるほど、精度は落ちるようだ。

        この式自体、Fosc= 80MHzの時を照準に合わせて割り数を調整したもと思われる。

        Fosc= 96MHz(内蔵RC OSC=8MHz)時の方が、Fosc= 100MHz(外部X'tal OSC=10MHz)時の方より精度が良い。

        しかし、このループによる遅延時間生成は、元々アバウトなものなので、この誤差は十分許容範囲と考える。

 

/////////////////////////////////////////////////

//  ループ遅延関数 usec単位

/////////////////////////////////////////////////

void delay_us(unsigned int usec)

{

  unsigned int i, Max;

 

  Max = usec * Fosc/10;

  for(i=0; i<Max; i++)

  {  }

}


■ 2017.9.26
  ・QVGA_TEST_2として、Fosc= 100MHzで動かしてみる。
   ついでに、us単位delay関数を上記のものに修正し、ライブラリ名も、colorlibPIC32MXVH.c及びcolorlibPIC32MXVH.h
   とリネームした。→ 問題なく動いた。

  ・Easy_6ch_LogAna_V2_testに戻る。
   Fosc= 100に変えてなかったので、変えてライブラリを上記のものに置換えてテストしたが、結果は同じだった。
   0.8uサンプル(40uS/D)止まりは変わらず。
   描画スピードも見た目はそんなに大差なし。
   変化を感じられるのは、全画面クリアの時間や、拡大表示の時、x10から元の等倍表示へ戻る時の時間が、約1秒ほど
   速くなった位。
   0.8uサンプル(40uS/D)では、等倍表示で視覚的に周期が確認し易いと感じる入力周波数の限界は、125kHz(8.0u)
   であった。


■ 2017.9.27〜 2017.9.29
  ・DMAによる方法を模索していたが、

   自分なりの結論として、PORTから、Bfferへの、T2トリガによる、ハード的なDMA転送は、不可能なことが判った。
   DMAのトリガ要因として、T2は可能なのだが、タイマーモジュールには、入力バッファは含まれない
   ので、転送元として、PORTを指定しても無駄。
   つまり、基本的には、転送元に予めデータが用意されてないと、定周期のDMA転送は不可と考えられる。

   <これまでのデバッグ状況整理>
    ・plib.hを使わない、DMAレジスタ直接設定にチャレンジしたが、どうも上手く行かず。
     データシートの英文が難解なことも要因。
    ・そこで、ワーニングは多発するが、ビルドは通るので、plib.hを使ったマクロ記述でdma設定を試みた。
     しかしDMAがまともに動かない。
     その中でも、何点か気付いたことあり。
      @ 今回はハードウエアDMA割込みなので、T2割込み設定は不要。(PR/PS設定は必要)
         なので、T2 IFフラグの操作も不要。

         転送終了チェックは、IFフラグでは駄目。
         DMAレジスタのステータスビット(DCH0INTbits.CHCCIF:セル転送終了ビット)でチェック。
      A @でやっても、DMA割込みは起動して転送終了後、そのチェック処理後に、RUNしてくるが
         波形は何一つ表示せず。

      B Aのことは何が原因か?
         よくよく考えると、転送元のアドレスを、(void*)&PORTとしているが、これでは入力ポートの
         仮想アドレス(これも意味不明だが?)を渡しているだけでデータの実態はない。
         ここは、既にバッファリング終了したデータが存在するメモリ(変数)の必要がある。
         (後閑さんの2つのDMAサンプルは、いずれも転送元が固定配列のデータであった。)

  ・結局、今回のソフトは、2017.9.26版を整理して、最終のテスト版とすることにした。


---<ここから、追試:「実験ソフト更新:V3」の記事>-------------------------------------

■ 2017.10.4
  ・6CHロジアナの追試をしてみる。
   以前からやりたかったのだが、敷居が高そうで躊躇していた、
   ロング・メモリにして、取得バッファ・データの内容をシフト(スクロール)表示させる実験をしてみる。
   5000レコード程度にしようと思い、現状のバッファ・サイズ、512byteから、5120byteにした。(後日、+1にして5121byteにしないと駄目なことに気付く。)
   5120byte取得後、左右シフトキーで、スクロール表示出来る様にしてみたい。

   次のように考えれば、そんなに難しくはなさそうだが・・・
    @ HOLD及び、シングル・トリガ・モード時の、READY SW ON待ちの間に、この処理を入れる。
    A キーを押す毎に、読み出すバッファ位置を、1つずらし、波形と座標線をリフレッシュするようにする。

   そうは言っても、頭の中で、横スクロールを理解するのは、そんなに簡単なことではないような気もするが。
   そこで、最初は、シフト表示のリミット点についてはあまり考えないで、とにかくソースを書いて
   ベースとなる動作を実験で確認してみることから始めようと思う。
   また、現在表示しているバッファ位置も表示してみたいが、これもとりあえずは無しで進める。

   左右シフトキーは追加しないといけないが、手持ちが未だ5個ほどある。


■ 2017.10.5
  ・ノーマル・トリガ・モード時にのみシフト表示機能を盛り込んでみた。
   コンパイルは通った。
   左右シフトキーの追加も済ます。

  ・動作確認だが、
頭の中で整理されてないまま進んでいるので、上手く行ってない。
   現在の方法は、シフト(スクロール)表示でなく、1画面単位のページング表示。
   (常に、SWを押す度にバッファ読出し位置を、1つずらして、そこから新たに1画面分表示するイージーな方法)
   これだと、常に右側がそのページの最新データになる。
   一応、キーセンスと連続送りもそれなりに動いてはいるが、ページングでは、動きが不自然。
   明日は、メモ用紙に、スクロールの動きを具体例で書きながら、頭の中を整理しスクロールにチャレンジしてみたい。


■ 2017.10.6
  ・
右スクロールはリミットも含め上手く行く。
   ただ、左スクロールは、リミットを決めるのが難しく未だ解決してない。
   リミット以外は上手く行った。

   <スクロール表示機能の整理:私なりに理解したこと>
    @ 右スクロール
     ・oldデータを押出して表示するイメージ
     ・バッファ開始位置(表示開始位置)を、1つ戻す。
     ・画面上のスクロールの動きと、バッファ・ポインタの動きは逆になる点に注意
     ・主にトリガ点以前のデータを表示する時、使う。(最大128バイト)もちろん途中の戻しの時も使用。

    A 左スクロール
     ・newデータを押戻して表示するイメージ
     ・バッファ開始位置(表示開始位置)を、1つ進める。
     ・画面上のスクロールの動きと、バッファ・ポインタの動きは逆になる点に注意
     ・トリガ点以降のデータを表示する時、使う。(最大5120バイト)

  ・スクロール時の、バッファ開始ポイント:BPの値を液晶に表示する機能を追加した。
   右スクロールの場合は、HOLD状態から最初にスクロールボタンを押すと、トリガ位置-1の値を示す。
   さらに押して行くと、ディクリメントして行き、BP=0000でリミットになり、表示が
   変化しなくなる。(リミットが掛かる。)→ これはOK
   左スクロールの場合は、HOLD状態から最初にスクロールボタンを押すと、トリガ位置+1の値を示す。
   さらに押して行くと、インクリメントして行き、BP=4801でリミットになり、表示が
   変化しなくなるはずだが、このリミット点を仮にこの値(5120-320=4800)+1にしているが
   ゴミを表示してしまい上手く行ってない。


■ 2017.10.7
  ・
右・左スクロール共にリミットも含め上手く行く。
   左スクロールの、リミットを決めるのは難しいと思っていたが、考えすぎ。
   トリガ点は固定でない為、最後の320バイト分のデータ表示域がバッファサイズ
   をオーバーしてゴミが表示されてしまうと考えていたのだが、
   冷静に考え直すとトリガ点が変動しても、1dot単位でシフトするので、
   max=5119が最後のバッファ読出し点に変わりはない。
   これに対応する開始点は、-319して、4800になるので、これを上限にすればよい。
   写真では、2〜6chの最後にエッジが描画されているが、これは1ch以外完全オープン
   になっているせいでレベル不定のためと思われる。(本番はicバッファ+プルダウンで解放時
   もレベルがlowに確定されるので問題は出ないと考える。)
   ↑-これは一理あるが、後日別理由であることが判明した。

  ・また、右スクロールのリミット点判断の式も誤っていた。
   左リミットにしておいて、そこから右スクロールすると、bp=4800から4799にシフト
   するはずだが、0000になってしまってた。
   以下の修正でokになる。(コメントアウトのところ)
   ↓
/// 右スクロールSW読込み(1dot毎のスクロール)
if(!R_SFT_SW) {
   --BufferStart; // バッファ読出し位置を1つ戻す(OLDデータを押し出す)

   // if(BufferStart < 320) LogAnaSft(); // シフト時のロジアナ表示
   if(BufferStart >= 0) LogAnaSft(); // シフト時のロジアナ表示
   else {
      BufferStart = 0; // 下限リミット
   }
   itostring(4, BufferStart, MsgBP+3);
   Glcd_Str(0, 16, MsgBP, CYAN, BLACK);}


■ 2017.10.8
  ・
P=4800(ロケーションの関係で、BPから変更)時のゴミ表示の原因が解明した。
   今迄は、1画面分しか表示していなかった。
   トリガ点max=127でトリガ検知して、そこから1画面(320dot)表示すると
   最終バッファ位置は、127+319= 446になる。
   そしてロジックレベル判断は、[446]と[447]のレベル比較で行われる。
   つまり、1画面分だけの表示の場合は、最低でもBuffer[448]必要。
   Buffer[512]と多めに取っているので問題なかった。

   今回は、シフトによって最終バッファ位置が、[5119]になり、これと比較してロジック
   状態を判別するため、[5120]までは必要になる。
   つまり最低でも、Buffer[5121]必要。この修正でOKになる。
   現在は、Buffer[5120]としているので、最後のデータ比較が上手く行かずゴミが出る。


■ 2017.10.9
  ・シングル・トリガ・モードにも適応してみた。よさそうである。

  ・MAG(拡大)とシフト表示を連動させてみる。
   今迄、MAG時のバッファ位置として使っていた、x_temp変数を、そのままシフト表示モードでも使うだけで、たぶんいける。
   今は、MAG→ x_temp, シフト表示→ BufferStartと分けている。
   x_tempの意味を最初のトリガ点とし、これは動かしたくないという思いが強かったせい。
   この修正で変数が減り、プログラムはすっきりする。

  <結果>
   ・MAGが効いたまま(拡大状態)シフト表示は出来ないが、MAGが等倍X1の時からのシフト表示は出来る。
    また、シフト表示した状態のまま、MAGもOK

  ・ここまでの171009-2版のソースを整理(コメントアウト部削除)し新たなHEXで以前作った、PIC24+ノキア液晶温度計の、
   5線式SPI(液晶I/F)のタイミングを観測してみた。

  <結果>
   ・プローブ5本をセット。
    1CH:RST/, 2CH:SCE/, 3CH:SCLK, 4CH:SDIN
    1CHの立上りトリガ
    RESET SW ONからのタイミングを、シングル・トリガで確認(今回は5121レコード)

    右シフトで、P=0000にしてから、左シフトで、Pを増やしていく、P=4800でリミットになるはずが、何故か、P=128で止まってしまう?
    またここからの、右シフトも出来なくなる?


■ 2017.10.10
  ・昨日の右シフトで、P=0000にしてから、左シフトで、Pを増やしていく、P=4800でリミットになるはずが、
   何故か、P=128で止まってしまう。
   またここからの、右シフトも出来なくなる件、調査解決する。

  <原因>
   シングルトリガ関数では、x_temp < 128の条件でトリガ検知と判断した時のみ拡大とシフト表示を許可している。
   しかし、今回の修正で、x_tempをシングルトリガ時と拡大・シフト表示共通のバッファ開始位置として共用するよう
   に修正した。
   シフト表示の時、x_tempがインクリメントして行くが、x_temp= 128になると、
   拡大・シフト表示機能をパスする為、128で止まっていた。

  <対策>
   シングル時のトリガ検知フラグを、x_tempでなく別のフラグ:TrgDetに修正し、これで判断することにした。
   これで上手く行く。


■ 2017.10.11
  ・これで、HP公開用の写真取りをして公開することにした。
   このページ冒頭の写真とコメントを参照してください。

  ・このバージョンアップを、実験テーマ56で作った、PIC32MX340Fファミリ(Fcy=80MHz)の、6CHロジアナにも
   適応できるかも試してみたいと思っている。
   こちらは、2.8インチ液晶なので視覚性は向上している。


<回路図>
 ・こちらから、どうぞ→
 「PIC32MX370F汎用実験基板」 (PIC32MX370Fでの、6CHロジアナの実験が前提)
                                 ※ 171012: シフトSWを2個追加しました。

<最終ソース及びヘッダファイル>
 ・こちらから、どうぞ→   @ Lチカ・プロジェクト
                    LED_BLINK_2.c (100MHz版)

                  A QVGA液晶表示テスト・プロジェクト
                    QVGA_TEST_2.c (100MHz版)

                    /// QVGAライブラリ→ B 6CHロジアナ実験プロジェクトでも必要です。
                    colorlcd_libPIC32MXVH.c
                    
colorlcd_libPIC32MXVH.h

                    /// アスキーフォント→ B 6CHロジアナ実験プロジェクトでも必要です。
                    
ASCII12dot.h

                    /// イメージデータ
                    imagedata.h

                  B 6CHロジアナ実験プロジェクト
                    Easy_6CH_LogAna_V2_test.c
                    Easy_6CH_LogAna_V3_test.c ※ 171012: ロングメモリ+シフト(スクロール)表示機能を追加


← 実験テーマ1に戻る   TOP PAGEに戻る   実験テーマ97へ →