C51 COMPILER V9.01   CALCULATE                                                             02/06/2025 15:28:45 PAGE 1   


C51 COMPILER V9.01, COMPILATION OF MODULE CALCULATE
OBJECT MODULE PLACED IN .\output\Calculate.obj
COMPILER INVOKED BY: D:\Tool\Keil\C51\BIN\C51.EXE code_drv\Calculate.c LARGE OPTIMIZE(7,SIZE) REGFILE(.\output\MCUCore_L
                    -oad.ORC) BROWSE INTVECTOR(0X1000) INCDIR(.\header_app;.\header_drv;.\code_gasguage;.\code_classb\iec60730_lib\include;.\
                    -code_classb\iec60730_proc\Include;.\code_classb\config) DEBUG OBJECTEXTEND PRINT(.\output\Calculate.lst) OBJECT(.\output
                    -\Calculate.obj)

line level    source

   1          /********************************************************************************
   2          Copyright (C), Sinowealth Electronic. Ltd.
   3          Author:         Sino
   4          Version:        V0.0
   5          Date:           2020/04/26
   6          History:
   7                  V2.0    2020/04/26               Preliminary
   8          ********************************************************************************/
   9          #include "Main.h"
  10          
  11          
  12          U8      xdata   ucChgingCheckCnt;
  13          U8      xdata   ucDsgingCheckCnt;
  14          
  15          /*************************************************************************************************
  16          * 函数名: CalcuTemp
  17          * 参  数: 无
  18          * 返回值: 无
  19          * 描  述: 根据计算的阻值来查表，获取对应温度。温度变量保存的为开尔文温度*10
  20                    例如摄氏度25°，温度变量保存的值为2731+250
  21          *************************************************************************************************/
  22          U16 CalcuTemp(U16 getdata)
  23          {
  24   1              U8      i;
  25   1              U16     Temperature;
  26   1          U32 Tempcalcu;
  27   1       
  28   1      #if (AFE_ID == 0x34)
                  Tempcalcu = (U32)getdata*REF_RES_VAL/(32768-getdata);
              #else
  31   1              Tempcalcu= (U32)getdata*REF_RES_VAL/(4096-getdata);     //calculte the resistance value of 103AT
  32   1          if(Tempcalcu > 10)
  33   1          {
  34   2              Tempcalcu -= 10;
  35   2          }   
  36   1      #endif
  37   1       
  38   1              if(Tempcalcu >= NTC103AT[0])                            //look up table to find the resieter  correspond 
             -temp
  39   1              {
  40   2                      Temperature = 2731+(TEMP_LOWER_LIMIT *10);                      
  41   2              }
  42   1              else if(Tempcalcu <= NTC103AT[NTC103AT_ARRAY_LEN-1])
  43   1              {
  44   2                      Temperature = 2731+(TEMP_UPPER_LIMIT *10);
  45   2              }
  46   1              else
  47   1              {
  48   2                      i = ucTempeMiddle;                                  //the ucTempeMiddle must be initialized in InitVar()
  49   2                      if(Tempcalcu > NTC103AT[i])
  50   2                      {
  51   3                              for(i=ucTempeMiddle-1; i>=0; i--)
C51 COMPILER V9.01   CALCULATE                                                             02/06/2025 15:28:45 PAGE 2   

  52   3                              {
  53   4                                      if(Tempcalcu <= NTC103AT[i])                //NTC103AT[i+1]<resis<NTC103AT[i]
  54   4                                      {
  55   5                                              break;
  56   5                                      }
  57   4                              }
  58   3                      }
  59   2                      else
  60   2                      {
  61   3                              for(i=ucTempeMiddle+1; i<NTC103AT_ARRAY_LEN-1; i++)
  62   3                              {
  63   4                                      if(Tempcalcu > NTC103AT[i])                 //NTC103AT[i-1]<resis<NTC103AT[i]
  64   4                                      {
  65   5                                              break;
  66   5                                      }
  67   4                              }
  68   3                              i--;
  69   3                      }
  70   2                      ucTempeMiddle = i;
  71   2                      
  72   2                      Temperature = (U16)(ucTempeMiddle-50)*10+(NTC103AT[i]-Tempcalcu)*10/(NTC103AT[i]-NTC103AT[i+1])+2731;   
  73   2              }
  74   1              return Temperature;     
  75   1      }
  76          
  77          
  78          /*************************************************************************************************
  79          * 函数名: AfeGetVol、AfeGetTempe
  80          * 参  数: 无
  81          * 返回值: 无
  82          * 描  述: 从AFE读取电压、温度采集数据
  83          *************************************************************************************************/
  84          BOOL AfeGetVol(void)
  85          {
  86   1              U8  i;
  87   1              BOOL Result=1;
  88   1      
  89   1              for(i=ucCellNumOffset; i<(ucCellNum+ucCellNumOffset); i++)
  90   1          {
  91   2                      if(!AFEReadReg(AFE_CELL1H+2*i, 2, (U8 xdata *)(&AFE.uiCell[i])))        //通过TWI读取VADC采集的电压值()
  92   2              {
  93   3                              Result = 0;
  94   3                              return Result;
  95   3                      }
  96   2              }
  97   1              
  98   1              return Result;
  99   1      }
 100          
 101          BOOL AfeGetTempe(void)
 102          {
 103   1              BOOL Result=1;
 104   1              
 105   1              if(!AFEReadReg(AFE_TS1H, 2, (U8 xdata *)&AFE.uiTS[0]))
 106   1              {
 107   2                      Result = 0;
 108   2              }
 109   1              if(!AFEReadReg(AFE_TS2H, 2, (U8 xdata *)&AFE.uiTS[1]))
 110   1              {
 111   2                      Result = 0;
 112   2          }
 113   1          
C51 COMPILER V9.01   CALCULATE                                                             02/06/2025 15:28:45 PAGE 3   

 114   1          if(!AFEReadReg(AFE_TEMP1H, 2, (U8 xdata *)&AFE.uiICTempe[0]))
 115   1              {
 116   2                      Result = 0;
 117   2              }
 118   1          if(ucCellNum > 5)                                           //6~10串应用时
 119   1          {
 120   2              if(!AFEReadReg(AFE_TEMP2H, 2, (U8 xdata *)&AFE.uiICTempe[1]))
 121   2              {
 122   3                  Result = 0;
 123   3              }
 124   2          }
 125   1              
 126   1              return Result;
 127   1      }
 128          
 129          
 130          /*************************************************************************************************
 131          * 函数名: AfeCalcuTempe
 132          * 参  数: 无
 133          * 返回值: 无
 134          * 描  述: 计算温度，更新uiTempeMax、uiTempeMin
 135          *************************************************************************************************/
 136          void AfeCalcuTempe(void)
 137          {
 138   1          U16 TempeData;
 139   1      
 140   1              if(AfeGetTempe())
 141   1              {
 142   2                      TempeData = CalcuTemp(AFE.uiTS[0]) + E2siTS0Offset;             //计算外部温度1
 143   2                      #if     (UART0_DEFINE != 0)     
 144   2                      IrqUart0Dis();
 145   2                      #endif
 146   2                      #if     (UART1_DEFINE != 0)
                              IrqUart1Dis();
                              #endif
 149   2                      #if     (UART2_DEFINE != 0)
                              IrqUart2Dis();
                              #endif
 152   2                      Info.uiTS[0] = TempeData;
 153   2                      #if     (UART0_DEFINE != 0)                     
 154   2                      IrqUart0En();                                                           //开启uart0中断                                                 
 155   2                      #endif  
 156   2                      #if     (UART1_DEFINE != 0)                     
                              IrqUart1En();                                                           //开启uart1中断                                                 
                              #endif  
 159   2                      #if     (UART2_DEFINE != 0)
                              IrqUart2En();                                                   //初始化UART2中断使能，根据具体使用UART模块来进行选择
                              #endif
 162   2                      TempeData = (U32)AFE.uiICTempe[0]*17/10+31;               //计算内部温度1
 163   2                      #if     (UART0_DEFINE != 0)     
 164   2                      IrqUart0Dis();
 165   2                      #endif
 166   2                      #if     (UART1_DEFINE != 0)
                              IrqUart1Dis();
                              #endif
 169   2                      #if     (UART2_DEFINE != 0)
                              IrqUart2Dis();
                              #endif
 172   2                      Info.uiICTempe[0] = TempeData;
 173   2                      
 174   2                      #if     (UART0_DEFINE != 0)                     
 175   2                      IrqUart0En();                                                           //开启uart0中断                                                 
C51 COMPILER V9.01   CALCULATE                                                             02/06/2025 15:28:45 PAGE 4   

 176   2                      #endif  
 177   2                      #if     (UART1_DEFINE != 0)                     
                              IrqUart1En();                                                           //开启uart1中断                                                 
                              #endif
 180   2                      #if     (UART2_DEFINE != 0)
                              IrqUart2En();                                                   //初始化UART2中断使能，根据具体使用UART模块来进行选择
                              #endif
 183   2                
 184   2                      if(ucCellNum > 5)                                                                               //6~10串应用时
 185   2                      {    
 186   3                              TempeData = (U32)AFE.uiICTempe[1]*17/10+31;           //计算内部温度2
 187   3                              #if     (UART0_DEFINE != 0)     
 188   3                              IrqUart0Dis();
 189   3                              #endif
 190   3                              #if     (UART1_DEFINE != 0)
                                      IrqUart1Dis();
                                      #endif
 193   3                              #if     (UART2_DEFINE != 0)
                                      IrqUart2Dis();
                                      #endif
 196   3                              Info.uiICTempe[1] = TempeData;
 197   3                              #if     (UART0_DEFINE != 0)                     
 198   3                              IrqUart0En();                                                           //开启uart0中断                                                 
 199   3                              #endif  
 200   3                              #if     (UART1_DEFINE != 0)                     
                                      IrqUart1En();                                                           //开启uart1中断                                                 
                                      #endif
 203   3                              #if     (UART2_DEFINE != 0)
                                      IrqUart2En();                                                   //初始化UART2中断使能，根据具体使用UART模块来进行选择
                                      #endif
 206   3                      }
 207   2               
 208   2                      uiTempeMin = Info.uiTS[0];
 209   2                      uiTempeMax = Info.uiTS[0];
 210   2                      if(bTempNum)
 211   2                      {
 212   3                              TempeData = CalcuTemp(AFE.uiTS[1]) + E2siTS1Offset; //计算外部温度2
 213   3                              #if     (UART0_DEFINE != 0)     
 214   3                              IrqUart0Dis();
 215   3                              #endif
 216   3                              #if     (UART1_DEFINE != 0)
                                      IrqUart1Dis();
                                      #endif
 219   3                              #if     (UART2_DEFINE != 0)
                                      IrqUart2Dis();
                                      #endif
 222   3                              Info.uiTS[1] = TempeData;
 223   3                              #if     (UART0_DEFINE != 0)                     
 224   3                              IrqUart0En();                                                           //开启uart0中断                                                 
 225   3                              #endif  
 226   3                              #if     (UART1_DEFINE != 0)                     
                                      IrqUart1En();                                                           //开启uart1中断                                                 
                                      #endif
 229   3                              #if     (UART2_DEFINE != 0)
                                      IrqUart2En();                                                   //初始化UART2中断使能，根据具体使用UART模块来进行选择
                                      #endif
 232   3                              
 233   3                              if(TempeData < uiTempeMin)
 234   3                              {
 235   4                                      uiTempeMin = TempeData;
 236   4                              }
 237   3                              else
C51 COMPILER V9.01   CALCULATE                                                             02/06/2025 15:28:45 PAGE 5   

 238   3                              {
 239   4                                      uiTempeMax = TempeData;
 240   4                              }
 241   3                      }
 242   2              }
 243   1      }
 244          
 245          
 246          /*************************************************************************************************
 247          * 函数名: AfeCalcuVol
 248          * 参  数: 无
 249          * 返回值: 无
 250          * 描  述: 计算电压，同步更新最大值最小值uiVadcVmax、uiVadcVmin，用于断线判断
 251                    当没有平衡时，才更新uiCellVmax、uiCellVmin，用于保护判断
 252          *************************************************************************************************/
 253          void AfeCalcuVol(void)
 254          {
 255   1              U8 i;
 256   1              U32 TempPackVol=0, TempCellVol=0;
 257   1              uiVadcVmax = 0;                                   
 258   1              uiVadcVmin = 6000;
 259   1      
 260   1              if(AfeGetVol())
 261   1              {
 262   2                      for(i=ucCellNumOffset; i<(ucCellNum+ucCellNumOffset); i++)
 263   2                      {
 264   3                              TempCellVol = (U32)AFE.uiCell[i]*CALIVOL/E2uiVPackGain;
 265   3                      
 266   3                              if(TempCellVol > uiVadcVmax)            //计算最大值&最小值
 267   3                              {
 268   4                                      uiVadcVmax = TempCellVol;
 269   4                              }
 270   3                              if(TempCellVol < uiVadcVmin)
 271   3                              {
 272   4                                      uiVadcVmin = TempCellVol;
 273   4                              }
 274   3      
 275   3                              if(!bBalancingFlg)                      //if bCellOpenDecFlag this data will throw away
 276   3                              {
 277   4                                      #if     (UART0_DEFINE != 0)     
 278   4                                      IrqUart0Dis();
 279   4                                      #endif
 280   4                                      #if     (UART1_DEFINE != 0)
                                              IrqUart1Dis();
                                              #endif
 283   4                                      #if     (UART2_DEFINE != 0)
                                              IrqUart2Dis();
                                              #endif
 286   4                                      Info.uiVCell[i] = TempCellVol;
 287   4                                      #if     (UART0_DEFINE != 0)                     
 288   4                                      IrqUart0En();                                                           //开启uart0中断                                                 
 289   4                                      #endif  
 290   4                                      #if     (UART1_DEFINE != 0)                     
                                              IrqUart1En();                                                           //开启uart1中断                                                 
                                              #endif
 293   4                                      #if     (UART2_DEFINE != 0)
                                              IrqUart2En();                                                   //初始化UART2中断使能，根据具体使用UART模块来进行选择
                                              #endif
 296   4                                      TempPackVol += TempCellVol;
 297   4                              }
 298   3                      }
 299   2      
C51 COMPILER V9.01   CALCULATE                                                             02/06/2025 15:28:45 PAGE 6   

 300   2                      if(!bBalancingFlg)
 301   2                      {
 302   3                              uiCellVmax = uiVadcVmax;
 303   3                              uiCellVmin = uiVadcVmin;
 304   3                              
 305   3                              #if     (UART0_DEFINE != 0)     
 306   3                              IrqUart0Dis();
 307   3                              #endif
 308   3                              #if     (UART1_DEFINE != 0)
                                      IrqUart1Dis();
                                      #endif
 311   3                              #if     (UART2_DEFINE != 0)
                                      IrqUart2Dis();
                                      #endif
 314   3                              Info.ulVoltage = TempPackVol;           //Calculate the total voltage
 315   3                              #if     (UART0_DEFINE != 0)                     
 316   3                              IrqUart0En();                                                           //开启uart0中断                                                 
 317   3                              #endif  
 318   3                              #if     (UART1_DEFINE != 0)                     
                                      IrqUart1En();                                                           //开启uart1中断                                                 
                                      #endif
 321   3                              #if     (UART2_DEFINE != 0)
                                      IrqUart2En();                                                   //初始化UART2中断使能，根据具体使用UART模块来进行选择
                                      #endif
 324   3                      }
 325   2              }
 326   1      }
 327          
 328          
 329          /*************************************************************************************************
 330          * 函数名: CurTempOffset
 331          * 参  数: 无
 332          * 返回值: 无
 333          * 描  述: 不同芯片温度下ADC的补偿值
 334          *************************************************************************************************/
 335          S16 code siCurTempOffset[2][13]=
 336          {   /**0****1****2****3***4***5***6***7***8***9**10**11**12**/
 337              {-40, -30, -20, -10,  0, 10, 25, 35, 45, 55, 65, 75, 85},
 338              { -5,  -4,  -3,  -2, -1, -1,  0,  1,  1,  2,  3,  4,  5},
 339          };
 340          
 341          /*************************************************************************************************
 342          * 函数名: OffsetCalculate()
 343          * 参  数: 无
 344          * 返回值: 无
 345          * 描  述: 根据芯片内部温度实时调整0电流补偿值，以便消除温度对ADC采集产生的影响
 346          *************************************************************************************************/
 347          S16 OffsetCalculate(void)
 348          {
 349   1          S16 xdata siCadcTempOffset=0;                       //20220620
 350   1          U8 xdata i;
 351   1          
 352   1          for(i=0; i<12; i++)
 353   1          {
 354   2              if(Info.uiICTempe[0] <= (((S32)siCurTempOffset[0][i] + siCurTempOffset[0][i+1]) / 2 * 10 + 2731))
 355   2              {
 356   3                  siCadcTempOffset = siCurTempOffset[1][i];
 357   3                  break;
 358   3              }
 359   2          }
 360   1          return siCadcTempOffset;
 361   1      }
C51 COMPILER V9.01   CALCULATE                                                             02/06/2025 15:28:45 PAGE 7   

 362          
 363          /*************************************************************************************************
 364          * 函数名: AfeCalcuCurr
 365          * 参  数: 无
 366          * 返回值: 无
 367          * 描  述: 计算CADC采集的电流数据
 368          *************************************************************************************************/
 369          void AfeCalcuCurr(void)
 370          {
 371   1              U8 i;
 372   1              S32 Tempdata=0;
 373   1      
 374   1              AFEReadReg(AFE_CURH, 2, (U8 xdata *)&AFE.siCurr);       //通过TWI读取CADC采集的电流值
 375   1      
 376   1              if((AFE.siCurr&0x1000) != 0)                                    //根据bit12判断是否为负数(放电电流为负值)，如为负值高位补0
 377   1              {
 378   2                      AFE.siCurr|=0xE000;
 379   2              }
 380   1              slCadcCurrent = (S32)CALICUR*(AFE.siCurr-E2siCadcOffset+OffsetCalculate())/E2siCadcGain;
 381   1      
 382   1              slCadcCurBuf[ucCadcCnt] = slCadcCurrent;                //对连续采集的16次电流取平均值，作为当前电流值
 383   1              if(++ucCadcCnt >= 16)
 384   1              {
 385   2                      ucCadcCnt = 0;
 386   2              }
 387   1              for(i=0; i<16; i++)
 388   1              {
 389   2                      Tempdata += slCadcCurBuf[i];
 390   2              }
 391   1              slCadcCurAverage = Tempdata/16;
 392   1         
 393   1              bDSGING = 0;                                                                    //根据电流判定充放电状态
 394   1              bCHGING = 0;
 395   1              if(slCadcCurAverage < (-E2siDfilterCur))
 396   1              {
 397   2                      if(++ucDsgingCheckCnt >= TIME_50MS_500MS)       //充放电状态检测延时10*50mS
 398   2                      {
 399   3                              ucDsgingCheckCnt = TIME_50MS_500MS;
 400   3                              bDSGING = 1;
 401   3                              #if     (UART0_DEFINE != 0)     
 402   3                              IrqUart0Dis();
 403   3                              #endif
 404   3                              #if     (UART1_DEFINE != 0)
                                      IrqUart1Dis();
                                      #endif
 407   3                              #if     (UART2_DEFINE != 0)
                                      IrqUart2Dis();
                                      #endif
 410   3                              Info.slCurr = slCadcCurAverage;
 411   3                              #if     (UART0_DEFINE != 0)                     
 412   3                              IrqUart0En();                                                           //开启uart0中断                                                 
 413   3                              #endif  
 414   3                              #if     (UART1_DEFINE != 0)                     
                                      IrqUart1En();                                                           //开启uart1中断                                                 
                                      #endif
 417   3                              #if     (UART2_DEFINE != 0)
                                      IrqUart2En();                                                   //初始化UART2中断使能，根据具体使用UART模块来进行选择
                                      #endif
 420   3                      }
 421   2              }
 422   1              else if(slCadcCurAverage > E2siDfilterCur)
 423   1              {
C51 COMPILER V9.01   CALCULATE                                                             02/06/2025 15:28:45 PAGE 8   

 424   2                      if(++ucChgingCheckCnt >= TIME_50MS_500MS)       //充放电状态检测延时10*50mS
 425   2                      {
 426   3                              ucChgingCheckCnt = TIME_50MS_500MS;
 427   3                              bCHGING = 1;            
 428   3                              McuPWM2Set(4000, 100);                  
 429   3                              #if     (UART0_DEFINE != 0)     
 430   3                              IrqUart0Dis();
 431   3                              #endif
 432   3                              #if     (UART1_DEFINE != 0)
                                      IrqUart1Dis();
                                      #endif
 435   3                              #if     (UART2_DEFINE != 0)
                                      IrqUart2Dis();
                                      #endif
 438   3                              Info.slCurr = slCadcCurAverage;
 439   3                              #if     (UART0_DEFINE != 0)                     
 440   3                              IrqUart0En();                                                           //开启uart0中断                                                 
 441   3                              #endif  
 442   3                              #if     (UART1_DEFINE != 0)                     
                                      IrqUart1En();                                                           //开启uart1中断                                                 
                                      #endif
 445   3                              #if     (UART2_DEFINE != 0)
                                      IrqUart2En();                                                   //初始化UART2中断使能，根据具体使用UART模块来进行选择
                                      #endif
 448   3                      }
 449   2              }
 450   1              else
 451   1              {
 452   2                      #if     (UART0_DEFINE != 0)     
 453   2                      IrqUart0Dis();
 454   2                      #endif
 455   2                      #if     (UART1_DEFINE != 0)
                              IrqUart1Dis();
                              #endif
 458   2                      #if     (UART2_DEFINE != 0)
                              IrqUart2Dis();
                              #endif
 461   2                      Info.slCurr = 0;
 462   2                      #if     (UART0_DEFINE != 0)                     
 463   2                      IrqUart0En();                                                           //开启uart0中断                                                 
 464   2                      #endif  
 465   2                      #if     (UART1_DEFINE != 0)                     
                              IrqUart1En();                                                           //开启uart1中断                                                 
                              #endif
 468   2                      #if     (UART2_DEFINE != 0)
                              IrqUart2En();                                                   //初始化UART2中断使能，根据具体使用UART模块来进行选择
                              #endif
 471   2              }
 472   1      }
 473          
 474          
 475          /*************************************************************************************************
 476          * 函数名: AFEInfoProcess
 477          * 参  数: 无
 478          * 返回值: 无
 479          * 描  述: 每50mS读取AFE信息，并更新电压、电流、温度数据
 480          *************************************************************************************************/
 481          void AFEInfoProcess(void)
 482          {
 483   1              AFERdFlg();
 484   1              
 485   1          bVADCFlg = 0;
C51 COMPILER V9.01   CALCULATE                                                             02/06/2025 15:28:45 PAGE 9   

 486   1          AfeCalcuVol();
 487   1          AfeCalcuTempe();
 488   1      
 489   1              if(bCADCFlg)                            //当CADC转换完成后，才读取AFE电流信息并计算
 490   1              {
 491   2                      bCADCFlg = 0;
 492   2                      AfeCalcuCurr();
 493   2              }
 494   1      }
 495          
 496          


MODULE INFORMATION:   STATIC OVERLAYABLE
   CODE SIZE        =   1760    ----
   CONSTANT SIZE    =     52    ----
   XDATA SIZE       =      2      25
   PDATA SIZE       =   ----    ----
   DATA SIZE        =   ----    ----
   IDATA SIZE       =   ----    ----
   BIT SIZE         =   ----       2
END OF MODULE INFORMATION.


C51 COMPILATION COMPLETE.  0 WARNING(S),  0 ERROR(S)
