From 92fe5ba752c11357f28e52ac3460b0b76df38417 Mon Sep 17 00:00:00 2001 From: tradke Date: Tue, 22 May 2001 01:49:04 +0000 Subject: Count the number of NaNs found in a variable. This will be reported in a level 1 warning for each variable. The indices of all NaN elements in a grid array variable are also reported as level 2 warnings. An integer parameter 'NaNChecker::check_max' was added which limits the number of those warnings. Default is unlimited (0). This closes PR 693. git-svn-id: http://svn.cactuscode.org/arrangements/CactusUtils/NaNChecker/trunk@9 ff385933-4943-42dc-877b-ffc776028de6 --- README | 9 +++++++-- param.ccl | 6 ++++++ src/NaNCheck.c | 64 ++++++++++++++++++++++++++++++++++++++-------------------- 3 files changed, 55 insertions(+), 24 deletions(-) diff --git a/README b/README index 2c9882a..cb85656 100644 --- a/README +++ b/README @@ -21,10 +21,15 @@ and - in case a NaN was found - performs an action as specified in Currently these actions can be to - * just print a level 1 warning message telling you where the NaN occurred, + * just print a level 1 warning message telling you where NaNs were found + and how many (for grid array variables). + For grid arrays it will also print level 2 warnings with the array index + (in fortran order) for all NaN elements. You can limit the number of + such warnings by setting the 'NanChecker::check_max' parameter. * also set the CCTK termination flag so that Cactus will stop the evolution loop and gracefully terminate at the next time possible (giving you the choice of outputting the data from the last evolution timestep), - * print the warning and immediately terminate Cactus by a call to CCTK_Abort() + * print the warning message(s) and immediately terminate Cactus + by a call to CCTK_Abort() diff --git a/param.ccl b/param.ccl index 86a1265..6412151 100644 --- a/param.ccl +++ b/param.ccl @@ -12,6 +12,12 @@ INT check_every "How often to check for NaN's" STEERABLE = ALWAYS 1:* :: "Every so many iterations" } 0 +INT check_max "How many NaN's to report for a single variable" STEERABLE = ALWAYS +{ + 0 :: "Report all (default)" + 1:* :: "Do not report more than check_max number of NaN's" +} 0 + STRING check_vars "Groups and/or variables to check for NaN's" STEERABLE = ALWAYS { .* :: "List of full group and/or variable names, or 'all' for everything" diff --git a/src/NaNCheck.c b/src/NaNCheck.c index 0824cf3..9060308 100644 --- a/src/NaNCheck.c +++ b/src/NaNCheck.c @@ -19,7 +19,7 @@ #include "cctk_Termination.h" /* the rcsid and the macro to use it */ static char *rcsid = "$Header$"; -CCTK_FILEVERSION(BetaThorns_NaNChecker_NaNCheck_c) +CCTK_FILEVERSION(CactusUtils_NaNChecker_NaNCheck_c) /******************************************************************** @@ -90,9 +90,8 @@ int NaNChecker_NaNCheck (cGH *GH) @author Thomas Radke @date Sat 21 Apr 2001 @desc - Prints a level 1 warning for a Inf/NaN found in a variable - at the given processor-local linear index and terminates - Cactus if requested. + Prints a warning for a Inf/NaN found in a variable + at the given processor-local linear index. The warning includes the variable's fullname along with the global index of the NaN element in fortran order. @enddesc @@ -130,7 +129,6 @@ static void PrintWarning (const char *error_type, const char *fullname, const cGroupDynamicData *gdata) { - DECLARE_CCTK_PARAMETERS int i; char *index_string; const char *complex_part; @@ -166,22 +164,12 @@ static void PrintWarning (const char *error_type, (linear_index % gdata->lsh[i]) + gdata->lbnd[i] + 1); } - CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING, + CCTK_VWarn (2, __LINE__, __FILE__, CCTK_THORNSTRING, "%s caught in %svariable '%s' at (%s)", error_type, complex_part, fullname, index_string); free (index_string); } - - /* Do more than just print a warning ? */ - if (CCTK_Equals (action_if_found, "terminate")) - { - CCTK_TerminateNext (NULL); - } - else if (CCTK_Equals (action_if_found, "abort")) - { - CCTK_Abort (NULL, 0); - } } @@ -215,8 +203,12 @@ static void PrintWarning (const char *error_type, { \ if (! finite ((double) _typed_data[_i])) \ { \ - PrintWarning (isnan ((double) _typed_data[_i]) ? "NaN" : "Inf", \ - _i, fp_type, fullname, &gdata); \ + nans_found++; \ + if (check_max == 0 || nans_found <= check_max) \ + { \ + PrintWarning (isnan ((double) _typed_data[_i]) ? "NaN" : "Inf", \ + _i, fp_type, fullname, &gdata); \ + } \ } \ } \ } @@ -236,7 +228,11 @@ static void PrintWarning (const char *error_type, { \ if (isnan ((double) _typed_data[_i])) \ { \ - PrintWarning ("NaN", _i, fp_type, fullname, &gdata); \ + nans_found++; \ + if (check_max == 0 || nans_found <= check_max) \ + { \ + PrintWarning ("NaN", _i, fp_type, fullname, &gdata); \ + } \ } \ } \ } @@ -256,7 +252,9 @@ static void PrintWarning (const char *error_type, @author Thomas Radke @desc Checks a CCTK variable given by its index against NaN's. - Only floating point typed variables are checked. + It will issue a warning each time a NaN was found and also + terminate Cactus afterwards if requested. + Note that only floating point typed variables are checked.
This routine is called as a callback via CCTK_TraverseString(). @enddesc @@ -280,8 +278,9 @@ static void PrintWarning (const char *error_type, @@*/ static void NaNCheck (int vindex, const char *optstring, void *_GH) { - cGH *GH; - int i, fp_type; + DECLARE_CCTK_PARAMETERS + const cGH *GH; + int i, fp_type, nans_found; int vtype, gindex, nelems; char *fullname; const char *vtypename; @@ -341,6 +340,7 @@ static void NaNCheck (int vindex, const char *optstring, void *_GH) data = CCTK_VarDataPtrI (GH, 0, vindex); /* do the checking according to the variable's type */ + nans_found = 0; if (vtype == CCTK_VARIABLE_REAL || CCTK_VARIABLE_COMPLEX) { CHECK_DATA (CCTK_REAL); @@ -369,6 +369,26 @@ static void NaNCheck (int vindex, const char *optstring, void *_GH) "NanCheck: Unknown variable type '%s' for variable '%s'", vtypename, fullname); } + + /* Do more than just print a warning ? */ + if (nans_found > 0) + { + if (gdata.dim > 0) + { + CCTK_VWarn (1, __LINE__, __FILE__, CCTK_THORNSTRING, + "There were %d NaN/Inf value(s) found in variable '%s'", + nans_found, fullname); + } + + if (CCTK_Equals (action_if_found, "terminate")) + { + CCTK_TerminateNext (NULL); + } + else if (CCTK_Equals (action_if_found, "abort")) + { + CCTK_Abort (NULL, 0); + } + } } else { -- cgit v1.2.3