diff --git a/Core/Src/AMS_HighLevel.c b/Core/Src/AMS_HighLevel.c index ce6ea28..464ef85 100755 --- a/Core/Src/AMS_HighLevel.c +++ b/Core/Src/AMS_HighLevel.c @@ -6,6 +6,7 @@ */ #include "AMS_HighLevel.h" +#include "ADBMS_Abstraction.h" #include "ADBMS_LL_Driver.h" #include @@ -169,10 +170,7 @@ uint8_t AMS_Idle_Loop() { mcuDelay(10); - if ((module.overVoltage | module.underVoltage)) { - - } - + AMS_Balancing_Loop(); return 0; } @@ -185,9 +183,9 @@ uint8_t AMS_Charging_Loop() { return 0; } uint8_t AMS_Discharging_Loop() { return 0; } uint8_t AMS_Balancing_Loop() { - AMS_Idle_Loop(); uint8_t id_cell_lowest_voltage = 0; uint8_t num_of_cells_to_balance = 0; + uint32_t channels = 0; for (int i = 0; i < 13; i++) { if (module.cellVoltages[i] < module.cellVoltages[id_cell_lowest_voltage]) id_cell_lowest_voltage = i; @@ -195,18 +193,17 @@ uint8_t AMS_Balancing_Loop() { for (int i = 0; i < 13; i++) { if (module.cellVoltages[i] - CELL_VOLTAGE_DIFF_BALANCING < module.cellVoltages[id_cell_lowest_voltage]){ - amsConfigBalancing((1 << i), 0xF); + channels |= 1 << i; num_of_cells_to_balance++; - } else { - amsConfigBalancing((1 << i), 0x0); } } + if (num_of_cells_to_balance == 0){ balancingActive = 0; return 0; } + amsConfigBalancing(channels, 0xF); balancingActive = 1; - amsStartBalancing(0); return 0; } diff --git a/Core/Src/can.c b/Core/Src/can.c index 4240421..32e8d29 100644 --- a/Core/Src/can.c +++ b/Core/Src/can.c @@ -19,7 +19,7 @@ #define CAN_ID_IN 0x501 #define CAN_ID_OUT 0x502 -#define CAN_ID_LOG 0x503 +#define CAN_ID_LOG 0x503 // Every X ms, send message #define CAN_STATUS_FREQ 1000 @@ -93,14 +93,14 @@ void can_handle_send_status() { uint16_t highest_temp = 0; sm_check_battery_temperature(&id_highest_temp, &highest_temp); - data[0] = ((state.current_state << 4) | (current_powerground_status >> 4)); // 1 bit emptyy | 3 bit state | 4 bit powerground - data[1] = ((current_powerground_status << 4) | (state.error_source >> 4)); // 4 bit powerground | 4 bit error - data[2] = ((state.error_source << 4)); // 4 bit error | 4 bit state of charge - data[3] = ((int) current_soc); // 8 bit state of charge - data[4] = (roundf(RELAY_BAT_SIDE_VOLTAGE / 1000.0)); // 8 bit battery voltage - data[5] = (roundf(RELAY_ESC_SIDE_VOLTAGE / 1000.0)); // 8 bit Inverter voltage - data[6] = (roundf(CURRENT_MEASUREMENT / 1000.0)); // 8 bit Current - data[7] = ((highest_temp) >> 4); // 8 bit highest cell temperature + data[0] = (state.current_state); // 8 bit state (only 3 are use) + data[1] = (current_powerground_status); // 8 bit powerground + data[2] = (state.error_source); // 8 bit error + data[3] = ((int) current_soc); // 8 bit state of charge + data[4] = (roundf(RELAY_BAT_SIDE_VOLTAGE / 1000.0)); // 8 bit battery voltage + data[5] = (roundf(RELAY_ESC_SIDE_VOLTAGE / 1000.0)); // 8 bit Inverter voltage + data[6] = (roundf(CURRENT_MEASUREMENT / 1000.0)); // 8 bit Current + data[7] = ((highest_temp) >> 4); // 8 bit highest cell temperature //data[7] = state.error_source; ftcan_transmit(CAN_ID_OUT, data, sizeof(data)); } @@ -110,7 +110,7 @@ void can_handle_send_log(){ if (can_log_timer > HAL_GetTick()) return; else { - uint8_t data[8] = {}; + uint8_t data[4] = {}; can_log_timer = HAL_GetTick() + CAN_LOGGING_FREQ; data[0] = id_to_log; data[1] = module.cellVoltages[id_to_log] >> 8; @@ -140,7 +140,7 @@ This function recieves a command from the Autobox with the CAN ID of 0x501. with format of: data[0] = target state 0x00 STATE_INACTIVE | disconnect power to the ESC of powerground. Send it to return the mvbms to idle/monitoring mode. If data[1] != 0 -> assume bad CAN message. - 0x01 STATE_READY | conneect power to the ESC of powerground and but with no PWM signal. If data[1] != 0 -> assume bad CAN message. + 0x01 STATE_READY | connect power to the ESC of powerground and but with no PWM signal. If data[1] != 0 -> assume bad CAN message. 0x02 STATE_ACTIVE | activate powerground at (data[1]) percent. If data[1] > 100 -> assume bad CAN message. allowed transitions: @@ -149,7 +149,7 @@ allowed transitions: STATE_ACTIVE -> STATE_INACTIVE, STATE_READY */ void can_handle_recieve_command(const uint8_t *data){ - if (data[0] == 0x00 && data[1] == 0x00){ + if (data[0] == 0x00){ sm_handle_ams_in(data); } else if (data[0] == 0x01 && data[1] == 0x00){ sm_handle_ams_in(data); @@ -159,10 +159,6 @@ void can_handle_recieve_command(const uint8_t *data){ sm_handle_ams_in(data); } else if (data[0] == 0xF1 && data[1] == 0x00) { sm_handle_ams_in(data); - } else if (data[0] == 0xF2 && data[1] == 0x00) { - sm_handle_ams_in(data); - } else if (data[0] == 0xFA && data[1] == 0x00) { - sm_handle_ams_in(data); } else if (data[0] == 0xFF && data[1] == 0x00) { sm_handle_ams_in(data); } diff --git a/Core/Src/state_machine.c b/Core/Src/state_machine.c index 55d4e34..902f9d4 100644 --- a/Core/Src/state_machine.c +++ b/Core/Src/state_machine.c @@ -7,6 +7,7 @@ #include #include +#include "ADBMS_Abstraction.h" #include "AMS_HighLevel.h" #include "PWM_control.h" #include "can.h" @@ -48,11 +49,13 @@ int32_t RELAY_BAT_SIDE_VOLTAGE; int32_t RELAY_ESC_SIDE_VOLTAGE; int32_t CURRENT_MEASUREMENT; bool CURRENT_MEASUREMENT_ON; +bool balancing_state; float base_offset = 0; uint32_t error_timer; uint32_t precharge_timer; uint32_t discharge_timer; +uint32_t balancing_timer; uint32_t eeprom_timer; uint32_t powerground_softstart_timer; @@ -68,9 +71,10 @@ void sm_init(){ state.current_state = STATE_INACTIVE; state.target_state = STATE_INACTIVE; state.error_source = 0; - precharge_timer = discharge_timer = powerground_calibration_timer = error_timer = eeprom_timer = 0; + precharge_timer = discharge_timer = powerground_calibration_timer = error_timer = eeprom_timer = balancing_timer = 0; programming_mode = 0; debugging_mode = 0; + balancing_state = 0; } void sm_update(){ @@ -93,6 +97,7 @@ void sm_update(){ sm_check_errors(); sm_precharge_discharge_manager(); //sm_calibrate_powerground(); + sm_balancing(); sm_powerground_manager(); tmp1075_measure(); status_led_update(); @@ -248,6 +253,44 @@ void sm_calibrate_powerground(){ } } +void sm_balancing(){ + if (balancing_timer < HAL_GetTick()){ + if (balancing_state){ + balancing_timer = HAL_GetTick() + 10000; + + uint8_t id_cell_lowest_voltage = 0; + uint8_t num_of_cells_to_balance = 0; + uint32_t channels = 0; + + for (int i = 0; i < 13; i++) { + if (module.cellVoltages[i] < module.cellVoltages[id_cell_lowest_voltage]) + id_cell_lowest_voltage = i; + } + + for (int i = 0; i < 13; i++) { + if (module.cellVoltages[i] - 20 < module.cellVoltages[id_cell_lowest_voltage]){ + channels |= 1 << i; + num_of_cells_to_balance++; + } + } + + if (num_of_cells_to_balance == 0){ + amsStopBalancing(); + balancing_state = 0; + return; + } + + amsConfigBalancing(channels, 0xF); + amsStartBalancing(0xF); + balancing_state = 1; + } else { + balancing_timer = HAL_GetTick() + 1000; + balancing_state = 0; + amsStopBalancing(); + } + } +} + void sm_program_powerground(){ if (programming_mode == 0) return;