shooting process

This commit is contained in:
DashyFox 2024-09-22 00:19:50 +03:00
parent 6746f19cf0
commit b98846eac1
12 changed files with 393 additions and 151 deletions

File diff suppressed because one or more lines are too long

View File

@ -11,6 +11,12 @@
#include "pca9685.h"
#include "EEPROM.h"
// 0 - setPos AFTER preRun delay
// 1 - setPos IMMEDIATELY
#define PRE_RUN_DELAY_MODE 0
#define NOBALL_TIMEOUT_MULTIPLIER 4.2
typedef enum ServoMap{
SERVO_AXIAL = 0,
SERVO_HORIZONTAL = 1,
@ -21,8 +27,16 @@ typedef enum CurrentMode {
NoneMode, ShotMode, ProgramMode, MacroMode,
} Mode;
typedef enum State{
STOP,
RUN,
PAUSE,
PRERUN_WAIT
}State;
typedef struct CurrentShot {
uint8_t index;
uint16_t currentRepeatCount;
Shot shot;
} CurrentShot;
@ -38,43 +52,47 @@ typedef struct CurrentMacro {
uint8_t program_index;
} CurrentMacro;
typedef struct CurrentState {
uint8_t isPause;
uint8_t isShooting;
} CurrentState;
//typedef struct CurrentState {
// uint8_t isPause;
// uint8_t isShooting;
//} CurrentState;
typedef struct CurrentInfo {
Mode mode;
CurrentState state;
State state;
CurrentShot shot;
CurrentProgram program;
CurrentMacro macro;
uint32_t startDelay;
} CurrentInfo;
void Robot_INIT();
void doShot(Shot*);
void shotApply(Shot*);
void doShotForever(uint8_t number);
void BallEXT();
void RobotTick();
uint8_t prepareShot(uint8_t number);
//uint8_t prepareProgramm(uint8_t number);
//uint8_t prepareMacro(uint8_t number);
void startShooting();
void startShooting(uint32_t delayTime);
void stopShooting();
int16_t map(int16_t x, int16_t in_min, int16_t in_max, int16_t out_min,
int16_t out_max);
long map(long x, long in_min, long in_max, long out_min, long out_max);
void setPos(uint8_t axial, uint8_t horizontal, uint8_t vertical);
void setPosSingle(ServoMap servo, uint8_t value);
void setPosFromShot(Shot* shot);
void setPosDefault();
void setPosDefaultSingle(ServoMap servo);
// 0 .. 100
void setScrewkSpeed(uint8_t speed);
//(-v) 0 .. 100(stop) .. 200(+v)
void setRollersSpeed(uint8_t up, uint8_t down); //(-v) 0 . 100(stop) . 200(+v)

View File

@ -10,6 +10,8 @@
#include "stm32f1xx_hal.h"
#define NUMLEDS 10
void SetShiftReg_inline (unsigned char b1, unsigned char b2, unsigned char b3);
void SetShiftReg (unsigned char shiftreg[3]);

View File

@ -49,7 +49,7 @@
#define HAL_I2C_MODULE_ENABLED
/*#define HAL_I2S_MODULE_ENABLED */
/*#define HAL_IRDA_MODULE_ENABLED */
/*#define HAL_IWDG_MODULE_ENABLED */
#define HAL_IWDG_MODULE_ENABLED
/*#define HAL_NOR_MODULE_ENABLED */
/*#define HAL_NAND_MODULE_ENABLED */
/*#define HAL_PCCARD_MODULE_ENABLED */

View File

@ -297,9 +297,9 @@ MemoryStatus FLASH_WriteBlock(uint16_t startAddr, uint8_t number,
result = HAL_I2C_Master_Transmit(&hi2c1, (AT24C_ADRESS << 1), Buf,
(dataSize + 2), 10);
print("Written ");
printNumber(dataSize);
print("bytes\n");
// print("Written ");
// printNumber(dataSize);
// print(" bytes\n");
HAL_Delay(1);
if (result != HAL_OK) {
return EEPROM_FAIL;

View File

@ -245,7 +245,7 @@ void IR_ShotPrepared() {
InputHandler = IR_ShotPrepared;
switch (data.command) {
case IR_START:
startShooting();
startShooting(infoBlock.hwInfo.timings.preRun);
break;
default:
InputHandler();

View File

@ -4,25 +4,154 @@
* Created on: Aug 28, 2024
* Author: DashyFox
*/
#include <math.h>
#include "RobotFunctions.h"
#include "pca9685.h"
#include "UART3_Handler.h"
#include "EEPROM.h"
#include "ShiftReg.h"
#include "Print.h"
#include "SimpleTimer.h"
uint8_t isPause = 0;
uint8_t isShooting = 0;
#define ballReact_value 10
CurrentInfo currentInfo;
extern int16_t Vz1;
extern int16_t Vz2;
unsigned char Shiftreg[3];
extern InfoBlock infoBlock;
uint8_t ballDetected = 0;
uint32_t ballReact_timer = 0;
uint8_t isDelayTimerRun = 0;
uint32_t startDelay_timer;
Shot* postDelayShot = NULL;
uint32_t lastIndicationTime = 0;
uint32_t noBallTimer = 0;
uint32_t noBallTimeout = 0xFFFFFFFF;
int16_t map(int16_t x, int16_t in_min, int16_t in_max, int16_t out_min,
int16_t out_max) {
void BallEXT_Handler();
void robotStateStart(uint32_t delayTime) {
currentInfo.state = PRERUN_WAIT;
currentInfo.startDelay = delayTime;
startDelay_timer = millis();
isDelayTimerRun = 1;
}
void robotStatePause() {
currentInfo.state = PAUSE;
}
void robotStateStop() {
currentInfo.state = STOP;
}
void BallEXT() {
ballDetected = 1;
ballReact_timer = millis();
}
// Функция для расчета периода вылета мяча на основе ШИМ
float calculatePeriod(int pwm_value) {
// Коэффициенты из аппроксимации
float a = 100382.255;
float b = 0.21895;
float c = 883.456;
// Расчет периода на основе экспоненциальной формулы
float period = a * expf(-b * pwm_value) + c;
return period;
}
void RobotTick() {
BallEXT_Handler();
// No Ball Handler
if(currentInfo.state == RUN && millis() - noBallTimer > noBallTimeout){
robotStateStop();
setScrewkSpeed(0);
setRollersSpeed(100, 100);
setPos(infoBlock.hwInfo.servos[SERVO_AXIAL].def,
infoBlock.hwInfo.servos[SERVO_HORIZONTAL].def,
infoBlock.hwInfo.servos[SERVO_VERTICAL].min);
print("NO BALL!!!");
}
// PreRun delay
if (isDelayTimerRun) {
uint32_t elapsedTime = millis() - startDelay_timer;
if (elapsedTime > currentInfo.startDelay) {
isDelayTimerRun = 0;
if (currentInfo.state == PRERUN_WAIT) {
currentInfo.state = RUN;
shotApply(postDelayShot);
}
} else {
uint32_t intervalStep = currentInfo.startDelay / NUMLEDS;
if (elapsedTime - lastIndicationTime >= intervalStep) {
lastIndicationTime = elapsedTime;
uint8_t progress = (elapsedTime * 100) / currentInfo.startDelay;
// indicate(progress);
print("delay: ");
printNumber(progress);
print("\n");
}
}
}
}
void BallEXT_Handler() {
if (ballDetected && millis() - ballReact_timer > ballReact_value) {
ballDetected = 0;
if (currentInfo.state != RUN) {
print("BallDetected on idle\n");
return;
}
print("BallDetected ");
uint16_t period = ballReact_timer - noBallTimer;
printNumber(period);
print("ms\n");
noBallTimer = ballReact_timer;
switch (currentInfo.mode) {
case NoneMode:
break;
case ShotMode:
if (currentInfo.shot.currentRepeatCount + 1
< currentInfo.shot.shot.countRepeatShot
|| !currentInfo.shot.shot.countRepeatShot) {
// nextRepeatCount
print("Shot ");
printNumber(currentInfo.shot.currentRepeatCount);
print("\n\n");
saveInfoBlock();
currentInfo.shot.currentRepeatCount++;
} else {
// shotDone
stopShooting();
print("Shot DONE\n");
}
infoBlock.statInfo.totalShots++;
break;
case ProgramMode:
break;
case MacroMode:
break;
default:
break;
}
}
}
long map(long x, long in_min, long in_max, long out_min, long out_max) {
return (x - in_min) * (out_max - out_min) / (in_max - in_min) + out_min;
}
void Robot_INIT() {
@ -96,16 +225,15 @@ void Robot_INIT() {
}
void doShot(Shot *shot) {
SetServo(0, shot->rotationHorizontal);
SetServo(1, shot->rotationVertical);
SetServo(2, shot->rotationAxial);
Vz1 = shot->speedRollerTop;
Vz2 = shot->speedRollerBottom;
void shotApply(Shot *shot) {
setPos(shot->rotationAxial, shot->rotationHorizontal,
shot->rotationVertical);
setRollersSpeed(shot->speedRollerTop, shot->speedRollerBottom);
setScrewkSpeed(shot->speedScrew);
noBallTimer = millis();
}
void startShooting() {
void startShooting(uint32_t delayTime) {
switch (currentInfo.mode) {
case ShotMode:
print("StartShooting\n");
@ -114,23 +242,27 @@ void startShooting() {
print("isExist ");
printNumber(currentInfo.shot.shot.isExist);
print("countRepeatShot; ");
print("\ncountRepeatShot; ");
printNumber(currentInfo.shot.shot.countRepeatShot);
print("speedRollerTop; ");
print("\nspeedRollerTop; ");
printNumber(currentInfo.shot.shot.speedRollerTop);
print("speedRollerBottom; ");
print("\nspeedRollerBottom; ");
printNumber(currentInfo.shot.shot.speedRollerBottom);
print("speedScrew; ");
print("\nspeedScrew; ");
printNumber(currentInfo.shot.shot.speedScrew);
print("rotationAxial; ");
print("\nrotationAxial; ");
printNumber(currentInfo.shot.shot.rotationAxial);
print("rotationHorizontal; ");
print("\nrotationHorizontal; ");
printNumber(currentInfo.shot.shot.rotationHorizontal);
print("rotationVertical; ");
print("\nrotationVertical; ");
printNumber(currentInfo.shot.shot.rotationVertical);
currentInfo.state.isShooting = 1;
doShot(&currentInfo.shot.shot);
print("\n\n");
postDelayShot = &currentInfo.shot.shot;
#if PRE_RUN_DELAY_MODE == 0
#elif PRE_RUN_DELAY_MODE == 1
setPosFromShot(postDelayShot);
#endif
robotStateStart(delayTime);
} else {
print("Current Shot is NULL\n");
// TODO: sound_ERR(); ledFX_ERR();
@ -148,24 +280,23 @@ void startShooting() {
}
void stopShooting() {
currentInfo.state.isPause = 0;
currentInfo.state.isShooting = 0;
robotStateStop();
setScrewkSpeed(0);
setRollersSpeed(100, 100);
setPosDefault();
}
void doShotForever(uint8_t number) {
}
uint8_t prepareShot(uint8_t number) {
Shot shot;
getShot(number, &shot);
if (shot.isExist) {
currentInfo.mode = ShotMode;
currentInfo.shot.shot = shot;
currentInfo.shot.currentRepeatCount = 0;
noBallTimeout = calculatePeriod(shot.speedScrew)*NOBALL_TIMEOUT_MULTIPLIER;
print("noBallTimeout: ");
printNumber(noBallTimeout);
print("\n");
return 1;
} else {
// TODO: sound_ERR(); ledFX_ERR();
@ -175,32 +306,35 @@ uint8_t prepareShot(uint8_t number) {
}
void setPosSingle(ServoMap servo, uint8_t value) {
ServoSetting* currentServo = &infoBlock.hwInfo.servos[servo];
uint8_t inv = currentServo->invert;
if (servo == SERVO_AXIAL)
inv = !inv;
ServoSetting *currentServo = &infoBlock.hwInfo.servos[servo];
uint8_t inv = currentServo->invert;
if (servo == SERVO_AXIAL)
inv = !inv;
if (inv)
value = 180 - value;
if (inv)
value = 180 - value;
if(value > 90){
value = map(value, 91, 180, currentServo->def, currentServo->max);
}else if(value < 90) {
value = map(value, 89, 0, currentServo->def, currentServo->min);
} else {
value = currentServo->def;
}
if (value > 90) {
value = map(value, 91, 180, currentServo->def, currentServo->max);
} else if (value < 90) {
value = map(value, 89, 0, currentServo->def, currentServo->min);
} else {
value = currentServo->def;
}
SetServo(servo, value);
SetServo(servo, value);
}
void setPos(uint8_t axial, uint8_t horizontal, uint8_t vertical) {
setPosSingle(SERVO_AXIAL, axial);
setPosSingle(SERVO_HORIZONTAL, horizontal);
setPosSingle(SERVO_VERTICAL, vertical);
}
void setPosFromShot(Shot* shot){
setPos(shot->rotationAxial, shot->rotationHorizontal, shot->rotationVertical);
}
void setPosDefault() {
setPos(infoBlock.hwInfo.servos[SERVO_AXIAL].def,
infoBlock.hwInfo.servos[SERVO_HORIZONTAL].def,

View File

@ -31,6 +31,7 @@ uint8_t checkLen(uint8_t cmd, uint8_t current_length, uint8_t required_length) {
return 1;
}
// 10
void UART3_SaveShot(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 8;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -44,9 +45,11 @@ void UART3_SaveShot(uint8_t *dataPtr, uint8_t len) {
shot.speedRollerTop = dataPtr[3] + 100;
shot.speedRollerBottom = dataPtr[4] + 100;
shot.speedScrew = map(dataPtr[5], 0, 120, 0, 100);
shot.rotationAxial = map(dataPtr[6], -99, 99, 0, 180);
shot.rotationHorizontal = map(dataPtr[7], -99, 99, 90 - 45, 90 + 45);
shot.rotationVertical = 180 - dataPtr[8];
shot.rotationAxial = map((int8_t)dataPtr[6], -99, 99, 0, 180);
shot.rotationHorizontal = map((int8_t)dataPtr[7], -99, 99, 0, 180);
shot.rotationVertical = 180 - (int8_t)dataPtr[8] - 90;
saveShot(shotIndx, &shot);
@ -106,6 +109,7 @@ void UART3_SaveMacro(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, NULL, 0);
}
void UART3_StartMacro(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 0;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -122,6 +126,7 @@ void UART3_StartProgram(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, NULL, 0);
}
// 102
void UART3_StartShot(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 1;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -129,19 +134,23 @@ void UART3_StartShot(uint8_t *dataPtr, uint8_t len) {
uint8_t shotIndx = dataPtr[1];
prepareShot(shotIndx);
startShooting();
startShooting(infoBlock.hwInfo.timings.preRun);
SendResponse(dataPtr[0], 0, NULL, 0);
}
// 110
void UART3_Stop(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 0;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
return;
stopShooting();
SendResponse(dataPtr[0], 0, NULL, 0);
}
// 13
void UART3_DeleteShot(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 1;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -153,6 +162,7 @@ void UART3_DeleteShot(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, NULL, 0);
}
// 14
void UART3_DeleteProgram(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 0;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -164,6 +174,7 @@ void UART3_DeleteProgram(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, NULL, 0);
}
// 15
void UART3_DeleteMacro(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 0;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -175,7 +186,7 @@ void UART3_DeleteMacro(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, NULL, 0);
}
//120
// 120
void UART3_DeleteAllData(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 0;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -189,41 +200,45 @@ void UART3_DeleteAllData(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, NULL, 0);
}
//180
// 180
void UART3_GetDeviceStatus(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 0;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
return;
uint8_t res = currentInfo.state.isShooting;
uint8_t res = currentInfo.state == RUN;
SendResponse(dataPtr[0], 0, &res, sizeof(res));
}
//200
// 200
void UART3_SetServoOffset(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 3;
const uint8_t MIN_PARAM_LENGTH = 2;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
return;
ServoMap servo = dataPtr[1];
ServoSetting *currentServo = &infoBlock.hwInfo.servos[servo];
int16_t newDef = (dataPtr[2] << 8) | dataPtr[3];
uint8_t newDef = dataPtr[2];
printNumber(newDef);
print("\n");
newDef += 90; // from center
if (newDef < 0)
newDef = 0;
if (newDef > 180)
newDef = 180;
currentServo->def = newDef;
printNumber(newDef);
print("\n");
saveInfoBlock();
SendResponse(dataPtr[0], 0, NULL, 0);
}
//204
// 205
void UART3_GetServoOffset(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 1;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -240,7 +255,7 @@ void UART3_GetServoOffset(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, res, sizeof(res));
}
//201
// 201
void UART3_SetServoMaxAngle(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 3;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -260,6 +275,26 @@ void UART3_SetServoMaxAngle(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, NULL, 0);
}
// 202
void UART3_SetServoMinAngle(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 3;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
return;
ServoMap servo = dataPtr[1];
uint16_t minAngl = (dataPtr[2] << 8) | dataPtr[3];
ServoSetting *currentServo = &infoBlock.hwInfo.servos[servo];
if (minAngl > 180)
minAngl = 180;
if (minAngl < 0)
minAngl = 0;
currentServo->min = minAngl;
saveInfoBlock();
SendResponse(dataPtr[0], 0, NULL, 0);
}
void UART3_GetServoMaxAngle(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 1;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -276,26 +311,6 @@ void UART3_GetServoMaxAngle(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, res, sizeof(res));
}
//202
void UART3_SetServoMinAngle(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 3;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
return;
ServoMap servo = dataPtr[1];
uint16_t minAngl = (dataPtr[2] << 8) | dataPtr[3];
ServoSetting *currentServo = &infoBlock.hwInfo.servos[servo];
if (minAngl > 180)
minAngl = 180;
if (minAngl < 0)
minAngl = 0;
currentServo->min = minAngl;
saveInfoBlock();
SendResponse(dataPtr[0], 0, NULL, 0);
}
void UART3_GetServoMinAngle(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 1;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -312,7 +327,7 @@ void UART3_GetServoMinAngle(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, res, sizeof(res));
}
//203
// 203
void UART3_MoveServoToInitialPosition(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 1;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -323,7 +338,7 @@ void UART3_MoveServoToInitialPosition(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, NULL, 0);
}
//206
// 206
void UART3_SetStartupDelay(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 2;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -335,7 +350,7 @@ void UART3_SetStartupDelay(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, NULL, 0);
}
//207
// 207
void UART3_GetStartupDelay(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 0;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -349,7 +364,7 @@ void UART3_GetStartupDelay(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, res, sizeof(res));
}
//210 !!!!!!!!
// 210 !!!!!!!!
void UART3_SetMinRollerSpeed(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 0;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -358,7 +373,7 @@ void UART3_SetMinRollerSpeed(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, NULL, 0);
}
//211 !!!!!!!!!!!
// 211 !!!!!!!!!!!
void UART3_GetMinRollerSpeed(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 0;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -370,7 +385,7 @@ void UART3_GetMinRollerSpeed(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, res, sizeof(res));
}
//212
// 212
void UART3_SetMinScrewSpeed(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 1;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -382,7 +397,7 @@ void UART3_SetMinScrewSpeed(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, NULL, 0);
}
//215
// 215
void UART3_GetMinScrewSpeed(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 0;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -394,7 +409,7 @@ void UART3_GetMinScrewSpeed(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, res, sizeof(res));
}
//214
// 214
void UART3_SetServoInvertFlag(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 1;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -411,7 +426,7 @@ void UART3_SetServoInvertFlag(uint8_t *dataPtr, uint8_t len) {
SendResponse(dataPtr[0], 0, NULL, 0);
}
//215
// 215
void UART3_GetServoInvertFlag(uint8_t *dataPtr, uint8_t len) {
const uint8_t MIN_PARAM_LENGTH = 0;
if (!checkLen(dataPtr[0], len, MIN_PARAM_LENGTH))
@ -447,7 +462,7 @@ void UART3_ReadStatistics(uint8_t *dataPtr, uint8_t len) {
StatusStruct res;
res.status = currentInfo.state.isShooting;
res.status = currentInfo.state == RUN;
res.shot_number = currentInfo.shot.index;
res.program_number = currentInfo.program.index;
res.macro_number = currentInfo.macro.index;

View File

@ -18,14 +18,12 @@ extern UART_HandleTypeDef huart3;
void UART3_CMD_Handler(uint8_t *dataPtr, uint8_t len);
void UART3_START() {
HAL_UART_Receive_DMA(&huart3, uart_rx_buffer, UART_BUFFER_SIZE);
}
volatile uint32_t last_rx_time = 0;
volatile uint32_t rx_complete_timeout = 10;
volatile uint32_t rx_complete_timeout = 15;
volatile uint32_t old_pos = 0;
volatile uint16_t rx_index = 0;
extern DMA_HandleTypeDef hdma_usart3_rx;
@ -123,12 +121,56 @@ void process_uart_data(uint32_t old_pos, uint32_t new_pos)
handle_rx_data(&uart_rx_buffer[0], new_pos);
}
}
volatile uint8_t rx_in_progress = 0;
void check_uart3_timeout(void)
{
void HAL_UART_ErrorCallback(UART_HandleTypeDef *huart)
{
if (huart->Instance == USART3)
{
char error_msg[128];
// Логгирование состояния до перезапуска
snprintf(error_msg, sizeof(error_msg),
"UART3 Error Detected: Code = 0x%02X, DMA Counter = %lu\n",
huart->ErrorCode, __HAL_DMA_GET_COUNTER(&hdma_usart3_rx));
CDC_Transmit_FS((uint8_t*) error_msg, strlen(error_msg));
// Останавливаем UART и DMA
HAL_UART_DMAStop(huart);
// Очищаем флаги всех возможных ошибок
__HAL_UART_CLEAR_FEFLAG(huart); // Сброс ошибки кадра
__HAL_UART_CLEAR_PEFLAG(huart); // Сброс ошибки четности
__HAL_UART_CLEAR_NEFLAG(huart); // Сброс ошибки шума
__HAL_UART_CLEAR_OREFLAG(huart); // Сброс ошибки переполнения
// Проверка, не повторяется ли ошибка через несколько циклов
static int error_count = 0;
error_count++;
if (error_count > 1)
{
NVIC_SystemReset(); // Полный перезапуск системы после n ошибок
}
// Деинициализация и повторная инициализация UART
HAL_UART_DeInit(huart);
HAL_UART_Init(huart);
// Перезапуск DMA
HAL_UART_Receive_DMA(huart, uart_rx_buffer, UART_BUFFER_SIZE);
// Логгирование состояния после перезапуска
snprintf(error_msg, sizeof(error_msg),
"UART3 DMA reception restarted: DMA Counter = %lu\n",
__HAL_DMA_GET_COUNTER(&hdma_usart3_rx));
CDC_Transmit_FS((uint8_t*) error_msg, strlen(error_msg));
}
}
uint8_t rx_in_progress = 0;
void UART3_Handler() {
uint32_t pos = UART_BUFFER_SIZE - __HAL_DMA_GET_COUNTER(&hdma_usart3_rx);
@ -243,9 +285,6 @@ void UART3_CMD_Handler(uint8_t *dataPtr, uint8_t len) {
case 200:
UART3_SetServoOffset(dataPtr, len);
break;
case 204:
UART3_GetServoOffset(dataPtr, len);
break;
case 201:
UART3_SetServoMaxAngle(dataPtr, len);
break;
@ -255,6 +294,12 @@ void UART3_CMD_Handler(uint8_t *dataPtr, uint8_t len) {
case 203:
UART3_MoveServoToInitialPosition(dataPtr, len);
break;
// case 204:
// UART3_GetServoOffset(dataPtr, len);
// break;
case 205:
UART3_GetServoOffset(dataPtr, len);
break;
case 206:
UART3_SetStartupDelay(dataPtr, len);
break;

View File

@ -53,6 +53,8 @@
/* Private variables ---------------------------------------------------------*/
I2C_HandleTypeDef hi2c1;
IWDG_HandleTypeDef hiwdg;
TIM_HandleTypeDef htim1;
TIM_HandleTypeDef htim2;
TIM_HandleTypeDef htim3;
@ -93,6 +95,7 @@ static void MX_TIM1_Init(void);
static void MX_TIM2_Init(void);
static void MX_TIM3_Init(void);
static void MX_USART3_UART_Init(void);
static void MX_IWDG_Init(void);
/* USER CODE BEGIN PFP */
/* USER CODE END PFP */
@ -143,6 +146,7 @@ int main(void) {
MX_TIM2_Init();
MX_TIM3_Init();
MX_USART3_UART_Init();
MX_IWDG_Init();
/* USER CODE BEGIN 2 */
__HAL_RCC_USART3_CLK_ENABLE();
@ -174,9 +178,9 @@ int main(void) {
IR_CMD_Handler();
UART3_Handler();
RobotTick();
forTimer(blinkTimer, 500)
{
forTimer(blinkTimer, 500) {
resetForTimer(blinkTimer);
GPIOC->ODR ^= GPIO_PIN_13;
// unsigned char text[] = "Hello\n";
@ -201,6 +205,7 @@ int main(void) {
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
HAL_IWDG_Refresh(&hiwdg);
}
/* USER CODE END 3 */
}
@ -217,10 +222,12 @@ void SystemClock_Config(void) {
/** Initializes the RCC Oscillators according to the specified parameters
* in the RCC_OscInitTypeDef structure.
*/
RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSE;
RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_LSI
| RCC_OSCILLATORTYPE_HSE;
RCC_OscInitStruct.HSEState = RCC_HSE_ON;
RCC_OscInitStruct.HSEPredivValue = RCC_HSE_PREDIV_DIV1;
RCC_OscInitStruct.HSIState = RCC_HSI_ON;
RCC_OscInitStruct.LSIState = RCC_LSI_ON;
RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSE;
RCC_OscInitStruct.PLL.PLLMUL = RCC_PLL_MUL6;
@ -279,6 +286,32 @@ static void MX_I2C1_Init(void) {
}
/**
* @brief IWDG Initialization Function
* @param None
* @retval None
*/
static void MX_IWDG_Init(void) {
/* USER CODE BEGIN IWDG_Init 0 */
/* USER CODE END IWDG_Init 0 */
/* USER CODE BEGIN IWDG_Init 1 */
/* USER CODE END IWDG_Init 1 */
hiwdg.Instance = IWDG;
hiwdg.Init.Prescaler = IWDG_PRESCALER_64;
hiwdg.Init.Reload = 625 * 5;
if (HAL_IWDG_Init(&hiwdg) != HAL_OK) {
Error_Handler();
}
/* USER CODE BEGIN IWDG_Init 2 */
/* USER CODE END IWDG_Init 2 */
}
/**
* @brief TIM1 Initialization Function
* @param None

View File

@ -31,7 +31,8 @@
#include "Print.h"
#include "UART3_Handler.h"
#include "SimpleTimer.h"
#include "RobotFunctions.h"
/* USER CODE END Includes */
/* Private typedef -----------------------------------------------------------*/
@ -469,22 +470,9 @@ void SysTick_Handler(void)
void EXTI0_IRQHandler(void)
{
/* USER CODE BEGIN EXTI0_IRQn 0 */
// if (avto == 1)
// {
// if (rejim_number < rejim[0])
// rejim_number++;
// else
// rejim_number = 1;
//
// SetServo(0, rejim[1 + (rejim_number - 1) * 6]);
// SetServo(1, rejim[2 + (rejim_number - 1) * 6]);
// SetServo(2, rejim[3 + (rejim_number - 1) * 6]);
// Vz1 = rejim[4 + (rejim_number - 1) * 6];
// Vz2 = rejim[5 + (rejim_number - 1) * 6];
// TIM1->CCR1 = 0;
// TIM1->CCR2 = (uint16_t)(40 * rejim[6 + (rejim_number - 1) * 6]);
// vi = 0; // zapis grafika start
// }
BallEXT();
/* USER CODE END EXTI0_IRQn 0 */
HAL_GPIO_EXTI_IRQHandler(BALL_EXT_Pin);
/* USER CODE BEGIN EXTI0_IRQn 1 */

View File

@ -15,21 +15,25 @@ Dma.USART3_RX.0.Priority=DMA_PRIORITY_HIGH
Dma.USART3_RX.0.RequestParameters=Instance,Direction,PeriphInc,MemInc,PeriphDataAlignment,MemDataAlignment,Mode,Priority
File.Version=6
GPIO.groupedBy=Group By Peripherals
IWDG.IPParameters=Prescaler,Reload
IWDG.Prescaler=IWDG_PRESCALER_64
IWDG.Reload=625*5
KeepUserPlacement=false
Mcu.CPN=STM32F103C8T6
Mcu.Family=STM32F1
Mcu.IP0=DMA
Mcu.IP1=I2C1
Mcu.IP10=USB_DEVICE
Mcu.IP2=NVIC
Mcu.IP3=RCC
Mcu.IP4=SYS
Mcu.IP5=TIM1
Mcu.IP6=TIM2
Mcu.IP7=TIM3
Mcu.IP8=USART3
Mcu.IP9=USB
Mcu.IPNb=11
Mcu.IP10=USB
Mcu.IP11=USB_DEVICE
Mcu.IP2=IWDG
Mcu.IP3=NVIC
Mcu.IP4=RCC
Mcu.IP5=SYS
Mcu.IP6=TIM1
Mcu.IP7=TIM2
Mcu.IP8=TIM3
Mcu.IP9=USART3
Mcu.IPNb=12
Mcu.Name=STM32F103C(8-B)Tx
Mcu.Package=LQFP48
Mcu.Pin0=PC13-TAMPER-RTC
@ -48,11 +52,12 @@ Mcu.Pin2=PD1-OSC_OUT
Mcu.Pin20=PA14
Mcu.Pin21=PB6
Mcu.Pin22=PB7
Mcu.Pin23=VP_SYS_VS_Systick
Mcu.Pin24=VP_TIM1_VS_ClockSourceINT
Mcu.Pin25=VP_TIM2_VS_ClockSourceINT
Mcu.Pin26=VP_TIM3_VS_ClockSourceINT
Mcu.Pin27=VP_USB_DEVICE_VS_USB_DEVICE_CDC_FS
Mcu.Pin23=VP_IWDG_VS_IWDG
Mcu.Pin24=VP_SYS_VS_Systick
Mcu.Pin25=VP_TIM1_VS_ClockSourceINT
Mcu.Pin26=VP_TIM2_VS_ClockSourceINT
Mcu.Pin27=VP_TIM3_VS_ClockSourceINT
Mcu.Pin28=VP_USB_DEVICE_VS_USB_DEVICE_CDC_FS
Mcu.Pin3=PA0-WKUP
Mcu.Pin4=PA1
Mcu.Pin5=PA2
@ -60,7 +65,7 @@ Mcu.Pin6=PA3
Mcu.Pin7=PA4
Mcu.Pin8=PA5
Mcu.Pin9=PA6
Mcu.PinsNb=28
Mcu.PinsNb=29
Mcu.ThirdPartyNb=0
Mcu.UserConstants=
Mcu.UserName=STM32F103C8Tx
@ -266,6 +271,8 @@ USB_DEVICE.IPParameters=VirtualMode,VirtualModeFS,CLASS_NAME_FS,APP_RX_DATA_SIZE
USB_DEVICE.MANUFACTURER_STRING=StackSport
USB_DEVICE.VirtualMode=Cdc
USB_DEVICE.VirtualModeFS=Cdc_FS
VP_IWDG_VS_IWDG.Mode=IWDG_Activate
VP_IWDG_VS_IWDG.Signal=IWDG_VS_IWDG
VP_SYS_VS_Systick.Mode=SysTick
VP_SYS_VS_Systick.Signal=SYS_VS_Systick
VP_TIM1_VS_ClockSourceINT.Mode=Internal