/**** Includes ****/ #include "hal/udccd_hal.h" #include "halfbridge.h" /**** Private variables ****/ static const uint16_t min_dc = 3277; //5% static const uint16_t max_dc = 62258; //95% static uint16_t target = 0; static uint8_t low_side_on = 1; static uint16_t active_dc = 0; static uint8_t is_en = 0; /**** Private function declarations ****/ static uint16_t CalculateDuty16b(uint16_t target, uint16_t supply); /**** Public function definitions ****/ void HB_SetTarget(uint16_t voltage) { target = voltage; } void HB_SetLowSide(uint8_t on) { low_side_on = on; } uint16_t HB_GetTarget(void) { return target; } void HB_UpdateOutput(uint16_t supply) { uint16_t temp_dc = CalculateDuty16b(target, supply); HB_SetDirect(temp_dc); } void HB_SetDirect(uint16_t duty) { /// Limit duty cycle if(duty > max_dc) active_dc = max_dc; else if(duty < min_dc) active_dc = 0; else active_dc = duty; // Set duty cycle if(!is_en) return; HAL_Coil_SetLowSide(low_side_on); HAL_Coil_SetPWM16b(active_dc); } uint8_t HB_IsLowOn(void) { if(HAL_ReadLvl_CoilLow() == HIGH) return 1; else return 0; } void HB_Enable(void) { // Restore low side if(low_side_on) HAL_Coil_SetLowSide(1); // Restore duty cycle HAL_Coil_SetPWM(active_dc); is_en = 1; } void HB_Disable(void) { // Set 0 DC HAL_Coil_SetPWM(0); // Disable low side HAL_Coil_SetLowSide(0); is_en = 0; } uint8_t HB_IsEnabled(void) { if(is_en) return 1; else return 0; } int8_t HB_IsOutputMatch(uint16_t fb_output_voltage, uint16_t limit) { // No fault if output not enabled if(!is_en) return -1; // Can't check voltage if low side is off if(!low_side_on) return -1; if(target==0) { // Output can be only 0 if(fb_output_voltage != 0) return 0; else return 1; }; // Calculate upper and lower bounds uint16_t max = target + limit; uint16_t min = target - limit; //Sanity check if(max < target) max = 0xFFFF; if(min > target) min = 0; //Do check if((fb_output_voltage < min)||(fb_output_voltage > max)) return 0; else return 1; } /**** Private function definitions ****/ static uint16_t CalculateDuty16b(uint16_t target, uint16_t supply) { if(target==0) return 0; if(supply==0) return 0; if(target > supply) return 0xFFFF; // Calculate Duty cycle, in 16bit format uint32_t temp = (uint32_t)target * 0x0000FFFF; temp = temp / supply; //Limit output to 16 bits if(temp > 0x0000FFFF) return 0xFFFF; else return (uint16_t)temp; }