2014 sift / Mbed 2 deprecated TVDctrller2017_brdRev1_PandA

Dependencies:   mbed

Fork of TVDctrller2017_brdRev1_ver6 by 2014 sift

Committer:
sift
Date:
Fri Oct 27 09:11:31 2017 +0000
Revision:
41:0c53acd31247
Parent:
40:8e33c60c6590
Child:
42:3ab09d0e3071
first commit

Who changed what in which revision?

UserRevisionLine numberNew contents of line
sift 0:276c1dab2d62 1 #include "TVDCTRL.h"
sift 1:4d86ec2fe4b1 2 #include "MCP4922.h"
sift 1:4d86ec2fe4b1 3 #include "Steering.h"
sift 39:c05074379713 4 #include "Global.h"
sift 1:4d86ec2fe4b1 5
sift 1:4d86ec2fe4b1 6 extern AnalogIn apsP;
sift 1:4d86ec2fe4b1 7 extern AnalogIn apsS;
sift 2:9d69f27a3d3b 8 extern AnalogIn brake;
sift 1:4d86ec2fe4b1 9 extern DigitalOut LED[];
sift 27:37a8b4f6d28d 10 extern DigitalOut brakeSignal;
sift 27:37a8b4f6d28d 11 extern DigitalOut indicatorLed;
sift 27:37a8b4f6d28d 12 extern DigitalOut shutDown;
sift 27:37a8b4f6d28d 13 extern DigitalIn sdState;
sift 1:4d86ec2fe4b1 14 extern InterruptIn rightMotorPulse;
sift 1:4d86ec2fe4b1 15 extern InterruptIn leftMotorPulse;
sift 39:c05074379713 16 extern InterruptIn rightWheelPulse1;
sift 39:c05074379713 17 extern InterruptIn rightWheelPulse2;
sift 39:c05074379713 18 extern InterruptIn leftWheelPulse1;
sift 39:c05074379713 19 extern InterruptIn leftWheelPulse2;
sift 1:4d86ec2fe4b1 20 extern MCP4922 mcp;
sift 8:a22aec357a64 21 extern Serial pc;
sift 19:571a4d00b89c 22 extern AnalogOut STR2AN;
sift 27:37a8b4f6d28d 23 extern CAN can;
sift 1:4d86ec2fe4b1 24
sift 26:331e77bb479b 25 #define indicateSystem(x) (indicatorLed.write(x))
sift 26:331e77bb479b 26
sift 39:c05074379713 27 Timer wheelPulseTimer;
sift 2:9d69f27a3d3b 28 Ticker ticker1;
sift 2:9d69f27a3d3b 29 Ticker ticker2;
sift 1:4d86ec2fe4b1 30
sift 2:9d69f27a3d3b 31 #define apsPVol() (apsP.read() * 3.3)
sift 2:9d69f27a3d3b 32 #define apsSVol() (apsS.read() * 3.3)
sift 0:276c1dab2d62 33
sift 0:276c1dab2d62 34 struct {
sift 0:276c1dab2d62 35 unsigned int valA:12;
sift 0:276c1dab2d62 36 unsigned int valB:12;
sift 2:9d69f27a3d3b 37 } McpData;
sift 1:4d86ec2fe4b1 38
sift 2:9d69f27a3d3b 39 //各変数が一定値を超えた時点でエラー検出とする
sift 2:9d69f27a3d3b 40 //2つのAPSの区別はつけないことにする
sift 12:ae291fa7239c 41 struct errCounter_t errCounter= {0,0,0,0,0,0,0};
sift 1:4d86ec2fe4b1 42
sift 12:ae291fa7239c 43 int readyToDriveFlag = 1;
sift 12:ae291fa7239c 44
sift 12:ae291fa7239c 45 int gApsP=0, gApsS=0, gBrake=0; //現在のセンサ値
sift 12:ae291fa7239c 46 int rawApsP=0, rawApsS=0, rawBrake=0; //現在の補正無しのセンサ値
sift 2:9d69f27a3d3b 47
sift 28:47e9531a3a9d 48 int gRightMotorTorque=0, gLeftMotorTorque=0;
sift 28:47e9531a3a9d 49
sift 28:47e9531a3a9d 50 int getMotorTorque(Select rl)
sift 28:47e9531a3a9d 51 {
sift 28:47e9531a3a9d 52 return ((rl==LEFT) ? gLeftMotorTorque : gRightMotorTorque);
sift 28:47e9531a3a9d 53 }
sift 28:47e9531a3a9d 54
sift 18:b7c362c8f0fd 55 //エラーカウンタ外部参照用関数
sift 18:b7c362c8f0fd 56 //errCounter_t型変数のポインタを引数に取る
sift 2:9d69f27a3d3b 57 void getCurrentErrCount(struct errCounter_t *ptr)
sift 1:4d86ec2fe4b1 58 {
sift 12:ae291fa7239c 59 ptr->apsUnderVolt = errCounter.apsUnderVolt;
sift 12:ae291fa7239c 60 ptr->apsExceedVolt = errCounter.apsExceedVolt;
sift 12:ae291fa7239c 61 ptr->apsErrorTolerance = errCounter.apsErrorTolerance;
sift 12:ae291fa7239c 62 ptr->apsStick = errCounter.apsStick;
sift 12:ae291fa7239c 63 ptr->brakeUnderVolt = errCounter.brakeUnderVolt;
sift 12:ae291fa7239c 64 ptr->brakeExceedVolt = errCounter.brakeExceedVolt;
sift 12:ae291fa7239c 65 ptr->brakeFuzzyVolt = errCounter.brakeFuzzyVolt;
sift 12:ae291fa7239c 66 ptr->brakeOverRide = errCounter.brakeOverRide;
sift 12:ae291fa7239c 67 }
sift 12:ae291fa7239c 68
sift 18:b7c362c8f0fd 69 //ブレーキONOFF判定関数
sift 12:ae291fa7239c 70 //Brake-ON:1 Brake-OFF:0
sift 12:ae291fa7239c 71 int isBrakeOn(void)
sift 12:ae291fa7239c 72 {
sift 12:ae291fa7239c 73 int brake = gBrake;
sift 12:ae291fa7239c 74 int brakeOnOff = 0;
sift 12:ae291fa7239c 75
sift 30:c596a0f5d685 76 if(brake < (BRK_ON_VOLTAGE + ERROR_TOLERANCE))
sift 12:ae291fa7239c 77 brakeOnOff = 1;
sift 30:c596a0f5d685 78 if(brake > (BRK_OFF_VOLTAGE - ERROR_TOLERANCE))
sift 12:ae291fa7239c 79 brakeOnOff = 0;
sift 12:ae291fa7239c 80
sift 12:ae291fa7239c 81 return brakeOnOff;
sift 2:9d69f27a3d3b 82 }
sift 1:4d86ec2fe4b1 83
sift 18:b7c362c8f0fd 84 //センサ現在値外部参照関数
sift 7:ad013d88a539 85 int getCurrentSensor(int sensor)
sift 2:9d69f27a3d3b 86 {
sift 2:9d69f27a3d3b 87 switch (sensor) {
sift 2:9d69f27a3d3b 88 case APS_PRIMARY:
sift 2:9d69f27a3d3b 89 return gApsP;
sift 2:9d69f27a3d3b 90 case APS_SECONDARY:
sift 2:9d69f27a3d3b 91 return gApsS;
sift 2:9d69f27a3d3b 92 case BRAKE:
sift 2:9d69f27a3d3b 93 return gBrake;
sift 2:9d69f27a3d3b 94 default:
sift 2:9d69f27a3d3b 95 return -1;
sift 1:4d86ec2fe4b1 96 }
sift 2:9d69f27a3d3b 97 }
sift 2:9d69f27a3d3b 98
sift 18:b7c362c8f0fd 99 //補正前センサ現在値外部参照関数
sift 7:ad013d88a539 100 int getRawSensor(int sensor)
sift 2:9d69f27a3d3b 101 {
sift 2:9d69f27a3d3b 102 switch (sensor) {
sift 2:9d69f27a3d3b 103 case APS_PRIMARY:
sift 2:9d69f27a3d3b 104 return rawApsP;
sift 2:9d69f27a3d3b 105 case APS_SECONDARY:
sift 2:9d69f27a3d3b 106 return rawApsS;
sift 2:9d69f27a3d3b 107 case BRAKE:
sift 2:9d69f27a3d3b 108 return rawBrake;
sift 2:9d69f27a3d3b 109 default:
sift 2:9d69f27a3d3b 110 return -1;
sift 1:4d86ec2fe4b1 111 }
sift 2:9d69f27a3d3b 112 }
sift 2:9d69f27a3d3b 113
sift 2:9d69f27a3d3b 114 bool loadSensorFlag = false;
sift 2:9d69f27a3d3b 115
sift 2:9d69f27a3d3b 116 //タイマー割り込みでコールされる
sift 2:9d69f27a3d3b 117 void loadSensorsISR(void)
sift 2:9d69f27a3d3b 118 {
sift 2:9d69f27a3d3b 119 loadSensorFlag = true;
sift 1:4d86ec2fe4b1 120 }
sift 1:4d86ec2fe4b1 121
sift 25:c21d35c7f0de 122 //センサ読み込み関数
sift 2:9d69f27a3d3b 123 void loadSensors(void)
sift 1:4d86ec2fe4b1 124 {
sift 2:9d69f27a3d3b 125 if(true == loadSensorFlag) {
sift 2:9d69f27a3d3b 126 loadSensorFlag = false;
sift 2:9d69f27a3d3b 127 static int preApsP=0, preApsS=0; //過去のセンサ値
sift 2:9d69f27a3d3b 128 static int preBrake=0;
sift 2:9d69f27a3d3b 129 int tmpApsP=0, tmpApsS=0, tmpBrake=0; //補正後のセンサ値
sift 2:9d69f27a3d3b 130 int tmpApsErrCountU=0, tmpApsErrCountE=0; //APSの一時的なエラーカウンタ
sift 2:9d69f27a3d3b 131
sift 2:9d69f27a3d3b 132 //Low Pass Filter
sift 2:9d69f27a3d3b 133 tmpApsP = (int)(apsP.read_u16()*ratioLPF + preApsP*(1.0f-ratioLPF));
sift 2:9d69f27a3d3b 134 tmpApsS = (int)(apsS.read_u16()*ratioLPF + preApsS*(1.0f-ratioLPF));
sift 2:9d69f27a3d3b 135 tmpBrake = (int)(brake.read_u16()*ratioLPF + preBrake*(1.0f-ratioLPF));
sift 2:9d69f27a3d3b 136
sift 2:9d69f27a3d3b 137 //生のセンサ値取得
sift 2:9d69f27a3d3b 138 rawApsP = tmpApsP;
sift 2:9d69f27a3d3b 139 rawApsS = tmpApsS;
sift 2:9d69f27a3d3b 140 rawBrake = tmpBrake;
sift 2:9d69f27a3d3b 141
sift 2:9d69f27a3d3b 142 //センサーチェック
sift 2:9d69f27a3d3b 143 //APS上限値チェック
sift 2:9d69f27a3d3b 144 if(tmpApsP > APS_MAX_POSITION + ERROR_TOLERANCE) {
sift 2:9d69f27a3d3b 145 tmpApsP = APS_MAX_POSITION; //異常時,上限値にクリップ
sift 2:9d69f27a3d3b 146 tmpApsErrCountE++;
sift 2:9d69f27a3d3b 147 }
sift 2:9d69f27a3d3b 148 if(tmpApsS > APS_MAX_POSITION + ERROR_TOLERANCE) {
sift 2:9d69f27a3d3b 149 tmpApsS = APS_MAX_POSITION; //異常時,上限値にクリップ
sift 2:9d69f27a3d3b 150 tmpApsErrCountE++;
sift 2:9d69f27a3d3b 151 }
sift 2:9d69f27a3d3b 152 if(0 == tmpApsErrCountE)
sift 2:9d69f27a3d3b 153 errCounter.apsExceedVolt = 0; //どちらも正常時エラーカウンタクリア
sift 2:9d69f27a3d3b 154 else
sift 2:9d69f27a3d3b 155 errCounter.apsExceedVolt += tmpApsErrCountE;
sift 2:9d69f27a3d3b 156
sift 2:9d69f27a3d3b 157 //APS下限値チェック
sift 2:9d69f27a3d3b 158 if(tmpApsP < APS_MIN_POSITION - ERROR_TOLERANCE) {
sift 2:9d69f27a3d3b 159 tmpApsP = APS_MIN_POSITION; //下限値にクリップ
sift 2:9d69f27a3d3b 160 tmpApsErrCountU++;
sift 2:9d69f27a3d3b 161 }
sift 2:9d69f27a3d3b 162 if(tmpApsS < APS_MIN_POSITION - ERROR_TOLERANCE) {
sift 2:9d69f27a3d3b 163 tmpApsS = APS_MIN_POSITION; //下限値にクリップ
sift 2:9d69f27a3d3b 164 tmpApsErrCountU++;
sift 2:9d69f27a3d3b 165 }
sift 2:9d69f27a3d3b 166 if(0 == tmpApsErrCountU)
sift 2:9d69f27a3d3b 167 errCounter.apsUnderVolt = 0; //どちらも正常時エラーカウンタクリア
sift 2:9d69f27a3d3b 168 else
sift 2:9d69f27a3d3b 169 errCounter.apsUnderVolt += tmpApsErrCountU;
sift 2:9d69f27a3d3b 170
sift 2:9d69f27a3d3b 171 //センサー偏差チェック
sift 2:9d69f27a3d3b 172 if(myAbs(tmpApsP - tmpApsS) > APS_DEVIATION_TOLERANCE) { //偏差チェックには補正後の値(tmp)を使用
sift 2:9d69f27a3d3b 173 errCounter.apsErrorTolerance++;
sift 2:9d69f27a3d3b 174 } else {
sift 2:9d69f27a3d3b 175 errCounter.apsErrorTolerance = 0;
sift 2:9d69f27a3d3b 176 }
sift 1:4d86ec2fe4b1 177
sift 2:9d69f27a3d3b 178 //小さい方にクリップ
sift 2:9d69f27a3d3b 179 //APS値は好きな方を使いな
sift 2:9d69f27a3d3b 180 if(tmpApsP > tmpApsS) {
sift 2:9d69f27a3d3b 181 tmpApsP = tmpApsS;
sift 2:9d69f27a3d3b 182 } else {
sift 2:9d69f27a3d3b 183 tmpApsS = tmpApsP;
sift 2:9d69f27a3d3b 184 }
sift 2:9d69f27a3d3b 185
sift 2:9d69f27a3d3b 186 //Brake上限値チェック
sift 30:c596a0f5d685 187 if(tmpBrake > BRK_OFF_VOLTAGE + ERROR_TOLERANCE) {
sift 2:9d69f27a3d3b 188 errCounter.brakeExceedVolt++;
sift 30:c596a0f5d685 189 tmpBrake = BRK_OFF_VOLTAGE;
sift 2:9d69f27a3d3b 190 } else {
sift 2:9d69f27a3d3b 191 errCounter.brakeExceedVolt = 0;
sift 2:9d69f27a3d3b 192 }
sift 2:9d69f27a3d3b 193
sift 2:9d69f27a3d3b 194 //Brake下限値チェック
sift 30:c596a0f5d685 195 if(tmpBrake < BRK_ON_VOLTAGE - ERROR_TOLERANCE) {
sift 2:9d69f27a3d3b 196 errCounter.brakeUnderVolt++;
sift 30:c596a0f5d685 197 tmpBrake = BRK_ON_VOLTAGE;
sift 2:9d69f27a3d3b 198 } else {
sift 2:9d69f27a3d3b 199 errCounter.brakeUnderVolt = 0;
sift 2:9d69f27a3d3b 200 }
sift 1:4d86ec2fe4b1 201
sift 2:9d69f27a3d3b 202 //brake範囲外電圧チェック
sift 30:c596a0f5d685 203 if((tmpBrake < BRK_OFF_VOLTAGE - ERROR_TOLERANCE) && (tmpBrake > BRK_ON_VOLTAGE + ERROR_TOLERANCE)) {
sift 2:9d69f27a3d3b 204 errCounter.brakeFuzzyVolt++;
sift 2:9d69f27a3d3b 205 tmpBrake = BRK_OFF_VOLTAGE;
sift 2:9d69f27a3d3b 206 } else {
sift 2:9d69f27a3d3b 207 errCounter.brakeFuzzyVolt=0;
sift 2:9d69f27a3d3b 208 }
sift 2:9d69f27a3d3b 209
sift 2:9d69f27a3d3b 210 //APS固着チェック
sift 2:9d69f27a3d3b 211 if((preApsP == tmpApsP) && (tmpApsP == APS_MAX_POSITION))
sift 2:9d69f27a3d3b 212 errCounter.apsStick++;
sift 2:9d69f27a3d3b 213 else
sift 2:9d69f27a3d3b 214 errCounter.apsStick=0;
sift 2:9d69f27a3d3b 215
sift 2:9d69f27a3d3b 216 //ブレーキオーバーライドチェック
sift 12:ae291fa7239c 217 if((isBrakeOn() == 1) && (tmpApsP >= APS_OVERRIDE25)) //Brake-ON and APS > 25%
sift 2:9d69f27a3d3b 218 errCounter.brakeOverRide++;
sift 41:0c53acd31247 219 if(tmpApsP < APS_OVERRIDE05) //APS < 5%
sift 2:9d69f27a3d3b 220 errCounter.brakeOverRide=0;
sift 2:9d69f27a3d3b 221
sift 2:9d69f27a3d3b 222 //センサ値取得
sift 2:9d69f27a3d3b 223 gApsP = tmpApsP;
sift 2:9d69f27a3d3b 224 gApsS = tmpApsS;
sift 2:9d69f27a3d3b 225 gBrake = tmpBrake;
sift 2:9d69f27a3d3b 226
sift 2:9d69f27a3d3b 227 //未来の自分に期待
sift 2:9d69f27a3d3b 228 preApsP = rawApsP;
sift 2:9d69f27a3d3b 229 preApsS = rawApsS;
sift 2:9d69f27a3d3b 230 preBrake = rawBrake;
sift 2:9d69f27a3d3b 231 }
sift 1:4d86ec2fe4b1 232 }
sift 1:4d86ec2fe4b1 233
sift 39:c05074379713 234 //車輪速計測は”【空転再粘着制御】山下道寛”を参照のこと(一部改修)
sift 39:c05074379713 235 //パルス数カウンタ
sift 25:c21d35c7f0de 236 volatile int gRightMotorPulseCounter = 0, gLeftMotorPulseCounter = 0;
sift 39:c05074379713 237 volatile int gRightWheelPulseCounter = 0, gLeftWheelPulseCounter = 0;
sift 39:c05074379713 238 //パルス入力までの時間
sift 39:c05074379713 239 volatile int gRightWheelPulse_dT2 = 0, gLeftWheelPulse_dT2 = 0;
sift 39:c05074379713 240 volatile float gRightWheelRPS = 0, gLeftWheelRPS = 0;
sift 39:c05074379713 241
sift 7:ad013d88a539 242 volatile bool pulseTimeISRFlag = false;
sift 1:4d86ec2fe4b1 243
sift 39:c05074379713 244 /***********************************/
sift 39:c05074379713 245 //モータパルスカウント
sift 25:c21d35c7f0de 246 void countRightMotorPulseISR(void)
sift 1:4d86ec2fe4b1 247 {
sift 25:c21d35c7f0de 248 gRightMotorPulseCounter++;
sift 1:4d86ec2fe4b1 249 }
sift 1:4d86ec2fe4b1 250
sift 25:c21d35c7f0de 251 void countLeftMotorPulseISR(void)
sift 1:4d86ec2fe4b1 252 {
sift 25:c21d35c7f0de 253 gLeftMotorPulseCounter++;
sift 2:9d69f27a3d3b 254 }
sift 39:c05074379713 255 /***********************************/
sift 39:c05074379713 256
sift 39:c05074379713 257 /***********************************/
sift 39:c05074379713 258 //ホイールパルスカウント
sift 39:c05074379713 259 void countRightWheelPulseISR(void)
sift 39:c05074379713 260 {
sift 39:c05074379713 261 gRightWheelPulseCounter++; //パルス数カウント
sift 39:c05074379713 262 gRightWheelPulse_dT2 = wheelPulseTimer.read_us(); //現在の時間いただきます
sift 39:c05074379713 263 }
sift 39:c05074379713 264
sift 39:c05074379713 265 void countLeftWheelPulseISR(void)
sift 39:c05074379713 266 {
sift 39:c05074379713 267 }
sift 39:c05074379713 268 /***********************************/
sift 39:c05074379713 269
sift 39:c05074379713 270 void measRpsISR(void)
sift 39:c05074379713 271 {
sift 39:c05074379713 272 int rwpCounter = gRightWheelPulseCounter;
sift 39:c05074379713 273 static int rwp_dT1 = MAX_WHEEL_PULSE_TIME_US; //初期設定は無限時間前にパルス入力があったと仮定
sift 39:c05074379713 274 int rwp_dT2 = gRightWheelPulse_dT2;
sift 41:0c53acd31247 275 static bool preInputState = false;
sift 41:0c53acd31247 276 static int rwpStopCounter = 0; //タイヤが止まっている間カウントアップ
sift 39:c05074379713 277
sift 40:8e33c60c6590 278 //パルス数クリア
sift 40:8e33c60c6590 279 gRightWheelPulseCounter = 0;
sift 40:8e33c60c6590 280 gLeftWheelPulseCounter = 0;
sift 40:8e33c60c6590 281 //dT2の初期値はパルス入力ない状態 => 計測時間=0
sift 40:8e33c60c6590 282 gRightWheelPulse_dT2 = 0;
sift 40:8e33c60c6590 283 //次回計測周期までのパルス時間計測開始
sift 40:8e33c60c6590 284 wheelPulseTimer.reset();
sift 41:0c53acd31247 285
sift 41:0c53acd31247 286 //前回パルス入力がない場合
sift 41:0c53acd31247 287 if(preInputState == false) {
sift 39:c05074379713 288 //以前のdT1に計測周期の時間を積算
sift 40:8e33c60c6590 289 rwp_dT1 = rwp_dT1 + TIRE_MEAS_CYCLE_US;
sift 39:c05074379713 290 if(rwp_dT1 > MAX_WHEEL_PULSE_TIME_US)
sift 41:0c53acd31247 291 rwp_dT1 = MAX_WHEEL_PULSE_TIME_US; //overflow防止
sift 41:0c53acd31247 292 }
sift 41:0c53acd31247 293
sift 41:0c53acd31247 294 //パルス入力あれば直前のパルス入力からの経過時間取得
sift 41:0c53acd31247 295 if(rwpCounter != 0) {
sift 41:0c53acd31247 296 rwp_dT2 = TIRE_MEAS_CYCLE_US - rwp_dT2;
sift 39:c05074379713 297 }
sift 41:0c53acd31247 298
sift 41:0c53acd31247 299 //パルス入力ない場合---(設定回数未満)前回値保持/(設定回数以上)疑似パルス入力判定
sift 41:0c53acd31247 300 if(rwpCounter == 0) {
sift 41:0c53acd31247 301 if(rwpStopCounter < 100) {
sift 41:0c53acd31247 302 rwpStopCounter++;
sift 41:0c53acd31247 303 } else {
sift 41:0c53acd31247 304 gRightWheelRPS = 1.0f / ((TIRE_MEAS_CYCLE_US + rwp_dT1 - rwp_dT2) / 1000000.0f) / WHEEL_PULSE_NUM;
sift 40:8e33c60c6590 305 }
sift 41:0c53acd31247 306 } else {
sift 41:0c53acd31247 307 //RPS計算[rps](1sec当たりパルス数/タイヤパルス数)
sift 41:0c53acd31247 308 gRightWheelRPS = ((float)rwpCounter / ((TIRE_MEAS_CYCLE_US + rwp_dT1 - rwp_dT2) / 1000000.0f)) / WHEEL_PULSE_NUM;
sift 41:0c53acd31247 309 rwpStopCounter = 0;
sift 41:0c53acd31247 310 }
sift 41:0c53acd31247 311
sift 39:c05074379713 312 //パルス入力あれば次回のdT1はdT2を採用(パルス入力なければ現在値保持)
sift 39:c05074379713 313 if(rwpCounter != 0)
sift 40:8e33c60c6590 314 rwp_dT1 = rwp_dT2;
sift 41:0c53acd31247 315
sift 41:0c53acd31247 316 if(rwpCounter == 0)
sift 41:0c53acd31247 317 preInputState = false;
sift 41:0c53acd31247 318 else
sift 41:0c53acd31247 319 preInputState = true;
sift 39:c05074379713 320 }
sift 2:9d69f27a3d3b 321
sift 25:c21d35c7f0de 322 void getPulseCounterISR(void)
sift 2:9d69f27a3d3b 323 {
sift 7:ad013d88a539 324 pulseTimeISRFlag = true;
sift 2:9d69f27a3d3b 325 }
sift 2:9d69f27a3d3b 326
sift 28:47e9531a3a9d 327 //default argument : switchWheel=false
sift 28:47e9531a3a9d 328 int getRPS(Select rl, bool switchWheel)
sift 2:9d69f27a3d3b 329 {
sift 37:ba10cf09c151 330 static int rightMotorPulse[100]= {0}, leftMotorPulse[100]= {0}; //過去1.0秒間のパルス数格納
sift 25:c21d35c7f0de 331 static int sumRightMotorPulse, sumLeftMotorPulse;
sift 28:47e9531a3a9d 332 float rps;
sift 2:9d69f27a3d3b 333
sift 7:ad013d88a539 334 if(pulseTimeISRFlag == true) {
sift 37:ba10cf09c151 335 for(int i=99; i>0; i--) {
sift 25:c21d35c7f0de 336 rightMotorPulse[i] = rightMotorPulse[i-1];
sift 25:c21d35c7f0de 337 leftMotorPulse[i] = leftMotorPulse[i-1];
sift 25:c21d35c7f0de 338 }
sift 25:c21d35c7f0de 339
sift 25:c21d35c7f0de 340 rightMotorPulse[0] = gRightMotorPulseCounter;
sift 25:c21d35c7f0de 341 leftMotorPulse[0] = gLeftMotorPulseCounter;
sift 2:9d69f27a3d3b 342
sift 25:c21d35c7f0de 343 gRightMotorPulseCounter = 0;
sift 25:c21d35c7f0de 344 gLeftMotorPulseCounter = 0;
sift 10:87ad65eef0e9 345
sift 25:c21d35c7f0de 346 sumRightMotorPulse = 0;
sift 25:c21d35c7f0de 347 sumLeftMotorPulse = 0;
sift 25:c21d35c7f0de 348
sift 37:ba10cf09c151 349 for(int i=0; i<100; i++) {
sift 25:c21d35c7f0de 350 sumRightMotorPulse += rightMotorPulse[i];
sift 25:c21d35c7f0de 351 sumLeftMotorPulse += leftMotorPulse[i];
sift 25:c21d35c7f0de 352 }
sift 28:47e9531a3a9d 353 pulseTimeISRFlag = false;
sift 2:9d69f27a3d3b 354 }
sift 2:9d69f27a3d3b 355
sift 31:042c08a7434f 356 if(switchWheel == false) {
sift 28:47e9531a3a9d 357 if(rl == RIGHT)
sift 37:ba10cf09c151 358 rps = (float)1.0f*sumRightMotorPulse / MOTOR_PULSE_NUM / GEAR_RATIO; //過去0.5秒間のモータパルス数を使ってRPS算出
sift 28:47e9531a3a9d 359 else
sift 37:ba10cf09c151 360 rps = (float)1.0f*sumLeftMotorPulse / MOTOR_PULSE_NUM / GEAR_RATIO; //過去0.5秒間のモータパルス数を使ってRPS算出
sift 28:47e9531a3a9d 361 } else {
sift 28:47e9531a3a9d 362 //こっちはタイヤ回転数
sift 28:47e9531a3a9d 363 //そのうち対応
sift 28:47e9531a3a9d 364 if(rl == RIGHT)
sift 39:c05074379713 365 rps = gRightWheelRPS; //過去1秒間のモータパルス数を使ってRPS算出
sift 28:47e9531a3a9d 366 else
sift 39:c05074379713 367 rps = gLeftWheelRPS; //過去1秒間のモータパルス数を使ってRPS算出
sift 28:47e9531a3a9d 368 }
sift 28:47e9531a3a9d 369 return (int)(rps / LSB_MOTORSPEED); //LSB変換
sift 2:9d69f27a3d3b 370 }
sift 2:9d69f27a3d3b 371
sift 2:9d69f27a3d3b 372 float getVelocity(void)
sift 2:9d69f27a3d3b 373 {
sift 38:11753ee9734f 374 // static float debugVelocity = 0.0f;
sift 38:11753ee9734f 375 // debugVelocity += 0.002;
sift 38:11753ee9734f 376 //
sift 38:11753ee9734f 377 // printf("%1.2f\r\n", debugVelocity);
sift 38:11753ee9734f 378 //
sift 38:11753ee9734f 379 // return debugVelocity;
sift 32:9688c30ac38b 380 return (0.5f*TIRE_DIAMETER*2*M_PI*(getRPS(RIGHT) + getRPS(LEFT))*0.5f)*LSB_MOTORSPEED;
sift 38:11753ee9734f 381 // return 15.0f;
sift 1:4d86ec2fe4b1 382 }
sift 1:4d86ec2fe4b1 383
sift 34:594ddb4008b2 384 int distributeTorque_omega(float steeringWheelAngle)
sift 21:bbf2ad7e6602 385 {
sift 21:bbf2ad7e6602 386 static float lastSteering=0.0f;
sift 22:95c1f753ecad 387 float omega=0;
sift 22:95c1f753ecad 388 int disTrq=0;
sift 30:c596a0f5d685 389
sift 34:594ddb4008b2 390 steeringWheelAngle = ratioLPF * steeringWheelAngle + (1.0f - ratioLPF) * lastSteering;
sift 21:bbf2ad7e6602 391
sift 34:594ddb4008b2 392 omega = steeringWheelAngle - lastSteering; //舵角の差分算出
sift 21:bbf2ad7e6602 393 omega /= 0.01f; //制御周期で角速度演算
sift 36:dc33a3a194c9 394
sift 22:95c1f753ecad 395 if(myAbs(omega) < 0.349f) { //20deg/s
sift 21:bbf2ad7e6602 396 disTrq = 0;
sift 22:95c1f753ecad 397 } else if(myAbs(omega) <= 8.727f) { //500deg/s
sift 34:594ddb4008b2 398 disTrq = (int)(MAX_DISTRIBUTION_TORQUE_OMEGA / (8.727f-0.349f) * (myAbs(omega) - 0.349f));
sift 21:bbf2ad7e6602 399 } else
sift 34:594ddb4008b2 400 disTrq = (int)MAX_DISTRIBUTION_TORQUE_OMEGA;
sift 22:95c1f753ecad 401
sift 34:594ddb4008b2 402 lastSteering = steeringWheelAngle;
sift 21:bbf2ad7e6602 403
sift 34:594ddb4008b2 404 if(omega < 0)
sift 22:95c1f753ecad 405 disTrq = -disTrq;
sift 22:95c1f753ecad 406
sift 21:bbf2ad7e6602 407 return disTrq;
sift 21:bbf2ad7e6602 408 }
sift 21:bbf2ad7e6602 409
sift 31:042c08a7434f 410 int distributeTorque(float steeringWheelAngle, float velocity)
sift 2:9d69f27a3d3b 411 {
sift 31:042c08a7434f 412 double V2 = velocity * velocity;
sift 31:042c08a7434f 413 double R = 0.0; //旋回半径
sift 31:042c08a7434f 414 double Gy = 0.0; //横G
sift 31:042c08a7434f 415 double deadband = 0.0;
sift 32:9688c30ac38b 416 double steeringAngle = (double)steeringWheelAngle * STEER_RATIO;
sift 31:042c08a7434f 417 double steeringSign = 1.0;
sift 9:220e4e77e056 418 int disTrq = 0;
sift 25:c21d35c7f0de 419
sift 31:042c08a7434f 420 if(steeringAngle > 0)
sift 34:594ddb4008b2 421 steeringSign = 1.0;
sift 25:c21d35c7f0de 422 else
sift 34:594ddb4008b2 423 steeringSign = -1.0;
sift 25:c21d35c7f0de 424
sift 31:042c08a7434f 425 steeringAngle = myAbs(steeringAngle);
sift 32:9688c30ac38b 426
sift 38:11753ee9734f 427 if(steeringAngle <= 0.0001)
sift 31:042c08a7434f 428 steeringAngle = 0.0001;
sift 2:9d69f27a3d3b 429
sift 31:042c08a7434f 430 R = (1.0 + A*V2)*WHEEL_BASE / steeringAngle; //理論旋回半径 計算
sift 32:9688c30ac38b 431 Gy = V2 / R / 9.81; //理論横G
sift 31:042c08a7434f 432
sift 34:594ddb4008b2 433 if(Gy <= deadband)
sift 9:220e4e77e056 434 disTrq = 0;
sift 34:594ddb4008b2 435 else if(Gy <= 1.5) {
sift 31:042c08a7434f 436 Gy -= deadband;
sift 34:594ddb4008b2 437 disTrq = (int)(MAX_DISTRIBUTION_TORQUE / (1.5 - deadband) * Gy);
sift 25:c21d35c7f0de 438 } else {
sift 19:571a4d00b89c 439 disTrq = MAX_DISTRIBUTION_TORQUE;
sift 25:c21d35c7f0de 440 }
sift 2:9d69f27a3d3b 441
sift 36:dc33a3a194c9 442 return (int)(disTrq * steeringSign);
sift 2:9d69f27a3d3b 443 }
sift 2:9d69f27a3d3b 444
sift 25:c21d35c7f0de 445 //rpm +++++ モータ回転数
sift 25:c21d35c7f0de 446 //regSwitch +++++ 回生=1 力行=0
sift 25:c21d35c7f0de 447 inline int calcMaxTorque(int rpm, bool regSwitch)
sift 2:9d69f27a3d3b 448 {
sift 25:c21d35c7f0de 449 int maxTrq=0;
sift 25:c21d35c7f0de 450
sift 25:c21d35c7f0de 451 //後で削除
sift 25:c21d35c7f0de 452 rpm = 2000;
sift 26:331e77bb479b 453 //++++++++++++++++++++
sift 25:c21d35c7f0de 454
sift 25:c21d35c7f0de 455 if(regSwitch == 0) {
sift 25:c21d35c7f0de 456 if(rpm <3000)
sift 25:c21d35c7f0de 457 maxTrq = MAX_MOTOR_TORQUE_POWER;
sift 25:c21d35c7f0de 458 else if(rpm <= 11000)
sift 25:c21d35c7f0de 459 maxTrq = maxTorqueMap[(int)(rpm / 10.0)];
sift 25:c21d35c7f0de 460 else
sift 25:c21d35c7f0de 461 maxTrq = MAX_REVOLUTION_TORQUE_POWER;
sift 25:c21d35c7f0de 462 } else {
sift 28:47e9531a3a9d 463 if(rpm < 600) {
sift 25:c21d35c7f0de 464 maxTrq = 0;
sift 28:47e9531a3a9d 465 } else if(rpm < 1250) {
sift 28:47e9531a3a9d 466 //+++++++++++++++++++++++++++++++++++++
sift 28:47e9531a3a9d 467 //暫定処理 今後回生トルクマップも要作成
sift 28:47e9531a3a9d 468 maxTrq = 0;
sift 28:47e9531a3a9d 469 //+++++++++++++++++++++++++++++++++++++
sift 25:c21d35c7f0de 470 } else if(rpm <= 6000) {
sift 26:331e77bb479b 471 maxTrq = MAX_MOTOR_TORQUE_REGENERATIVE;
sift 26:331e77bb479b 472 } else if(rpm <= 11000) {
sift 25:c21d35c7f0de 473 //+++++++++++++++++++++++++++++++++++++
sift 25:c21d35c7f0de 474 //暫定処理 今後回生トルクマップも要作成
sift 26:331e77bb479b 475 maxTrq = MAX_REVOLUTION_TORQUE_REGENERATIVE;
sift 25:c21d35c7f0de 476 //+++++++++++++++++++++++++++++++++++++
sift 25:c21d35c7f0de 477 } else {
sift 25:c21d35c7f0de 478 maxTrq = MAX_REVOLUTION_TORQUE_REGENERATIVE;
sift 25:c21d35c7f0de 479 }
sift 25:c21d35c7f0de 480 }
sift 25:c21d35c7f0de 481 return maxTrq;
sift 2:9d69f27a3d3b 482 }
sift 2:9d69f27a3d3b 483
sift 25:c21d35c7f0de 484 //演算方法
sift 25:c21d35c7f0de 485 //y = a(x - b) + c
sift 25:c21d35c7f0de 486 //x = 1/a * (y + ab - c)
sift 25:c21d35c7f0de 487 unsigned int calcTorqueToVoltage(int reqTorque, int rpm)
sift 2:9d69f27a3d3b 488 {
sift 25:c21d35c7f0de 489 float slope = 0; //a
sift 25:c21d35c7f0de 490 int startPoint = 0; //b
sift 25:c21d35c7f0de 491 int intercept = 0; //c
sift 12:ae291fa7239c 492
sift 25:c21d35c7f0de 493 int outputVoltage=0;
sift 16:7afd623ef48a 494
sift 25:c21d35c7f0de 495 if(reqTorque > LINEAR_REGION_TORQUE_POWER) { //力行トルクがrpmに対して非線形となる領域
sift 25:c21d35c7f0de 496 slope = (float)(calcMaxTorque(rpm, 0) - LINEAR_REGION_TORQUE_POWER)/(DACOUTPUT_MAX - LINEAR_REGION_VOLTAGE_POWER);
sift 25:c21d35c7f0de 497 startPoint = LINEAR_REGION_VOLTAGE_POWER;
sift 25:c21d35c7f0de 498 intercept = LINEAR_REGION_TORQUE_POWER;
sift 25:c21d35c7f0de 499
sift 25:c21d35c7f0de 500 outputVoltage = (int)((reqTorque + slope*startPoint - intercept) / slope);
sift 6:26fa8c78500e 501
sift 25:c21d35c7f0de 502 } else if(reqTorque > 0) { //力行トルクがrpmに対して線形となる領域
sift 25:c21d35c7f0de 503 slope = (float)LINEAR_REGION_TORQUE_POWER/(LINEAR_REGION_VOLTAGE_POWER - ZERO_TORQUE_VOLTAGE_P);
sift 25:c21d35c7f0de 504 startPoint = ZERO_TORQUE_VOLTAGE_P;
sift 25:c21d35c7f0de 505 intercept = 0;
sift 25:c21d35c7f0de 506
sift 25:c21d35c7f0de 507 outputVoltage = (int)(reqTorque/slope + startPoint);
sift 25:c21d35c7f0de 508
sift 25:c21d35c7f0de 509 } else if(0 == reqTorque) {
sift 25:c21d35c7f0de 510
sift 25:c21d35c7f0de 511 outputVoltage = ZERO_TORQUE_VOLTAGE_NEUTRAL; //ニュートラル信号
sift 6:26fa8c78500e 512
sift 25:c21d35c7f0de 513 } else if(reqTorque > LINEAR_REGION_TORQUE_REGENERATIVE) { //回生トルクがrpmに対して線形となる領域
sift 25:c21d35c7f0de 514 slope = (float)(0 - LINEAR_REGION_TORQUE_REGENERATIVE)/(ZERO_TORQUE_VOLTAGE_REG - LINEAR_REGION_VOLTAGE_REGENERATIVE);
sift 25:c21d35c7f0de 515 startPoint = LINEAR_REGION_VOLTAGE_REGENERATIVE;
sift 25:c21d35c7f0de 516 intercept = LINEAR_REGION_TORQUE_REGENERATIVE;
sift 25:c21d35c7f0de 517
sift 25:c21d35c7f0de 518 outputVoltage = (int)(reqTorque/slope + startPoint);
sift 25:c21d35c7f0de 519
sift 25:c21d35c7f0de 520 } else { //回生トルクがrpmに対して非線形となる領域
sift 25:c21d35c7f0de 521 slope = (float)(LINEAR_REGION_TORQUE_REGENERATIVE - calcMaxTorque(rpm, 1))/(LINEAR_REGION_VOLTAGE_REGENERATIVE - DACOUTPUT_MIN);
sift 25:c21d35c7f0de 522 startPoint = DACOUTPUT_MIN;
sift 25:c21d35c7f0de 523 intercept = calcMaxTorque(rpm, 1);
sift 25:c21d35c7f0de 524
sift 25:c21d35c7f0de 525 outputVoltage = (int)((reqTorque + slope*startPoint - intercept) / slope);
sift 2:9d69f27a3d3b 526 }
sift 2:9d69f27a3d3b 527
sift 25:c21d35c7f0de 528 if(outputVoltage > DACOUTPUT_MAX)
sift 25:c21d35c7f0de 529 outputVoltage = DACOUTPUT_MAX;
sift 25:c21d35c7f0de 530 if(outputVoltage < DACOUTPUT_MIN)
sift 25:c21d35c7f0de 531 outputVoltage = DACOUTPUT_MIN;
sift 16:7afd623ef48a 532
sift 20:3c5061281a7a 533 return (unsigned int)(0xFFF*((double)outputVoltage/0xFFFF)); //DACの分解能に適応(16bit->12bit)
sift 2:9d69f27a3d3b 534 }
sift 2:9d69f27a3d3b 535
sift 2:9d69f27a3d3b 536 int calcRequestTorque(void)
sift 2:9d69f27a3d3b 537 {
sift 2:9d69f27a3d3b 538 int currentAPS;
sift 2:9d69f27a3d3b 539 int requestTorque;
sift 2:9d69f27a3d3b 540
sift 2:9d69f27a3d3b 541 currentAPS = ((gApsP>gApsS) ? gApsS : gApsP); //センサ値は小さい方を採用
sift 12:ae291fa7239c 542
sift 2:9d69f27a3d3b 543 if(currentAPS < APS_MIN_POSITION)
sift 2:9d69f27a3d3b 544 currentAPS = 0;
sift 2:9d69f27a3d3b 545 else
sift 2:9d69f27a3d3b 546 currentAPS -= APS_MIN_POSITION; //オフセット修正
sift 2:9d69f27a3d3b 547
sift 25:c21d35c7f0de 548 if(currentAPS <= APS_REG_RANGE) //デッドバンド内であれば要求トルク->0
sift 25:c21d35c7f0de 549 requestTorque = (int)((float)(-MAX_OUTPUT_TORQUE_REGENERATIVE) / APS_REG_RANGE * currentAPS + MAX_OUTPUT_TORQUE_REGENERATIVE);
sift 2:9d69f27a3d3b 550 else
sift 25:c21d35c7f0de 551 requestTorque = (int)((float)MAX_OUTPUT_TORQUE_POWER / APS_PWR_RANGE * (currentAPS - APS_REG_RANGE));
sift 2:9d69f27a3d3b 552
sift 25:c21d35c7f0de 553 if(requestTorque > MAX_OUTPUT_TORQUE_POWER)
sift 25:c21d35c7f0de 554 requestTorque = MAX_OUTPUT_TORQUE_POWER;
sift 25:c21d35c7f0de 555 else if(requestTorque < MAX_OUTPUT_TORQUE_REGENERATIVE)
sift 25:c21d35c7f0de 556 requestTorque = MAX_OUTPUT_TORQUE_REGENERATIVE;
sift 2:9d69f27a3d3b 557
sift 12:ae291fa7239c 558 if((errCounter.brakeOverRide > ERRCOUNTER_DECISION) || (readyToDriveFlag == 1))
sift 12:ae291fa7239c 559 requestTorque = 0;
sift 12:ae291fa7239c 560
sift 2:9d69f27a3d3b 561 return requestTorque;
sift 2:9d69f27a3d3b 562 }
sift 2:9d69f27a3d3b 563
sift 17:a2246ce3333f 564 //トルク配分車速制限関数
sift 17:a2246ce3333f 565 //車速が低速域の場合,トルク配分0
sift 17:a2246ce3333f 566 float limitTorqueDistribution(void)
sift 17:a2246ce3333f 567 {
sift 17:a2246ce3333f 568 float limitRate;
sift 17:a2246ce3333f 569 float currentVelocity = getVelocity() * 3.6f; //km/hで車速取得
sift 20:3c5061281a7a 570
sift 37:ba10cf09c151 571 if(currentVelocity < 15.0f)
sift 17:a2246ce3333f 572 limitRate = 0.0f;
sift 36:dc33a3a194c9 573 else if(currentVelocity < 30.0f)
sift 38:11753ee9734f 574 limitRate = (currentVelocity - 15.0f) / (30.0f - 15.0f);
sift 17:a2246ce3333f 575 else
sift 17:a2246ce3333f 576 limitRate = 1.0f;
sift 36:dc33a3a194c9 577
sift 35:b75595b1da36 578 //printf("rate:%1.3f\r\n", limitRate);
sift 36:dc33a3a194c9 579
sift 17:a2246ce3333f 580 return limitRate;
sift 17:a2246ce3333f 581 }
sift 17:a2246ce3333f 582
sift 26:331e77bb479b 583 void driveTVD(int TVDmode, bool isRedyToDrive)
sift 1:4d86ec2fe4b1 584 {
sift 6:26fa8c78500e 585 int requestTorque=0; //ドライバー要求トルク
sift 6:26fa8c78500e 586 int distributionTrq=0; //分配トルク
sift 21:bbf2ad7e6602 587 int disTrq_omega=0;
sift 21:bbf2ad7e6602 588 int torqueRight, torqueLeft; //トルクの右左
sift 20:3c5061281a7a 589 static unsigned int preMcpA=0, preMcpB=0;
sift 20:3c5061281a7a 590
sift 2:9d69f27a3d3b 591 loadSensors(); //APS,BRAKE更新
sift 2:9d69f27a3d3b 592 loadSteerAngle(); //舵角更新
sift 41:0c53acd31247 593
sift 41:0c53acd31247 594 // printf("%04d\r\n",gRightWheelPulseCounter);
sift 41:0c53acd31247 595 printf("%f\r\n",gRightWheelRPS*60.0f);
sift 41:0c53acd31247 596 // printf("%09d %09d %09d\r\n",rwp_dT1, rwp_dT2, rwpCounter);
sift 12:ae291fa7239c 597
sift 26:331e77bb479b 598 if(isRedyToDrive && isBrakeOn())
sift 12:ae291fa7239c 599 readyToDriveFlag = 0;
sift 2:9d69f27a3d3b 600
sift 12:ae291fa7239c 601 if((errCounter.apsUnderVolt > ERRCOUNTER_DECISION)
sift 12:ae291fa7239c 602 || (errCounter.apsExceedVolt > ERRCOUNTER_DECISION)
sift 12:ae291fa7239c 603 || (errCounter.apsErrorTolerance > ERRCOUNTER_DECISION)
sift 12:ae291fa7239c 604 // || (errCounter.apsStick > ERRCOUNTER_DECISION)
sift 30:c596a0f5d685 605 || (errCounter.brakeUnderVolt > ERRCOUNTER_DECISION)
sift 30:c596a0f5d685 606 || (errCounter.brakeExceedVolt > ERRCOUNTER_DECISION)
sift 30:c596a0f5d685 607 || (errCounter.brakeFuzzyVolt > ERRCOUNTER_DECISION)
sift 12:ae291fa7239c 608 ) {
sift 16:7afd623ef48a 609 readyToDriveFlag = 1;
sift 12:ae291fa7239c 610 }
sift 16:7afd623ef48a 611
sift 12:ae291fa7239c 612 indicateSystem(readyToDriveFlag | (errCounter.brakeOverRide > ERRCOUNTER_DECISION));
sift 20:3c5061281a7a 613 LED[0] = readyToDriveFlag | (errCounter.brakeOverRide > ERRCOUNTER_DECISION);
sift 16:7afd623ef48a 614
sift 6:26fa8c78500e 615 requestTorque=calcRequestTorque(); //ドライバー要求トルク取得
sift 4:d7778cde0aff 616
sift 37:ba10cf09c151 617 distributionTrq = (int)((distributeTorque(M_PI * getSteerAngle() / 127.0f, getVelocity())*limitTorqueDistribution()) / 2.0f); //片モーターのトルク分配量計算
sift 38:11753ee9734f 618 disTrq_omega = (int)((distributeTorque_omega(M_PI * getSteerAngle() / 127.0f)*limitTorqueDistribution()) / 2.0f); //微分制御
sift 12:ae291fa7239c 619
sift 34:594ddb4008b2 620 //printf("%d\r\n", distributionTrq);
sift 34:594ddb4008b2 621
sift 38:11753ee9734f 622 // distributionTrq = 0;
sift 35:b75595b1da36 623 disTrq_omega = 0;
sift 31:042c08a7434f 624
sift 25:c21d35c7f0de 625 torqueRight = requestTorque + distributionTrq;
sift 25:c21d35c7f0de 626 torqueLeft = requestTorque - distributionTrq;
sift 21:bbf2ad7e6602 627
sift 22:95c1f753ecad 628 torqueRight += disTrq_omega;
sift 22:95c1f753ecad 629 torqueLeft -= disTrq_omega;
sift 20:3c5061281a7a 630
sift 38:11753ee9734f 631 if(torqueRight < 0) {
sift 38:11753ee9734f 632 if((getRPS(RIGHT) * LSB_MOTORSPEED * 60.0f) < 600.0f) {
sift 38:11753ee9734f 633 torqueLeft = requestTorque + torqueRight;
sift 38:11753ee9734f 634 torqueRight = 0;
sift 38:11753ee9734f 635 } else if((getRPS(RIGHT) * LSB_MOTORSPEED * 60.0f) <= 1250.0f) {
sift 38:11753ee9734f 636 torqueLeft = requestTorque + torqueRight*((getRPS(RIGHT) * GEAR_RATIO * LSB_MOTORSPEED * 60.0f - 600.0f)/(1250.0f - 600.0f));
sift 38:11753ee9734f 637 torqueRight = torqueRight*((getRPS(RIGHT)-600.0f)/(1250.0f - 600.0f));
sift 38:11753ee9734f 638 }
sift 38:11753ee9734f 639 }
sift 38:11753ee9734f 640 if(torqueLeft < 0) {
sift 38:11753ee9734f 641 if((getRPS(LEFT) * LSB_MOTORSPEED * 60.0f) < 600.0f) {
sift 38:11753ee9734f 642 torqueRight = requestTorque + torqueLeft;
sift 38:11753ee9734f 643 torqueLeft = 0;
sift 38:11753ee9734f 644 } else if((getRPS(LEFT) * LSB_MOTORSPEED * 60.0f) <= 1250.0f) {
sift 38:11753ee9734f 645 torqueRight = requestTorque + torqueLeft*((getRPS(LEFT) * GEAR_RATIO * LSB_MOTORSPEED * 60.0f - 600.0f)/(1250.0f - 600.0f));
sift 38:11753ee9734f 646 torqueLeft = torqueLeft*((getRPS(LEFT)-600.0f)/(1250.0f - 600.0f));
sift 38:11753ee9734f 647 }
sift 38:11753ee9734f 648 }
sift 38:11753ee9734f 649
sift 26:331e77bb479b 650 //アクセルべた踏みでトルクMAX、旋回より駆動を優先(加速番長モード)
sift 26:331e77bb479b 651 if(torqueLeft > MAX_OUTPUT_TORQUE_POWER) { //片モーター上限時最大値にクリップ
sift 26:331e77bb479b 652 torqueLeft = MAX_OUTPUT_TORQUE_POWER;
sift 26:331e77bb479b 653 torqueRight = requestTorque - (MAX_OUTPUT_TORQUE_POWER-requestTorque);
sift 16:7afd623ef48a 654 }
sift 26:331e77bb479b 655 if(torqueRight > MAX_OUTPUT_TORQUE_POWER) { //片モーター上限時最大値にクリップ
sift 26:331e77bb479b 656 torqueRight = MAX_OUTPUT_TORQUE_POWER;
sift 26:331e77bb479b 657 torqueLeft = requestTorque - (MAX_OUTPUT_TORQUE_POWER-requestTorque);
sift 26:331e77bb479b 658 }
sift 34:594ddb4008b2 659
sift 34:594ddb4008b2 660 gRightMotorTorque = torqueRight;
sift 34:594ddb4008b2 661 gLeftMotorTorque = torqueLeft;
sift 34:594ddb4008b2 662
sift 28:47e9531a3a9d 663 McpData.valA = calcTorqueToVoltage(torqueRight, getRPS(RIGHT));
sift 28:47e9531a3a9d 664 McpData.valB = calcTorqueToVoltage(torqueLeft, getRPS(LEFT));
sift 16:7afd623ef48a 665
sift 38:11753ee9734f 666 // preMcpA = (unsigned int)(McpData.valA * 0.456 + preMcpA * 0.544);
sift 38:11753ee9734f 667 // preMcpB = (unsigned int)(McpData.valB * 0.456 + preMcpB * 0.544);
sift 38:11753ee9734f 668 preMcpA = McpData.valA;
sift 38:11753ee9734f 669 preMcpB = McpData.valB;
sift 20:3c5061281a7a 670
sift 20:3c5061281a7a 671 mcp.writeA(preMcpA); //右モーター
sift 20:3c5061281a7a 672 mcp.writeB(preMcpB); //左モーター
sift 1:4d86ec2fe4b1 673 }
sift 1:4d86ec2fe4b1 674
sift 1:4d86ec2fe4b1 675 void initTVD(void)
sift 1:4d86ec2fe4b1 676 {
sift 39:c05074379713 677 wheelPulseTimer.reset();
sift 39:c05074379713 678
sift 39:c05074379713 679 wheelPulseTimer.start();
sift 1:4d86ec2fe4b1 680
sift 25:c21d35c7f0de 681 rightMotorPulse.fall(&countRightMotorPulseISR);
sift 25:c21d35c7f0de 682 leftMotorPulse.fall(&countLeftMotorPulseISR);
sift 39:c05074379713 683 rightWheelPulse1.fall(&countRightWheelPulseISR);
sift 41:0c53acd31247 684 // rightWheelPulse2.fall(&countRightWheelPulseISR);
sift 41:0c53acd31247 685 // rightWheelPulse1.rise(&countRightWheelPulseISR);
sift 41:0c53acd31247 686 // rightWheelPulse2.rise(&countRightWheelPulseISR);
sift 39:c05074379713 687 leftWheelPulse1.fall(&countLeftWheelPulseISR);
sift 25:c21d35c7f0de 688
sift 25:c21d35c7f0de 689 ticker1.attach(&loadSensorsISR, CONTROL_CYCLE_S); //制御周期毎にデータ読み込み(LPF演算のため)
sift 40:8e33c60c6590 690 // ticker2.attach(&getPulseCounterISR, CONTROL_CYCLE_S); //
sift 40:8e33c60c6590 691 ticker2.attach(&measRpsISR, TIRE_MEAS_CYCLE_US / 1000000.0f); //
sift 10:87ad65eef0e9 692
sift 10:87ad65eef0e9 693 mcp.writeA(0); //右モーター
sift 10:87ad65eef0e9 694 mcp.writeB(0); //左モーター
sift 28:47e9531a3a9d 695
sift 30:c596a0f5d685 696 printf("MAX OUTPUT TORQUE:\t\t%1.2f[Nm]\r\n", LSB_MOTOR_TORQUE * MAX_OUTPUT_TORQUE_POWER);
sift 30:c596a0f5d685 697 printf("MAX OUTPUT REG-TORQUE:\t\t%1.2f[Nm]\r\n", LSB_MOTOR_TORQUE * MAX_OUTPUT_TORQUE_REGENERATIVE);
sift 30:c596a0f5d685 698 printf("MAX DISTRIBUTION TORQUE:\t%1.2f[Nm]\r\n", LSB_MOTOR_TORQUE * MAX_DISTRIBUTION_TORQUE);
sift 30:c596a0f5d685 699 printf("MIN INNERWHEEL-MOTOR TORQUE:\t%1.2f[Nm]\r\n", LSB_MOTOR_TORQUE * MIN_INNERWHEEL_MOTOR_TORQUE);
sift 1:4d86ec2fe4b1 700 }