MPUとHMCでうごくかもver
Dependencies: ConfigFile SDFileSystem mbed
Fork of LAURUS_program by
Diff: main.cpp
- Revision:
- 19:ad8ff2de68f5
- Parent:
- 18:9dd72e417c60
- Parent:
- 17:03b45055ca05
- Child:
- 20:00afba164688
diff -r 9dd72e417c60 -r ad8ff2de68f5 main.cpp --- a/main.cpp Mon Jun 22 15:16:00 2015 +0000 +++ b/main.cpp Mon Jun 22 15:23:37 2015 +0000 @@ -46,6 +46,7 @@ Serial pc(SERIAL_TX, SERIAL_RX); // PC通信用シリアルポート GMS6_CR6 gms(&gps, &pc); // GPS SDFileSystem sd(PB_5, PB_4, PB_3, PB_10, "sd"); // microSD +FILE * fp; // ログファイルのポインタ BufferedSerial xbee(PA_9, PA_10, PC_1); // Xbee ConfigFile cfg; // ConfigFile PwmOut servoL(PB_6), servoR(PC_7); // サーボ用PWM出力 @@ -58,10 +59,12 @@ int lps_cnt = 0; // 気圧センサ読み取りカウント uint8_t INT_flag = TRUE; // 割り込み可否フラグ +/* こちらの変数群はメインループでは参照しない */ Vector raw_acc(3); // 加速度(m/s^2) 生 Vector raw_gyro(3); // 角速度(deg/s) 生 Vector raw_geomag(3); // 地磁気(?) 生 float raw_press; // 気圧(hPa) 生 +/* メインループ内ではこちらを参照する */ Vector acc(3); // 加速度(m/s^2) Vector gyro(3); // 角速度(deg/s) Vector geomag(3); // 地磁気(?) @@ -133,9 +136,11 @@ /****************************** private functions ******************************/ +void SD_Init(); // SDカード初期化 +void VectorsInit(); // 各種ベクトルの初期化 +void KalmanInit(); // カルマンフィルタ初期化 void LoadConfig(); // config読み取り int Find_last(); // SDカード初期化用関数 -void KalmanInit(); // カルマンフィルタ初期化 void KalmanUpdate(); // カルマンフィルタ更新 float Distance(Vector p1, Vector p2); // 緯度・経度の差から2点間の距離を算出(m) bool thrown(); // 投下されたかどうかを判断する @@ -161,44 +166,20 @@ //Config読み取り LoadConfig(); - //SDカード初期化 - FILE *fp; - char filename[15]; - int n = Find_last(); - if(n < 0) { - pc.printf("Could not read a SD Card.\n"); - return 0; - } - sprintf(filename, "/sd/log%03d.csv", n+1); - fp = fopen(filename, "w"); - fprintf(fp, "log data\r\n"); - xbee.printf("log data\r\n"); - - servoL.period(0.020f); // サーボの信号の周期は20ms - servoR.period(0.020f); + // SDカード初期化 + SD_Init(); //カルマンフィルタ初期化 KalmanInit(); + // 各種ベクトルの初期化 + VectorsInit(); + INT_timer.attach(&INT_func, dt); // 割り込み有効化(Freq = 0.01fなので、10msおきの割り込み) - - //重力ベクトルの初期化 - raw_g.SetComp(1, 0.0f); - raw_g.SetComp(2, 0.0f); - raw_g.SetComp(3, 1.0f); + + servoL.period(0.020f); // サーボの信号の周期は20ms + servoR.period(0.020f); - // 機体に固定されたベクトルの初期化 - b_f.SetComp(1, 0.0f); - b_f.SetComp(2, 0.0f); - b_f.SetComp(3, -1.0f); - b_u.SetComp(1, 1.0f); - b_u.SetComp(2, 0.0f); - b_u.SetComp(3, 0.0f); - b_l = Cross(b_u, b_f); - - // 目標座標をベクトルに代入 - target_p.SetComp(1, target_x * DEG_TO_RAD); - target_p.SetComp(2, target_y * DEG_TO_RAD); /* ------------------------------ ↓↓↓ ここからメインループ ↓↓↓ ------------------------------ */ while(1) { @@ -214,8 +195,6 @@ gms.read(); // GPSデータ取得 UTC_t = (int)gms.time; - - // 参照座標系の基底を求める r_u = g; r_f = geomag.GetPerpCompTo(g).Normalize(); @@ -242,8 +221,6 @@ if(yaw < -180.0f) yaw += 360.0f; // ヨー角を[-π, π]に補正 if(yaw > 180.0f) yaw -= 360.0f; // ヨー角を[-π, π]に補正 - - if(UTC_t - pre_UTC_t >= 1) { // GPSデータが更新されていたら p.SetComp(1, gms.longitude * DEG_TO_RAD); p.SetComp(2, gms.latitude * DEG_TO_RAD); @@ -259,20 +236,14 @@ float lv = (float)logicVcc.read_u16() * ADC_LSB_TO_V * 2.0f; // ロジック電源電圧 // データをmicroSDに保存し、XBeeでPCへ送信する - sprintf(data, "%d, %.1f,%.1f,%.1f, %.3f,%.5f,%.5f", + sprintf(data, "%d, %.1f,%.1f,%.1f, %.3f,%.5f,%.5f, %.3f,%.3f,%.3f, %.3f,%d\r\n", UTC_t, yaw, pitch, roll, - press, gms.longitude, gms.latitude); + press, gms.longitude, gms.latitude, + sv, lv, vrt_acc, + Distance(target_p, p), optSensor.read_u16()); fprintf(fp, data); fflush(fp); - xbee.printf(data); - - sprintf(data, ", %.3f,%.3f,%.3f, %.3f,%d\r\n", - sv, lv, vrt_acc, - Distance(target_p, p), optSensor.read_u16()); - - fprintf(fp, data); - fflush(fp); - xbee.printf(data); + xbee.printf(data); INT_flag = TRUE; // 割り込み許可 } @@ -359,7 +330,7 @@ } } - + #ifdef RULE2 // 目標地点との距離が閾値以下だった場合、落下シーケンスへと移行する if(Distance(target_p, p) < BorderDistance) step = 2; @@ -370,7 +341,7 @@ #ifdef RULE2 // 落下シーケンス case 2: - pull_L = 25; + pull_L = PullMax; pull_R = 0; // もし落下中に目標値から離れてしまった場合は、体勢を立て直して再び滑空 @@ -389,21 +360,61 @@ servoL.pulsewidth((ServoMax - ServoMin) * pull_L / PullMax + ServoMin); servoR.pulsewidth((ServoMax - ServoMin) * pull_R / PullMax + ServoMin); - - } myled = 0; // LED is OFF // ループはきっかり0.2秒ごと while(timer.read_ms() < 200); - - + } /* ------------------------------ ↑↑↑ ここまでメインループ ↑↑↑ ------------------------------ */ } +/** 各種ベクトルの初期化を行う関数 + * + */ +void VectorsInit() { + //重力ベクトルの初期化 + raw_g.SetComp(1, 0.0f); + raw_g.SetComp(2, 0.0f); + raw_g.SetComp(3, 1.0f); + + // 機体に固定されたベクトルの初期化 + b_f.SetComp(1, 0.0f); + b_f.SetComp(2, 0.0f); + b_f.SetComp(3, -1.0f); + b_u.SetComp(1, 1.0f); + b_u.SetComp(2, 0.0f); + b_u.SetComp(3, 0.0f); + b_l = Cross(b_u, b_f); + + // 目標座標をベクトルに代入 + target_p.SetComp(1, target_x * DEG_TO_RAD); + target_p.SetComp(2, target_y * DEG_TO_RAD); +} + +/** マイクロSDカードの初期化を行う関数 + * + */ +void SD_Init() { + //SDカード初期化 + char filename[15]; + int n = Find_last(); + if(n < 0) { + pc.printf("Could not read a SD Card.\n"); + return; + } + sprintf(filename, "/sd/log%03d.csv", n+1); + fp = fopen(filename, "w"); + fprintf(fp, "log data\r\n"); + xbee.printf("log data\r\n"); +} + +/** コンフィグファイルを読み込む関数 + * + */ void LoadConfig() { char value[20]; @@ -423,6 +434,10 @@ } } +/** ログファイルの番号の最大値を得る関数 + * + * @return マイクロSD内に存在するログファイル番号の最大値 + */ int Find_last() { int i, n = 0; @@ -443,6 +458,9 @@ return n; } +/** カルマンフィルタの初期化を行う関数 + * + */ void KalmanInit() { // 重力 @@ -482,6 +500,9 @@ } } +/** カルマンフィルタの更新を行う関数 + * + */ void KalmanUpdate() { // 重力 @@ -573,24 +594,17 @@ // 事後推定値の更新 post_x1 = pri_x1 + K1 * (raw_geomag - H1 * pri_x1); - // 地磁気ベクトルの大きさに拘束条件を与える - /*{ - Vector gm(3); - gm.SetComp(1, post_x1.GetComp(1)); - gm.SetComp(2, post_x1.GetComp(2)); - gm.SetComp(3, post_x1.GetComp(3)); - - gm = MAG_MAGNITUDE * gm.Normalize(); - - post_x1.SetComp(1, gm.GetComp(1)); - post_x1.SetComp(2, gm.GetComp(2)); - post_x1.SetComp(3, gm.GetComp(3)); - }*/ // 事後誤差分散行列の更新 post_P1 = (I1 - K1 * H1) * pri_P1; } } +/** GPS座標から距離を算出 + * @param 座標1(経度、緯度)(rad) + * @param 座標2(経度、緯度)(rad) + * + * @return 2点間の距離(m) + */ float Distance(Vector p1, Vector p2) { if(p1.GetDim() != p2.GetDim()) return 0.0f; @@ -610,7 +624,7 @@ * * @return 投下されたかどうか(true=投下 false=未投下 * -*/ + */ bool thrown() { static int opt_count = 0;