Changeset 26 for trunk/firmware/Src


Ignore:
Timestamp:
Sep 8, 2025, 6:57:30 PM (7 weeks ago)
Author:
f.jahn
Message:
  • Bug in ADC Kalibrierung (STM32 ADC Strom) behoben
  • DMA Buffer für ADC 1 und ADC wird vor Überschreibung während bearbeitung geschützt, indem Datenübertragung nur einmalig erfolgt und erst nach Auswertung wieder gestartet wird
  • RS485Modbus: Timeout Zeit wird für Baudraten >19200 korrekt berechnet
  • Hardware ID geändert
  • Separates Register für "Batterie Empty detection mode" auf Adresse 92 angelegt
Location:
trunk/firmware/Src
Files:
10 edited

Legend:

Unmodified
Added
Removed
  • trunk/firmware/Src/adc.c

    r6 r26  
    3636  */
    3737  hadc1.Instance = ADC1;
    38   hadc1.Init.ClockPrescaler = LL_ADC_CLOCK_SYNC_PCLK_DIV4;
     38  hadc1.Init.ClockPrescaler = ADC_CLOCK_SYNC_PCLK_DIV4;
    3939  hadc1.Init.Resolution = ADC_RESOLUTION_12B;
    4040  hadc1.Init.DataAlign = ADC_DATAALIGN_RIGHT;
    41   hadc1.Init.ScanConvMode = ADC_SCAN_ENABLE;
     41  hadc1.Init.ScanConvMode = ADC_SCAN_SEQ_FIXED; //More channnels
    4242  hadc1.Init.EOCSelection = ADC_EOC_SEQ_CONV;
    4343  hadc1.Init.LowPowerAutoWait = DISABLE;
    4444  hadc1.Init.LowPowerAutoPowerOff = DISABLE;
    4545  hadc1.Init.ContinuousConvMode = ENABLE;
    46   hadc1.Init.NbrOfConversion = 8;
     46  hadc1.Init.NbrOfConversion = 1;
    4747  hadc1.Init.DiscontinuousConvMode = DISABLE;
    4848  hadc1.Init.ExternalTrigConv = ADC_SOFTWARE_START;
    4949  hadc1.Init.ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE;
    5050  hadc1.Init.DMAContinuousRequests = ENABLE;
    51   hadc1.Init.Overrun = ADC_OVR_DATA_OVERWRITTEN;
    52   hadc1.Init.SamplingTimeCommon1 = ADC_SAMPLETIME_160CYCLES_5;
     51  hadc1.Init.Overrun = ADC_OVR_DATA_PRESERVED;
     52  hadc1.Init.SamplingTimeCommon1 = ADC_SAMPLETIME_160CYCLES_5; //bei79,5 ist das gezappelt in der fast voltage eindeutig höher
    5353  hadc1.Init.SamplingTimeCommon2 = ADC_SAMPLETIME_160CYCLES_5;
    5454  hadc1.Init.OversamplingMode = ENABLE;
     
    6565  //Messung Common Mode Voltage (Shunt Spannung - gegen Batterie Minus)
    6666  sConfig.Channel = ADC_CHANNEL_0;
    67   sConfig.Rank = ADC_REGULAR_RANK_1;
     67  sConfig.Rank = ADC_RANK_CHANNEL_NUMBER;
    6868  sConfig.SamplingTime = ADC_SAMPLINGTIME_COMMON_1;
    6969  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
     
    7575  //Messung Batteriespannung Plus
    7676  sConfig.Channel = ADC_CHANNEL_1;
    77   sConfig.Rank = ADC_REGULAR_RANK_2;
    78   sConfig.SamplingTime = ADC_SAMPLINGTIME_COMMON_1;
    7977  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
    8078  {
     
    8583  //Messung Neu : Vref
    8684  sConfig.Channel = ADC_CHANNEL_2;
    87   sConfig.Rank = ADC_REGULAR_RANK_3;
    88   sConfig.SamplingTime = ADC_SAMPLINGTIME_COMMON_1;
    8985  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
    9086  {
     
    9490  //Fast current Plus
    9591  sConfig.Channel = ADC_CHANNEL_3;
    96   sConfig.Rank = ADC_REGULAR_RANK_4;
    97   sConfig.SamplingTime = ADC_SAMPLINGTIME_COMMON_1;
    9892  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
    9993  {
     
    10397  //Fast current Minus
    10498  sConfig.Channel = ADC_CHANNEL_4;
    105   sConfig.Rank = ADC_REGULAR_RANK_5;
    106   sConfig.SamplingTime = ADC_SAMPLINGTIME_COMMON_1;
    107   if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
    108   {
    109     Error_Handler();
    110   }
     99  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
     100  {
     101    Error_Handler();
     102  }
     103
     104
     105  sConfig.Channel = ADC_CHANNEL_TEMPSENSOR;
     106  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
     107  {
     108    Error_Handler();
     109  }
     110
    111111
    112112
     
    115115  //ovp sense
    116116  sConfig.Channel = ADC_CHANNEL_8;
    117   sConfig.Rank = ADC_REGULAR_RANK_6;
    118   sConfig.SamplingTime = ADC_SAMPLINGTIME_COMMON_2;
    119117  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
    120118  {
     
    124122  //lvp sense
    125123  sConfig.Channel = ADC_CHANNEL_9;
    126   sConfig.Rank = ADC_REGULAR_RANK_7;
    127   sConfig.SamplingTime = ADC_SAMPLINGTIME_COMMON_2;
    128   if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
    129   {
    130     Error_Handler();
    131   }
    132 
     124  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
     125  {
     126    Error_Handler();
     127  }
    133128
    134129  //Temp Meas
    135130  sConfig.Channel = ADC_CHANNEL_10;
    136   sConfig.Rank = ADC_REGULAR_RANK_8;
    137   sConfig.SamplingTime = ADC_SAMPLINGTIME_COMMON_1;
    138   if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
    139   {
    140     Error_Handler();
    141   }
    142 
    143 
    144 
    145 
     131  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
     132  {
     133    Error_Handler();
     134  }
    146135}
    147136
  • trunk/firmware/Src/battery_voltage.c

    r6 r26  
    5353
    5454  //Umrechung auf Eingangsspannung am Gerät mit Teiler
    55   sys_data.s.values.batteryVoltage = (avgvalP * (uint64_t)sys_data.s.values.realVdd * BATTERY_VOLTAGE_VOLTAGE_DIVIDER ) / 655360.0;
     55  sys_data.s.values.batteryVoltage = (avgvalP * (uint64_t)sys_data.s.values.realVdd * BATTERY_VOLTAGE_VOLTAGE_DIVIDER ) / 65536;
    5656
    5757 
     
    7575  //Berechnung schnellen Wert ohne Glättung:
    7676  //Umrechung auf Eingangsspannung am Gerät mit Teiler
    77   sys_data.s.values.fast_voltage = (newvalP * (uint64_t)sys_data.s.values.realVdd * BATTERY_VOLTAGE_VOLTAGE_DIVIDER ) / 655360.0;
     77  sys_data.s.values.fast_voltage = (newvalP * (uint64_t)sys_data.s.values.realVdd * BATTERY_VOLTAGE_VOLTAGE_DIVIDER ) / 65536;
    7878
    7979
  • trunk/firmware/Src/eeprom.c

    r6 r26  
    4848  int32_t         detectedCapacity;
    4949  int32_t         detectedEnergy;
    50   //int32_t       mAh_AutoMode;
    51   //int32_t       mWh_AutoMode;
    5250  int64_t         mAs_AutoMode;                                                         // 160-163      Helps to restore current SoC after Reset or Shutdown
    5351  int64_t         mWs_AutoMode;                                                         // 164-167      Helps to restore current SoC after Reset or Shutdown
     
    298296        /* tBatFull                                     */                                                                                      2,                              // t-batt full 2 Sekunden
    299297        /* uBatFull                                     */                                                                                      14000,                  // 14Volt Ubatt full
    300         /* uBatEmpty                            */                                                                                      11312,                  // 11,312V Ubatt Empty
     298        /* uBatEmpty                            */                                                                                      12500,                  // 11,312V Ubatt Empty
    301299        /* socCalcMode                          */                                                                                      1,                              // SoC calculation mode: 0(default)
    302300        /* cellRatedDischargeTime       */                                                                                      2,                              // cell rated current discharge time [C/x]. For example, if 40Ah cell is rated as 0.5c, then rated discharge time is 2
    303301
    304         /* lvpStart     */                                                                                                                      11200,                  // uint16_t lvpStart; Spannung ab der die LOW Voltage Protection aktiv wird in mV
    305         /* lvpStop      */                                                                                                                      12000,                  // uint16_t lvpStop; Spannung ab der die LOW Voltage Protection wieder inaktiv wird
    306         /* ovpStart     */                                                                                                                      60000,                  // uint16_t  ovpStart; Spannung ab der die OVER Voltage Protection aktiv wird in mV
    307         /* ovpStop      */                                                                                                                      56000,                  // uint16_t  ovpStop; Spannung ab der die OVER Voltage Protection wieder inaktiv wird
     302        /* lvpStart     */                                                                                                                      12000,                  // uint16_t lvpStart; Spannung ab der die LOW Voltage Protection aktiv wird in mV
     303        /* lvpStop      */                                                                                                                      12500,                  // uint16_t lvpStop; Spannung ab der die LOW Voltage Protection wieder inaktiv wird
     304        /* ovpStart     */                                                                                                                      15000,                  // uint16_t  ovpStart; Spannung ab der die OVER Voltage Protection aktiv wird in mV
     305        /* ovpStop      */                                                                                                                      14000,                  // uint16_t  ovpStop; Spannung ab der die OVER Voltage Protection wieder inaktiv wird
    308306
    309307#if (DEVICETYPE == 500)
  • trunk/firmware/Src/fast_current.c

    r6 r26  
    2020
    2121
    22   // Formel zur Berechnen der Eingangsspannung
    23   // Da ein Spannungteiler mit Offset genutzt wird muss die gemessene Spannung korrigiert werden
    24   // R14 bis R19 sind die Wiederstände auf der Platine die Formel findet sich unter folgendem Link:
    25   // https://www.mikrocontroller.net/articles/Spannungsteiler#Spannungsteiler_mit_Offset.2C_passiv
    26   // Widerstände auf der Platine sind um den Faktor 1000 größer
     22
    2723#define I_SENSE_GAIN    40.0
    2824
     
    8076  double diff;
    8177  diff = (int32_t) newvalP - (int32_t) newvalM;
    82   diff = (diff * sys_data.s.values.realVdd)  / 655350.0;
     78  diff = (diff * sys_data.s.values.realVdd)  / 65536;
    8379
    8480  //Umrechung auf Strom
    85   sys_data.s.values.fast_current = (diff / I_SENSE_GAIN) /  SHUNT_RESISTOR;
    86 
     81  double temp_current;
     82  temp_current = (diff / I_SENSE_GAIN) /  SHUNT_RESISTOR;
     83  sys_data.s.values.fast_current = temp_current * (sys_data.s.parameter.batteryCurrentGainCorrectionFaktor / 1000000.0);
    8784 
    8885}
  • trunk/firmware/Src/main.c

    r6 r26  
    3131/* USER CODE BEGIN Includes */
    3232#include <stdio.h>
    33 #include <stdlib.h>
    34 #include <math.h>
     33
    3534#include "sysdata.h"
    3635#include "chip_temperature.h"
     
    7473modbus_t modbusData;
    7574
    76 static volatile uint32_t adcData[8];
     75static volatile uint32_t adcData[9];
    7776static RTC_TimeTypeDef     Time;
    7877static uint32_t conversionCounter;
     
    126125  }
    127126
     127  //Wenn Speichernutzung größer 50% (debug) nötig??
     128  //https://community.st.com/t5/stm32-mcus-products/hard-fault-with-stm32g0b1-and-lvgl/td-p/777366
     129  __HAL_FLASH_PREFETCH_BUFFER_DISABLE();
     130
    128131  /* USER CODE END 1 */
    129132
     
    194197
    195198  // STM32G0 Chiptemperatur Kalibrierung
    196   //CHIP_TEMPERATURE_Calibration(/*&sys_data*/);
     199  CHIP_TEMPERATURE_Calibration(/*&sys_data*/);
    197200
    198201  // ADC auf STM32G0 starten
    199202  HAL_ADCEx_Calibration_Start(&hadc1);
    200   HAL_ADC_Start_DMA(&hadc1, (uint32_t*)adcData, 8);
     203  HAL_ADC_Start_DMA(&hadc1, (uint32_t*)adcData, 9);
    201204
    202205  // Power up Sequenz fr INA240 Strommessverstrker
     
    315318
    316319      // Ausgabe der Temperatur des STM32G0
    317       //CHIP_TEMPERATURE_Exec( adcData[7]);
     320      CHIP_TEMPERATURE_Exec( adcData[8]);
    318321
    319322      SHUNT_TEMPERATURE_Exec(adcData[7]);
  • trunk/firmware/Src/ref_voltage.c

    r6 r26  
    3939   uint32_t avgval;
    4040   // Filterlängen in 2er-Potenzen --> Compiler optimiert
    41    avgsum -= avgsum/REF_FILTER;
     41   avgsum -= avgsum / REF_FILTER;
    4242   avgsum += newval;
    4343   avgval = avgsum / REF_FILTER;
     
    4545  // Messung Externe Spannung basierend auf 3,3V Versorgungsspannung
    4646  // Nur für Debug Zwecke
    47   sys_data.s.values.voltageVref =  (avgval * 330 * 100) / 65535;
     47  sys_data.s.values.voltageVref =  (avgval * 3300) / 65536;
    4848 
    4949  // Ermittlung Vdd als Referenz
    50   sys_data.s.values.realVdd =  30000L * 65535 / avgval;;
     50  sys_data.s.values.realVdd =  3000L * 65536 / avgval;;
    5151}
    5252/*************************** End of file ****************************/
  • trunk/firmware/Src/self_discharge.c

    r6 r26  
    1 
     1#include <stdio.h>
    22#include "sysdata.h"
    33#include "self_discharge.h"
    44
    5 #define HOLD_TIME   ( 3 * 3600 ) // 3 stunde
     5#define HOLD_TIME (10800 ) //10800 = 3 stunde
    66#define SD_FILTER 64
    77
     
    1010
    1111  const double batt_float_voltage_tol = 0.03;
    12   const double batt_voltage_holding_tol = 10;
     12  const int32_t batt_voltage_holding_tol = 10;
    1313  int32_t max_u = sys_data.s.parameter.uBatFull * ( 1 + batt_float_voltage_tol);
    1414  int32_t min_u = sys_data.s.parameter.uBatFull * ( 1 - batt_float_voltage_tol);
     
    4848    u_hold = 0;
    4949    holding_counter = 0;
     50        //printf("self_discharge: fail voltage too  high!\n");
    5051    return -2;
    5152  }
     
    5657    u_hold = 0;
    5758    holding_counter = 0;
     59        //printf("self_discharge: fail voltage too  low!\n");
    5860    return -2;
     61  }
     62
     63
     64  if (sys_data.s.values.batteryCurrent < sys_data.s.parameter.extraDischargeStrom_mA)
     65  {
     66        //Abbruch Ladegerät wurde entfernt, wir müssen mindesten den Lipro Strom messen
     67    u_hold = 0;
     68    holding_counter = 0;
     69        //printf("self_discharge: fail current too small!\n");
     70    return -3;
    5971  }
    6072
     
    6274  if (holding_counter > HOLD_TIME)
    6375  {
    64     sys_data.s.values.selfDischarge = sys_data.s.values.batteryCurrent;
     76    sys_data.s.values.selfDischarge = sys_data.s.values.batteryCurrent -  sys_data.s.parameter.extraDischargeStrom_mA;
    6577  }
    6678
    6779
     80  //Wenn ein gültiger Wert gemessen wurde, dann zu Mittelwert hinzufügen
     81  if (sys_data.s.values.selfDischarge > 0)
     82  {
    6883
    69   // --- Mittelwert ---
    70   static uint32_t last_days;
    71   static unsigned long avgsum = 0;
     84    // --- Mittelwert ---
     85    static uint32_t last_days;
     86    static unsigned long avgsum = 0;
    7287
    73   // Converting seconds into days
    74   uint32_t days = sys_data.s.values.onTime / (24U * 3600U);
     88    // Converting seconds into days
     89    uint32_t days = sys_data.s.values.onTime / (24U * 3600U);
    7590
    76   // Alle 24 Stunden ein Wert zur Mittelwertberechnung hinzufügen
    77   if (days != last_days)
    78   {
    79     last_days = days;
     91    // Alle 24 Stunden ein Wert zur Mittelwertberechnung hinzufügen
     92    if (days != last_days)
     93    {
     94      last_days = days;
    8095   
    81     uint32_t avgval;
    82     // Filterlängen in 2er-Potenzen --> Compiler optimiert
    83     avgsum -= avgsum/SD_FILTER;
    84     avgsum += sys_data.s.values.selfDischarge;
    85     avgval = avgsum / SD_FILTER;
     96      uint32_t avgval;
     97      // Filterlängen in 2er-Potenzen --> Compiler optimiert
     98      avgsum -= avgsum/SD_FILTER;
     99      avgsum += sys_data.s.values.selfDischarge;
     100      avgval = avgsum / SD_FILTER;
    86101
    87     sys_data.s.values.selfDischargeAvg = avgval;
     102      sys_data.s.values.selfDischargeAvg = avgval;
     103    }
     104
    88105  }
    89 
    90 
    91106
    92107 
  • trunk/firmware/Src/shunt_voltage.c

    r6 r26  
    5151   //avgval = avgsum / SHUNT_FILTER;
    5252
    53    sys_data.s.values.shuntVoltage =  (newval * (uint64_t)sys_data.s.values.realVdd * SHUNT_VOLTAGE_DIVIDER ) / 655360.0;
     53   sys_data.s.values.shuntVoltage =  (newval * (uint64_t)sys_data.s.values.realVdd * SHUNT_VOLTAGE_DIVIDER ) / 65536;
    5454
    5555}
  • trunk/firmware/Src/stm32g0xx_it.c

    r6 r26  
    9090{
    9191  /* USER CODE BEGIN HardFault_IRQn 0 */
     92  static volatile uint32_t cont=0;
    9293
    9394  /* USER CODE END HardFault_IRQn 0 */
    94   while (1)
     95  while (cont == 0)
    9596  {
    9697    /* USER CODE BEGIN W1_HardFault_IRQn 0 */
  • trunk/firmware/Src/sysdata.c

    r6 r26  
    3535        sys_data.s.values.selfDischargeAvg = -1;
    3636
    37         //sys_data.s.values.mWh_AutoMode = -sys_data.s.parameter.battEnergy;
    38         //sys_data.s.values.mAh_AutoMode = -sys_data.s.parameter.cellCapacity;
     37
    3938
    4039        sys_data.s.parameter.fw_revision_major     = 2;
Note: See TracChangeset for help on using the changeset viewer.