diff --git a/doc/manual/statements.tex b/doc/manual/statements.tex index b61b63e9..5a29f952 100644 --- a/doc/manual/statements.tex +++ b/doc/manual/statements.tex @@ -3780,6 +3780,13 @@ \section{off} \leftvitem{3.5cm}{highfirst\index{off!highfirst}} \rightvitem{13cm}{Puts the sorting in a low first mode.} +\leftvitem{3.5cm}{humanstatistics\index{off!humanstats}} +\rightvitem{13cm}{Disables the printing of human-readable numbers and +units in the statistics. This is the default.} + +\leftvitem{3.5cm}{humanstats\index{off!humanstats}} +\rightvitem{13cm}{Same as `Off humanstatistics;'} + \leftvitem{3.5cm}{insidefirst\index{off!insidefirst}} \rightvitem{13cm}{Not active at the moment.} @@ -3979,6 +3986,13 @@ \section{on} \rightvitem{13cm}{In this mode polynomials are sorted in a way that high powers come before low powers.} +\leftvitem{3.5cm}{humanstatistics\index{on!humanstats}} +\rightvitem{13cm}{If enabled, human-readable numbers and units are included +in the statistics printing. Disabled by default.} + +\leftvitem{3.5cm}{humanstats\index{on!humanstats}} +\rightvitem{13cm}{Same as the above humanstatistics.} + %\leftvitem{3.5cm}{indentspace\index{on!indentspace}} %\rightvitem{13cm}{Not active at the moment.} diff --git a/sources/compcomm.c b/sources/compcomm.c index ea52b1fa..bf70f7db 100644 --- a/sources/compcomm.c +++ b/sources/compcomm.c @@ -139,6 +139,8 @@ static KEYWORDV onoffoptions[] = { ,{"sortreallocate", &(AC.SortReallocateFlag), 1, 0} ,{"backtrace", &(AC.PrintBacktraceFlag), 1, 0} ,{"flint", &(AC.FlintPolyFlag), 1, 0} + ,{"humanstats", &(AC.HumanStatsFlag), 1, 0} + ,{"humanstatistics", &(AC.HumanStatsFlag), 1, 0} }; static WORD one = 1; diff --git a/sources/sort.c b/sources/sort.c index b54bed72..1b358814 100644 --- a/sources/sort.c +++ b/sources/sort.c @@ -82,6 +82,26 @@ LONG numcompares; char *toterms[] = { " ", " >>", "-->" }; +#define HUMANSTRLEN 12 +#define HUMANSUFFLEN 4 +const char humanTermsSuffix[HUMANSUFFLEN][4] = {"K ","M ","B ","T "}; +const char humanBytesSuffix[HUMANSUFFLEN][4] = {"KiB","MiB","GiB","TiB"}; +void HumanString(char* string, float input, const char suffix[HUMANSUFFLEN][4]) { + int ind = -1; + while (ind < 0 || (input >= 1000.0 && ind < HUMANSUFFLEN) ) { + input /= 1000.0; + ind++; + } + if ( input < 0.5 ) { + snprintf(string, HUMANSTRLEN, + " ( <1 %s)", suffix[ind]); + } + else { + snprintf(string, HUMANSTRLEN, + " (%3.f %s)", input, suffix[ind]); + } +} + /** * Writes the statistics. * @@ -124,6 +144,15 @@ void WriteStats(POSITION *plspace, WORD par, WORD checkLogType) S = AT.SS; + char humanGenTermsText[HUMANSTRLEN] = ""; + char humanTermsLeftText[HUMANSTRLEN] = ""; + char humanBytesText[HUMANSTRLEN] = ""; + if ( AC.HumanStatsFlag ) { + HumanString(humanGenTermsText, (float)(S->GenTerms), humanTermsSuffix); + HumanString(humanTermsLeftText, (float)(S->TermsLeft), humanTermsSuffix); + HumanString(humanBytesText, (float)(BASEPOSITION(*plspace)), humanBytesSuffix); + } + MLOCK(ErrorMessageLock); /* If the statistics should not go to the log file, temporarily hide the @@ -436,149 +465,149 @@ void WriteStats(POSITION *plspace, WORD par, WORD checkLogType) #if ( BITSINLONG > 32 ) if ( S->GenTerms >= 10000000000L ) { if ( use_wtime ) { - MesPrint("WTime = %7l.%2i sec Generated terms = %16l", - millitime,timepart,S->GenTerms); + MesPrint("WTime = %7l.%2i sec Generated terms = %16l%s", + millitime,timepart,S->GenTerms,humanGenTermsText); } else { - MesPrint("Time = %7l.%2i sec Generated terms = %16l", - millitime,timepart,S->GenTerms); + MesPrint("Time = %7l.%2i sec Generated terms = %16l%s", + millitime,timepart,S->GenTerms,humanGenTermsText); } } else { if ( use_wtime ) { - MesPrint("WTime = %7l.%2i sec Generated terms = %10l", - millitime,timepart,S->GenTerms); + MesPrint("WTime = %7l.%2i sec Generated terms = %10l%s", + millitime,timepart,S->GenTerms,humanGenTermsText); } else { - MesPrint("Time = %7l.%2i sec Generated terms = %10l", - millitime,timepart,S->GenTerms); + MesPrint("Time = %7l.%2i sec Generated terms = %10l%s", + millitime,timepart,S->GenTerms,humanGenTermsText); } } #else if ( use_wtime ) { - MesPrint("WTime = %7l.%2i sec Generated terms = %10l", - millitime,timepart,S->GenTerms); + MesPrint("WTime = %7l.%2i sec Generated terms = %10l%s", + millitime,timepart,S->GenTerms,humanGenTermsText); } else { - MesPrint("Time = %7l.%2i sec Generated terms = %10l", - millitime,timepart,S->GenTerms); + MesPrint("Time = %7l.%2i sec Generated terms = %10l%s", + millitime,timepart,S->GenTerms,humanGenTermsText); } #endif } #if ( BITSINLONG > 32 ) if ( par == STATSSPLITMERGE ) if ( S->TermsLeft >= 10000000000L ) { - MesPrint("%16s%8l Terms %s = %16l",EXPRNAME(AR.CurExpr), - AN.ninterms,FG.swmes[par],S->TermsLeft); + MesPrint("%16s%8l Terms %s = %16l%s",EXPRNAME(AR.CurExpr), + AN.ninterms,FG.swmes[par],S->TermsLeft,humanTermsLeftText); } else { - MesPrint("%16s%8l Terms %s = %10l",EXPRNAME(AR.CurExpr), - AN.ninterms,FG.swmes[par],S->TermsLeft); + MesPrint("%16s%8l Terms %s = %10l%s",EXPRNAME(AR.CurExpr), + AN.ninterms,FG.swmes[par],S->TermsLeft,humanTermsLeftText); } else { if ( S->TermsLeft >= 10000000000L ) { #ifdef WITHPTHREADS if ( identity > 0 && par == STATSPOSTSORT ) { - MesPrint("%16s Terms in thread = %16l", - EXPRNAME(AR.CurExpr),S->TermsLeft); + MesPrint("%16s Terms in thread = %16l%s", + EXPRNAME(AR.CurExpr),S->TermsLeft,humanTermsLeftText); } else #elif defined(WITHMPI) if ( PF.me != MASTER && par == STATSPOSTSORT ) { - MesPrint("%16s Terms in process= %16l", - EXPRNAME(AR.CurExpr),S->TermsLeft); + MesPrint("%16s Terms in process= %16l%s", + EXPRNAME(AR.CurExpr),S->TermsLeft,humanTermsLeftText); } else #endif { - MesPrint("%16s Terms %s = %16l", - EXPRNAME(AR.CurExpr),FG.swmes[par],S->TermsLeft); + MesPrint("%16s Terms %s = %16l%s", + EXPRNAME(AR.CurExpr),FG.swmes[par],S->TermsLeft,humanTermsLeftText); } } else { #ifdef WITHPTHREADS if ( identity > 0 && par == STATSPOSTSORT ) { - MesPrint("%16s Terms in thread = %10l", - EXPRNAME(AR.CurExpr),S->TermsLeft); + MesPrint("%16s Terms in thread = %10l%s", + EXPRNAME(AR.CurExpr),S->TermsLeft,humanTermsLeftText); } else #elif defined(WITHMPI) if ( PF.me != MASTER && par == STATSPOSTSORT ) { - MesPrint("%16s Terms in process= %10l", - EXPRNAME(AR.CurExpr),S->TermsLeft); + MesPrint("%16s Terms in process= %10l%s", + EXPRNAME(AR.CurExpr),S->TermsLeft,humanTermsLeftText); } else #endif { - MesPrint("%16s Terms %s = %10l", - EXPRNAME(AR.CurExpr),FG.swmes[par],S->TermsLeft); + MesPrint("%16s Terms %s = %10l%s", + EXPRNAME(AR.CurExpr),FG.swmes[par],S->TermsLeft,humanTermsLeftText); } } } #else if ( par == STATSSPLITMERGE ) - MesPrint("%16s%8l Terms %s = %10l",EXPRNAME(AR.CurExpr), - AN.ninterms,FG.swmes[par],S->TermsLeft); + MesPrint("%16s%8l Terms %s = %10l%s",EXPRNAME(AR.CurExpr), + AN.ninterms,FG.swmes[par],S->TermsLeft,humanTermsLeftText); else { #ifdef WITHPTHREADS if ( identity > 0 && par == STATSPOSTSORT ) { - MesPrint("%16s Terms in thread = %10l", - EXPRNAME(AR.CurExpr),S->TermsLeft); + MesPrint("%16s Terms in thread = %10l%s", + EXPRNAME(AR.CurExpr),S->TermsLeft,humanTermsLeftText); } else #elif defined(WITHMPI) if ( PF.me != MASTER && par == STATSPOSTSORT ) { - MesPrint("%16s Terms in process= %10l", - EXPRNAME(AR.CurExpr),S->TermsLeft); + MesPrint("%16s Terms in process= %10l%s", + EXPRNAME(AR.CurExpr),S->TermsLeft,humanTermsLeftText); } else #endif { - MesPrint("%16s Terms %s = %10l", - EXPRNAME(AR.CurExpr),FG.swmes[par],S->TermsLeft); + MesPrint("%16s Terms %s = %10l%s", + EXPRNAME(AR.CurExpr),FG.swmes[par],S->TermsLeft,humanTermsLeftText); } } #endif SETBASEPOSITION(pp,y); if ( ISLESSPOS(*plspace,pp) ) { - MesPrint("%24s Bytes used = %10p",AC.Commercial,plspace); + MesPrint("%24s Bytes used = %10p%s",AC.Commercial,plspace,humanBytesText); } else { y = 1000000000L; SETBASEPOSITION(pp,y); MULPOS(pp,100); if ( ISLESSPOS(*plspace,pp) ) { - MesPrint("%24s Bytes used =%11p",AC.Commercial,plspace); + MesPrint("%24s Bytes used =%11p%s",AC.Commercial,plspace,humanBytesText); } else { MULPOS(pp,10); if ( ISLESSPOS(*plspace,pp) ) { - MesPrint("%24s Bytes used =%12p",AC.Commercial,plspace); + MesPrint("%24s Bytes used =%12p%s",AC.Commercial,plspace,humanBytesText); } else { MULPOS(pp,10); if ( ISLESSPOS(*plspace,pp) ) { - MesPrint("%24s Bytes used =%13p",AC.Commercial,plspace); + MesPrint("%24s Bytes used =%13p%s",AC.Commercial,plspace,humanBytesText); } else { MULPOS(pp,10); if ( ISLESSPOS(*plspace,pp) ) { - MesPrint("%24s Bytes used =%14p",AC.Commercial,plspace); + MesPrint("%24s Bytes used =%14p%s",AC.Commercial,plspace,humanBytesText); } else { MULPOS(pp,10); if ( ISLESSPOS(*plspace,pp) ) { - MesPrint("%24s Bytes used =%15p",AC.Commercial,plspace); + MesPrint("%24s Bytes used =%15p%s",AC.Commercial,plspace,humanBytesText); } else { MULPOS(pp,10); if ( ISLESSPOS(*plspace,pp) ) { - MesPrint("%24s Bytes used =%16p",AC.Commercial,plspace); + MesPrint("%24s Bytes used =%16p%s",AC.Commercial,plspace,humanBytesText); } else { MULPOS(pp,10); if ( ISLESSPOS(*plspace,pp) ) { - MesPrint("%24s Bytes used=%17p",AC.Commercial,plspace); + MesPrint("%24s Bytes used=%17p%s",AC.Commercial,plspace,humanBytesText); } } } } } } } diff --git a/sources/startup.c b/sources/startup.c index a47899fd..5e3d47e7 100644 --- a/sources/startup.c +++ b/sources/startup.c @@ -1405,6 +1405,8 @@ WORD IniVars(void) #else AC.PrintBacktraceFlag = 0; #endif + /* Human-readable statistics are off by default */ + AC.HumanStatsFlag = 0; AC.extrasymbols = AM.gextrasymbols = AM.ggextrasymbols = 0; AC.extrasym = (UBYTE *)Malloc1(2*sizeof(UBYTE),"extrasym"); AM.gextrasym = (UBYTE *)Malloc1(2*sizeof(UBYTE),"extrasym"); diff --git a/sources/structs.h b/sources/structs.h index ad0ef6a7..001fc5aa 100644 --- a/sources/structs.h +++ b/sources/structs.h @@ -1873,6 +1873,7 @@ struct C_const { 2 : On, single module (set by #sortreallocate) */ int PrintBacktraceFlag; /* Print backtrace on terminate? */ int FlintPolyFlag; /* Use Flint for polynomial arithmetic */ + int HumanStatsFlag; /* Print human-readable stats in the stats print? */ int doloopstacksize; int dolooplevel; int CheckpointFlag; /**< Tells preprocessor whether checkpoint code must executed.