|
@@ -0,0 +1,143 @@
|
|
|
+#include "SOP.h"
|
|
|
+
|
|
|
+void SOP_Init(void)
|
|
|
+{
|
|
|
+ sopd_flg_firstRun = true;
|
|
|
+}
|
|
|
+//-------------------------------------------------------------------------
|
|
|
+
|
|
|
+void SOP(void)
|
|
|
+{
|
|
|
+ static real_T sopn_V_up;
|
|
|
+ real_T sopn_I_currPred;
|
|
|
+ real_T sopn_V_battPred10;
|
|
|
+ real_T sopn_pct_socPred10;
|
|
|
+ real_T ocv;
|
|
|
+ real_T Ro;
|
|
|
+ real_T RC;
|
|
|
+ real_T Rp;
|
|
|
+ real_T ileft;
|
|
|
+ real_T iright;
|
|
|
+ real_T imid;
|
|
|
+ real_T sopn_V_battU;
|
|
|
+ if(sopd_flg_firstRun)
|
|
|
+ {
|
|
|
+ sopn_V_up = 0;
|
|
|
+ }
|
|
|
+ ocv = (real_T)look1_u16tu16(socd_pct_battSoc, cmnm_pct_soc, cmnm_V_ocv, 13) * 0.001;
|
|
|
+ Ro = (real_T)look1_u16tu16(socd_pct_battSoc, cmnm_pct_soc, cmnm_R_ohm, 13) * 0.001 * 0.001;
|
|
|
+ Rp = (real_T)look1_u16tu16(socd_pct_battSoc, cmnm_pct_soc, cmnm_R_polar,13) * 0.001 * 0.001;
|
|
|
+ RC = (real_T)look1_u16tu16(socd_pct_battSoc, cmnm_pct_soc, cmnm_F_polar,13) * 0.001;
|
|
|
+ //printf("%f %f %f %f\n",ocv,Ro,Rp,RC);
|
|
|
+
|
|
|
+ //printf("soc:%d,I:%d,up:%f\n",socd_pct_battSoc,sfmd_I_curr,sopn_V_up);
|
|
|
+ //充电功率
|
|
|
+ sopn_I_currPred = 0;
|
|
|
+ predSystem(ocv,Ro,Rp,RC,sopn_I_currPred,sopn_V_up,&sopn_pct_socPred10,&sopn_V_battPred10);
|
|
|
+
|
|
|
+ if(sopn_V_battPred10 > (real_T)cmnc_V_chrgFul * 0.001 || sopn_pct_socPred10 > (real_T)socc_pct_battSocUp * 0.1)
|
|
|
+ {
|
|
|
+ sopn_I_currPred = 0;
|
|
|
+
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ sopn_I_currPred = (real_T)sopc_I_currUp * 0.1;
|
|
|
+ predSystem(ocv,Ro,Rp,RC,sopn_I_currPred,sopn_V_up,&sopn_pct_socPred10,&sopn_V_battPred10);
|
|
|
+ if(sopn_V_battPred10 < (real_T)cmnc_V_chrgFul * 0.001 && sopn_pct_socPred10 < (real_T)socc_pct_battSocUp * 0.1)
|
|
|
+ {
|
|
|
+ sopn_I_currPred = (real_T)sopc_I_currUp * 0.1;;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ iright = (real_T) sopc_I_currUp * 0.1;
|
|
|
+ ileft = 0;
|
|
|
+ imid = (iright + ileft)/2;
|
|
|
+ while(iright - ileft > 0.1)
|
|
|
+ {
|
|
|
+ predSystem(ocv,Ro,Rp,RC,imid,sopn_V_up,&sopn_pct_socPred10,&sopn_V_battPred10);
|
|
|
+
|
|
|
+ if(sopn_V_battPred10 > (real_T)cmnc_V_chrgFul * 0.001 || sopn_pct_socPred10 > (real_T)socc_pct_battSocUp * 0.1)
|
|
|
+ {
|
|
|
+ iright = imid;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ ileft = imid;
|
|
|
+ }
|
|
|
+ imid = (iright + ileft)/2;
|
|
|
+ }
|
|
|
+ sopn_I_currPred = ileft;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ sopn_V_battU = (ocv + sopn_I_currPred * Ro + sopn_V_up) * cmnc_num_cellUNum;
|
|
|
+ sopd_I_chrgCurrMax = (int16_T)(sopn_I_currPred * 10);
|
|
|
+ sopd_P_chrgPMax = (uint16_T)(sopn_V_battU * sopn_I_currPred * 1000);
|
|
|
+ predSystem(ocv,Ro,Rp,RC,sopn_I_currPred,sopn_V_up,&sopn_pct_socPred10,&sopn_V_battPred10);
|
|
|
+ //printf("%f, %f, %f\n\n",sopn_I_currPred,sopn_pct_socPred10,sopn_V_battPred10);
|
|
|
+
|
|
|
+
|
|
|
+ //放电功率
|
|
|
+
|
|
|
+ sopn_I_currPred = 0;
|
|
|
+ predSystem(ocv,Ro,Rp,RC,sopn_I_currPred,sopn_V_up,&sopn_pct_socPred10,&sopn_V_battPred10);
|
|
|
+ if(sopn_V_battPred10 < (real_T)cmnc_V_disChrgLim * 0.001 || sopn_pct_socPred10 < (real_T)socc_pct_battSocLow * 0.1)
|
|
|
+ {
|
|
|
+ sopn_I_currPred = 0;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ sopn_I_currPred = (real_T)sopc_I_currLow * 0.1;
|
|
|
+ predSystem(ocv,Ro,Rp,RC,sopn_I_currPred,sopn_V_up,&sopn_pct_socPred10,&sopn_V_battPred10);
|
|
|
+ if(sopn_V_battPred10 > (real_T)cmnc_V_disChrgLim * 0.001 && sopn_pct_socPred10 > (real_T)socc_pct_battSocLow * 0.1)
|
|
|
+ {
|
|
|
+ sopn_I_currPred = (real_T)sopc_I_currLow * 0.1;;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ iright = 0;
|
|
|
+ ileft = (real_T) sopc_I_currLow * 0.1;
|
|
|
+ imid = (iright + ileft)/2;
|
|
|
+ while(iright - ileft > 0.1)
|
|
|
+ {
|
|
|
+ predSystem(ocv,Ro,Rp,RC,imid,sopn_V_up,&sopn_pct_socPred10,&sopn_V_battPred10);
|
|
|
+ if(sopn_V_battPred10 > (real_T)cmnc_V_disChrgLim * 0.001 && sopn_pct_socPred10 > (real_T)socc_pct_battSocLow * 0.1)
|
|
|
+ {
|
|
|
+ iright = imid;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ ileft = imid;
|
|
|
+ }
|
|
|
+ imid = (iright + ileft)/2;
|
|
|
+ }
|
|
|
+ sopn_I_currPred = iright;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ sopn_V_battU = sopn_V_battPred10 * cmnc_num_cellUNum;
|
|
|
+ sopd_I_disChrgCurrMax = (int16_T)(sopn_I_currPred * 10);
|
|
|
+ sopd_P_disChrgPMax = (uint16_T)(- sopn_V_battU * sopn_I_currPred * 1000);
|
|
|
+
|
|
|
+
|
|
|
+ sopn_V_up = sopn_V_up * exp(-1/RC) + Rp * (1 - exp(-1/RC)) * sfmd_I_curr;
|
|
|
+ sopd_flg_firstRun = false;
|
|
|
+}
|
|
|
+
|
|
|
+void predSystem(real_T ocv,real_T Ro,real_T Rp,real_T RC,real_T sopn_I_currPred,real_T sopn_V_up,real_T *sopn_pct_socPred10,real_T *sopn_V_battPred10)
|
|
|
+{
|
|
|
+ uint8_T i;
|
|
|
+ real_T sopn_V_upPred;
|
|
|
+ real_T sopn_pct_socPred;
|
|
|
+ real_T sopn_Q_cellCap;
|
|
|
+ sopn_Q_cellCap = (real_T)sohd_pct_bcuSoh * cmnc_Q_ratedCp * 0.0001;
|
|
|
+ sopn_pct_socPred = (real_T) socd_pct_battSoc * 0.1;
|
|
|
+ sopn_V_upPred = sopn_V_up;
|
|
|
+ for(i = 0;i < 10;i++)
|
|
|
+ {
|
|
|
+ sopn_V_upPred = sopn_V_upPred * exp(-1/RC) + Rp * (1 - exp(-1/RC)) * sopn_I_currPred;
|
|
|
+ sopn_pct_socPred = sopn_pct_socPred + sopn_I_currPred/sopn_Q_cellCap/36;
|
|
|
+ }
|
|
|
+ *sopn_pct_socPred10 = sopn_pct_socPred;
|
|
|
+ *sopn_V_battPred10 = ocv + sopn_I_currPred * Ro + sopn_V_upPred;
|
|
|
+}
|
|
|
+
|