@@ -670,6 +670,9 @@ void RK_Integrator( int N,
670670 SkipJac ,
671671 NewtonDone ,
672672 SkipLU ;
673+ /* Initialize variables to prevent use of uninitialized values */
674+ Hacc = ZERO ;
675+ ErrOld = ZERO ;
673676
674677/*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
675678
@@ -769,6 +772,7 @@ Tloop: while ( (Tend-*T)*Tdirection - Roundoff > ZERO ) {
769772 /*~~~> Initializations for Newton iteration */
770773 NewtonDone = 0 ;
771774 Fac = (KPP_REAL )0.5 ; /* Step reduction if too many iterations */
775+ NewtonIncrementOld = Roundoff ; /* Initialize to prevent division by zero */
772776
773777 /* for NewtonLoop */
774778 for (NewtonIter = 1 ; NewtonIter <= NewtonMaxit ; NewtonIter ++ )
@@ -791,8 +795,12 @@ Tloop: while ( (Tend-*T)*Tdirection - Roundoff > ZERO ) {
791795 Theta = ABS (ThetaMin );
792796 NewtonRate = (KPP_REAL )2.0 ;
793797 }
794- else {
798+ else {
795799 /*printf("Entering else from NewtonIter=%d == 1\n", NewtonIter);*/
800+ /* Safety check: prevent division by zero */
801+ if (NewtonIncrementOld <= Roundoff ) {
802+ NewtonIncrementOld = MAX (NewtonIncrement , Roundoff );
803+ }
796804 Theta = NewtonIncrement / NewtonIncrementOld ;
797805 /*printf("Theta=%f\n", Theta);*/
798806 if (Theta < (KPP_REAL )0.99 ) {
@@ -874,6 +882,7 @@ Tloop: while ( (Tend-*T)*Tdirection - Roundoff > ZERO ) {
874882 /*~~~> Initializations for Newton iteration */
875883 NewtonDone = 0 ;
876884 Fac = (KPP_REAL )0.5 ; /* Step reduction factor if too many iterations */
885+ NewtonIncrementOld = Roundoff ; /* Initialize to prevent division by zero */
877886
878887 /* for SDNewtonLoop */
879888 for (NewtonIter = 1 ; NewtonIter <= NewtonMaxit ; NewtonIter ++ )
@@ -884,6 +893,11 @@ Tloop: while ( (Tend-*T)*Tdirection - Roundoff > ZERO ) {
884893 FUN_CHEM (* T + H ,TMP ,DZ4 ); /* DZ4 <- Fun(Y+Z4) */
885894 ISTATUS [Nfun ]++ ;
886895 /* DZ4[1,N] = (D[1, N]-Z4[1,N])*(rkGamma/H) + DZ4[1,N]; */
896+ /* Safety check: H should not be zero here, but add protection */
897+ if (ABS (H ) <= Roundoff ) {
898+ * IERR = -10 ;
899+ return ;
900+ }
887901 WAXPY (N ,- ONE * rkGamma /H ,Z4 ,1 ,DZ4 ,1 );
888902 WAXPY (N ,rkGamma /H ,G ,1 ,DZ4 ,1 );
889903
@@ -902,6 +916,10 @@ Tloop: while ( (Tend-*T)*Tdirection - Roundoff > ZERO ) {
902916 }
903917 else {
904918 /*printf("Entering else from NewtonIter=%d == 1\n", NewtonIter);*/
919+ /* Safety check: prevent division by zero */
920+ if (NewtonIncrementOld <= Roundoff ) {
921+ NewtonIncrementOld = MAX (NewtonIncrement , Roundoff );
922+ }
905923 ThetaSD = NewtonIncrement / NewtonIncrementOld ;
906924 if (ThetaSD < (KPP_REAL )0.99 ) {
907925 /*printf( "Entering if Theta=%g < 0.99\n", Theta );*/
@@ -1001,7 +1019,13 @@ Tloop: while ( (Tend-*T)*Tdirection - Roundoff > ZERO ) {
10011019 if (Gustafsson == 1 ) {
10021020 /*~~~> Predictive controller of Gustafsson */
10031021 if (ISTATUS [Nacc ] > 1 ) {
1004- FacGus = FacSafe * (H /Hacc )* pow (Err * Err /ErrOld ,(KPP_REAL )(-0.25 ));
1022+ /* Safety check: prevent division by zero or near-zero values */
1023+ if (ABS (Hacc ) > ((KPP_REAL )10.0 )* WLAMCH ('E' ) &&
1024+ ABS (ErrOld ) > ((KPP_REAL )10.0 )* WLAMCH ('E' )) {
1025+ FacGus = FacSafe * (H /Hacc )* pow (Err * Err /ErrOld ,(KPP_REAL )(-0.25 ));
1026+ } else {
1027+ FacGus = Fac ;
1028+ }
10051029 FacGus = MIN (FacMax ,MAX (FacMin ,FacGus ));
10061030 Fac = MIN (Fac ,FacGus );
10071031 Hnew = Fac * H ;
@@ -1067,7 +1091,7 @@ Tloop: while ( (Tend-*T)*Tdirection - Roundoff > ZERO ) {
10671091~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
10681092void RK_ErrorMsg (int Code , KPP_REAL T , KPP_REAL H , int * IERR )
10691093{
1070- Code = * IERR ;
1094+ * IERR = Code ;
10711095 printf ("\n~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~" );
10721096 printf ("\nForced exit from RungeKutta due to the following error:\n" );
10731097
@@ -1177,6 +1201,10 @@ void RK_Interpolate(char action[], int N, KPP_REAL H, KPP_REAL Hold, KPP_REAL Z1
11771201 /* Construct the solution quadratic interpolant Q(c_i) = Z_i, i=1:3 */
11781202 if ( strncmp (action , "make" , 4 ) ) {
11791203 den = (rkC [2 ]- rkC [1 ])* (rkC [1 ]- rkC [0 ])* (rkC [0 ]- rkC [2 ]);
1204+ /* Safety check: prevent division by zero or near-zero denominator */
1205+ if (ABS (den ) <= ((KPP_REAL )10.0 )* WLAMCH ('E' )) {
1206+ return ; /* Denominator is too small, cannot interpolate */
1207+ }
11801208 for (i = 0 ; i < N ; i ++ )
11811209 {
11821210 CONT [i ][0 ] = (- rkC [2 ]* rkC [2 ]* rkC [1 ]* Z1 [i ]
@@ -1195,6 +1223,10 @@ void RK_Interpolate(char action[], int N, KPP_REAL H, KPP_REAL Hold, KPP_REAL Z1
11951223 }
11961224 /* Evaluate quadratic polynomial */
11971225 else if ( strncmp ( action , "eval" , 4 ) ) {
1226+ /* Safety check: prevent division by zero or near-zero Hold */
1227+ if (ABS (Hold ) <= ((KPP_REAL )10.0 )* WLAMCH ('E' )) {
1228+ return ; /* Hold is too small, cannot interpolate */
1229+ }
11981230 r = H / Hold ;
11991231 x1 = ONE + rkC [0 ]* r ;
12001232 x2 = ONE + rkC [1 ]* r ;
@@ -1258,6 +1290,11 @@ void RK_Decomp(int N, KPP_REAL H, KPP_REAL FJAC[], KPP_REAL E1[],
12581290 KPP_REAL Alpha , Beta , Gamma ;
12591291 int i ,j ;
12601292
1293+ /* Safety check: prevent division by zero or near-zero H */
1294+ if (ABS (H ) <= ((KPP_REAL )10.0 )* WLAMCH ('E' )) {
1295+ * ISING = 1 ;
1296+ return ;
1297+ }
12611298 Gamma = rkGamma / H ;
12621299 Alpha = rkAlpha / H ;
12631300 Beta = rkBeta / H ;
@@ -1318,6 +1355,10 @@ void RK_Solve(int N, KPP_REAL H, KPP_REAL E1[], int IP1[], KPP_REAL E2R[],
13181355 int i ;
13191356
13201357 /* Z <- h^{-1) T^{-1) A^{-1) x Z */
1358+ /* Safety check: prevent division by zero or near-zero H */
1359+ if (ABS (H ) <= ((KPP_REAL )10.0 )* WLAMCH ('E' )) {
1360+ return ; /* H is too small, skip this operation */
1361+ }
13211362 for (i = 0 ; i < N ; i ++ )
13221363 {
13231364 x1 = R1 [i ]/H ;
@@ -1368,6 +1409,11 @@ void RK_ErrorEstimate(int N, KPP_REAL H, KPP_REAL T, KPP_REAL Y[],
13681409 KPP_REAL HrkE1 ,HrkE2 ,HrkE3 ;
13691410 int i ;
13701411
1412+ /* Safety check: prevent division by zero or near-zero H */
1413+ if (ABS (H ) <= ((KPP_REAL )10.0 )* WLAMCH ('E' )) {
1414+ * Err = (KPP_REAL )1.0e10 ; /* Large error if H is too small */
1415+ return ;
1416+ }
13711417 HrkE1 = rkE [0 ]/H ;
13721418 HrkE2 = rkE [1 ]/H ;
13731419 HrkE3 = rkE [2 ]/H ;
@@ -1458,7 +1504,7 @@ void Radau2A_Coefficients()
14581504
14591505 rkB [0 ] = (KPP_REAL )(3.764030627004672750500754423692808e-01 );
14601506 rkB [1 ] = (KPP_REAL )(5.124858261884216138388134465196080e-01 );
1461- rkB [2 ] = (KPP_REAL )(1111111111111111111111111111111111e -01 );
1507+ rkB [2 ] = (KPP_REAL )(1.111111111111111111111111111111111e -01 );
14621508
14631509 rkC [0 ] = (KPP_REAL )(1.550510257216821901802715925294109e-01 );
14641510 rkC [1 ] = (KPP_REAL )(6.449489742783178098197284074705891e-01 );
@@ -1636,8 +1682,8 @@ void Lobatto3C_Coefficients ()
16361682 rkAlpha = (KPP_REAL )1.687091590520766641994055533117359 ;
16371683 rkBeta = (KPP_REAL )2.508731754924880510838743672432351 ;
16381684
1639- rkT [0 ][1 ] = ONE ;
1640- rkT [0 ][1 ] = ONE ;
1685+ rkT [0 ][0 ] = ( KPP_REAL ) .4554100411010284672111720348287483 ;
1686+ rkT [0 ][1 ] = ( KPP_REAL )( -.6027050205505142336055860174143743 ) ;
16411687 rkT [0 ][2 ] = ZERO ;
16421688 rkT [1 ][0 ] = (KPP_REAL ).4554100411010284672111720348287483 ;
16431689 rkT [1 ][1 ] = (KPP_REAL )(-.6027050205505142336055860174143743 );
0 commit comments