GPS Data Logger - 2nd Project
概要
ハードウェア
ソフトウェア
ソフトウェアソースコード
参考文献
変更履歴
2010年1月16日 新規作成
2010年1月17日 写真追加
2010年1月24日 コメント追加
2010年2月7日 コメント追加 ソフトウェア電圧低下検出
データロガー外観
上面には、紙のパネルを内側から |
こんなに満杯にするつもりはなかったが |
||
データロガーの組立工程
アクリルボックスは 東急ハンズにて入手 |
ウレタンのマットも 東急ハンズ |
穴あけは注意して ピンジャックは電源SW |
LCDはアクリルに入れて いるだけで固定せず |
アクリル板(黄色)で 基板をサポート |
|
黄色のアクリルは右下で スイッチの為に切欠き |
アクリル板で仕切り ケースには止めない |
eneloop単三 4個予定 |
端子に直接 ハンダ付け |
グランドプレーンは 最終的には削除 |
|
GPSとPIC24USBの 位置関係 |
電線はオヤイデで BX-S0.08sqを購入 |
Gセンサーは GPSの裏 |
下部に温度センサと シャントレギュレータ |
ほぼ配線終了 PICには32KHzのクリスタル付加 |
|
microSD Adaptorは ハンダ直付け |
全てを入れたところ |
配線が太く ほぼ満杯状態 |
スイッチ周り |
GPS→アクリル→Gセンサ |
|
USBの穴は未だ |
赤い電線が集まった 下が3.3V電源 |
USBコネクタは アクリルの穴経由で |
|||
デバック時は 左のような状態で |
|||||
Data Logger ----- 概要
<2ndの位置付け>
先のデータロガーからの主な変更点は、下記の点です。
SD Memory | ||||||||
PIC24USB | CARD | |||||||
CN2 | 13 | RD4/RP25 | CS | 1 | SD_CS | |||
CN2 | 14 | RD3/RP22 | SD0 | 2 | SD_D1 | |||
CN2 | 1 | GND | GND | 3 | Vss | |||
CN1 | 3 | +3.3V | Vdd | 4 | Vdd | |||
CN2 | 15 | RD2/RP23 | SCK | 5 | SD_SCLK | |||
CN2 | 1 | GND | GND | 6 | Vss | |||
CN2 | 12 | RD5/RP20 | SDI | 7 | SD_D0 | |||
N/A | 8 | |||||||
N/A | 9 | |||||||
CN2 | 10 | RD7 | CD | GND | ||||
CN2 | 11 | RD6 | WE | GND |
GPS | |||||||
PIC24USB | GM-318 | ||||||
CN1 | 1 | GND | 1 | GND | |||
CN1 | 3 | +3.3.V | 2 | +3.3V | |||
CN1 | 17 | RB6/RP6/AN6/RX1 | 3 | TX | |||
CN1 | 18 | RB7/RP7/AN7/TX1 | 4 | RX | |||
CN1 | 5 | RE7 | 5 | PWR_CTRL. |
気付いたこと
GPS内には、ボタン電池が内蔵されており電圧を測定したところ、0.7V以下になっていたので品番を確認するため外して見た。
品番からWeb検索したところ、下記と思われる(ボタン電池には品番全桁が書かれていないので断定できないが、サイズは一致)。
セイコーインスツル株式会社 MS621FE
カタログによれば、MS(マンガン・シリコン)リチウム二次電池で使い捨ての一次電池ではないことがわかり、再度ハンダ付けして利用再開した。その後、確かに端子電圧は上昇して、ちゃんと動作している模様です。
端子電圧が低いからと言って、決して交換しないように。
その後、GM-318のカタログをよく読むと、
Please note that the backup battery is already included in GM-318. You
saved the space, charging circuit and related materials.
とありました。充電回路を用意しなくてよいと書いてあり、二次電池搭載を意識して書かれているのでしょうが、その他のページを含め明示的には書かれていないように思えます。
明示的に書かなくてもGPSのバックアップは、二次電池か電気二重層キャパシタと業界では決まっているのでしょうか?
グランドプレーンの廃止
当初、作り始めはGPSの周りに銅板を使用したグランドプレーンを配置したが、結果は最悪で衛星捕捉が実験中には一度も成功しなかった。
理由は、不明だがGNDの取り方を含めてノイズを拾う効果しかなかったように思える。
現在、グランドプレーンなしでの衛星捕捉のスピードは今までの中で、GM-318が一番よさそうである。
Data Logger ----- ソフトウェア
先のデータロガーに対して、下記のような修正を実施。
1)GPS関連
(1)初期化と速度
測地系のディフォルト値が、GM-318はWGS-84で特にコマンドを送って初期設定せずに使える。通信速度は、4800BPSのままとした。
(2)データフォーマット
同じNMEA-0183フォーマットと言っても出力に若干の差があり、それに対応した。下記の例は、受信状態が悪く、充分な情報が衛星から得られていない時の出力の差である。
52Dは、それでもイニシャル値を返してくるが、318は何も返してこない。52Dのフォーマットから必要なデータを抜き出す際に、コンマの数だけで且つ何もないことを考慮するプログラムに修正した。
GPS-52D | $GPGGA,001406.948,3600.0000,N,13600.0000,E,0,00,99.9,00000.0,M,0000.0,M,000.0,0000*4D $GPGSA,A,1,,,,,,,,,,,,,99.9,99.9,99.9*09 $GPRMC,001406.948,V,3600.0000,N,13600.0000,E,9999.99,999.99,200909,,*28 $GPVTG,999.99,T,,M,9999.99,N,9999.99,K*59 |
|
GM-318 | $GPGGA,000125.034,,,,,0,00,,,M,0.0,M,,0000*57 $GPGSA,A,1,,,,,,,,,,,,,,,*1E $GPRMC,000125.034,V,,,,,,,291006,,,N*40 $GPVTG,,T,,M,,N,,K,N*2C |
(3)緯度経度の表示
先のデータロガーのバグ発見。
LCDへの表示が、あたかも度分秒(秒は少数点以下含む)のようになっていたが、GPSが52Dでも318でも度分(分が小数点以下含む)のデータフォーマットであり、分を秒に変える必要があったにも関わらず何もしていなかった。分の小数点以下をASCIIから数値に変換の上、60をかけて秒換算後にLCD表示のために再度ASCII変換した。但し、SDカードへのデータは生データのままで未加工とした。
(4)時間表示の高速化
先のデータロガーでは、GPSが衛星捕捉が2D以上になってからJSTを修正し、これをRTCCへ送ってファイルのタイムスタンプにしていました。初期値を2009年9月9日9時9分9秒にしたため、電源ON直後からSDカードへの記録を開始すると、ファイルのタイムスタンプがその初期データに近いものが多く生まれてしまいました。
今回は、GM-318のバックアップ電源がしっかりしているため衛星捕捉前に現時刻に近い時間を返してきます。私が購入したものは、バックアップが上手く行ってない場合には、2006年10月のタイムスタンプをGPSが返すので、2010年以降の年度を返して来た時はGPSの時刻を信ずることにしました。これで、かなり早い時間にRTCCの時間設定ができます。
但し、このバックアップの時間がどのくらい正確なのかは不明です。
また、途中で正確な数値がGPSから受信出来ても、LCD表示される時刻やタイムスタンプに使う時刻はRTCCの数値を使い、現在のソフトウェアでは再更新していませんので、この点も将来の改良点でしょう。
2)ADCデータ処理
先のデータロガーでの手抜き部分の改善。
25mS毎にADCデータを取り込み、それを4回分で平均(100mS)する処理をしていたが、
@GPSの一秒間隔に意図的な同期をさせていない点、
A25mS毎の処理は4回後に正規化などの処理速度が遅くなる部分があり、正確に25mSのDelayを置くと1秒間に10回(100mS毎処理)のSDカード出力が9回になったりしていた。
そこで、3つの対策を実施。
(1)GPS受信との同期
GPSが折角、1秒間を正確に判断してメッセージを出しているのに、ADCがそれに同期していなかったので$GPGAAパケット受信時にQueueを送って、ADCを同期させました。
本来は、パケットの最初の$に同期させるのがベストだと思いますが、割込み内の処理が煩雑化するので今回はTASK#4で判断しています。
GPSによっては、1秒ごとのパルス信号を正確に送出する機能を持っている製品があるので、その信号で同期させるのが一番正確です。
次回(いつになるかは不明)は、更に低消費電力のGPSとしてGM-316を使いたいですが、これなら1PPS信号が取り出せます(残念ながらバックアップ電源は外付けしないといけない様子)。
ソースコードとしては、緑部分が関係しています。
(2)sprintf関数の簡易版実装
FreeRTOSのパッケージ内にデモ用ソースコードがあり、そこで"printf-stdarg.c"が使われている。例えば、バージョンV.6.0.12では、
..\FreeRTOSV6.0.1\Demo\PIC32MX_MPLAB
の中に、ファイルが見つかります。sprintfに関しては、上記ファイルを使用すると改善効果が見られます(速度実測は未実施だが変更前にはsprintfでmS単位の処理時間を費やしていた模様)。
これは、下記ソースファイル内の赤字部分に有効です。
(3)vTaskDelayUnit関数の利用
今までは、vTaskDelay関数を使っていましたが、上記関数に変更しました。FreeRTOSのWebで2つの関数の違いを説明しています。
簡単に言ってしまえば、vTaskDelayは自タスクの休止時間を規定しますが、vTaskDelayUnitは先の起動時期からの時間を規定することになります。
下記の図で違いがわかると思います。タスクの処理時間に変動があっても起動周期を一定に出来ます。
下記ソースファイルで、青字が関係する部分です。
ソースファイル
/***** TASK #2 ******/ // ADC Data Control void vTask2(void *pvParameters) { portTickType xLastCheckTime; portTickType xDelayTime; static char Buf[8]; int i; mADC_MODULE_ON(); EnableADC1; #if defined(GSEN_I2C) i2c1_Gsensor_initialize(); // Use MMA7455L Three axis G-sensor #endif /* GSEN_I2C */ vTaskDelay( 500 / portTICK_RATE_MS );// Wait 0.5sec EnableIntADC1; mADC_ISR_ENB(); xDelayTime = 25 / portTICK_RATE_MS; xLastCheckTime = xTaskGetTickCount(); // Need to initialise time prior to the first call to vTaskDelayUntil() while(1){ xQueueReceive(adctrgrQueue, Buf, portMAX_DELAY); for ( i = 0; i < 10; i++ ){ mADC_START(); // Start Convertion vTaskDelayUntil( &xLastCheckTime, xDelayTime ); adc_save( i * 4 + 0 ); // see adc_func.c mADC_START(); // Start Convertion vTaskDelayUntil( &xLastCheckTime, xDelayTime ); adc_save( i * 4 + 1 ); // see adc_func.c mADC_START(); // Start Convertion vTaskDelayUntil( &xLastCheckTime, xDelayTime ); adc_save( i * 4 + 2 );; // see adc_func.c mADC_START(); // Start Convertion vTaskDelayUntil( &xLastCheckTime, xDelayTime ); adc_save( i * 4 + 3 ); adc_data_processing( i * 4); // see adc_func.c adc_g_sensor_processing(); sprintf( MsgBuf_ADC, "$ADC, %4d, %4d, %4d,%4d, %4d, %4d,*00\r\n", adc_DG_X, adc_DG_Y, adc_DG_Z, lng_adc_TEMP_old, lng_adc_VBAT_old, lng_adc_REF_old); msg_count_ADC = strlen(MsgBuf_ADC); if (File_state == SD_FILE_WR){ xQueueSendToBack(sdcardQueue, "ADC", portMAX_DELAY); } } long_ave_batt(); adc_to_physical_value(); } } |
3)電圧低下検出とファイル操作
使用中に下記のような電源電圧低下をログ出来ました(クリックで拡大可)。
今まで、電源低下でシステムが停止した際のファイル喪失防止に、一時間毎にファイル更新をすることで対応していました。しかし、上記データが取れたことで、下記の動作を追加することにしました。
@電源電圧低下の時間推移がある閾値に達した際に、1時間毎の更新でなくその時点でファイルをクローズする。
A設定電圧以下になった場合には、2分毎にファイルのクローズ/オープンを繰り返し、システム停止までなるべく多くのデータ記録を実施する。
この機能は、下記のようにタスクに実装しました(上記説明文の色と下記ソースファイルの色が対応しています)。
TASK1は1秒ごとに起動され、他にGPSからの時刻情報に基づきRTCC(Real-Time Clock & Calender)に時刻設定します(一回限り)。
実際の判定値は、下記のように設定しています。
20秒間の電圧変化が0.15Vを越えた場合には、その時点で一度ファイルをクローズして、再度ファイルをオープンする(delta_batt >= QUICK_DROP)。
また、電源電圧が2.3V以下に低下した後は、2分毎のファイルのクローズ/オープンを繰り返す(ad_batt <= BAT_END)。
/***** TASK
#1 ******/ |
Data Logger ----- ソフトウェアソースコード
ソースファイル一式を用意出来ます。
必要な方はお手数ですが、メールにてお知らせください。
kenjia の後に@sannet.ne.jp
です。
下記をベースとしています。
FreeRTOS V.6.0.1
Microchip MDD File System, USB v2009-11-18
Data Logger ----- 参考文献
GPS-GM318関連
aitendo
http://www.aitendo.co.jp/
http://www.aitendo.co.jp/product/1007