Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependencies: mbed SDFileSystem ConfigFile
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;