diff --git a/src/multio/action/encode-mtg2/EncodeMtg2.cc b/src/multio/action/encode-mtg2/EncodeMtg2.cc index 03dbf8a88..4c7d3dc6e 100644 --- a/src/multio/action/encode-mtg2/EncodeMtg2.cc +++ b/src/multio/action/encode-mtg2/EncodeMtg2.cc @@ -11,6 +11,7 @@ #include "EncodeMtg2.h" #include +#include #include "eckit/config/LocalConfiguration.h" #include "eckit/exception/Exceptions.h" @@ -34,11 +35,61 @@ namespace dm = multio::datamod; using message::Message; using message::Peer; +namespace { + +const std::unordered_set& supportedMars2gribOptions() { + static const auto supported = std::unordered_set{"applyChecks", + "enableOverride", + "enableBitsPerValueCompression", + "normalizeMars", + "normalizeMisc", + "fixMarsGrid", + "skipSection3", + "allowDefaultTimeIncrement", + "allowZeroLengthFsWindow", + "allowNonEnumeratedPositiveIntegerTimespanHours", + "allowRedundantTimeIncrement", + "allowMissingTimespanForInstantProduct", + "allowMissingTimespanForStatisticalProduct"}; + return supported; +} + +std::unique_ptr makeEncoder(const ComponentConfiguration& compConf) { + const auto& actionConf = compConf.parsedConfig(); + + if (!actionConf.has("mars2grib-options")) { + return std::make_unique(); + } + + if (!actionConf.isSubConfiguration("mars2grib-options")) { + throw EncodeMtg2Exception("encode-mtg2 option 'mars2grib-options' must be a configuration section", Here()); + } + + const auto rawEncoderConf = actionConf.getSubConfiguration("mars2grib-options"); + eckit::LocalConfiguration validatedEncoderConf{}; + + for (const auto& key : rawEncoderConf.keys()) { + if (supportedMars2gribOptions().find(key) == supportedMars2gribOptions().end()) { + throw EncodeMtg2Exception("Unsupported mars2grib option 'mars2grib-options." + key + "'", Here()); + } + + if (!rawEncoderConf.isBoolean(key)) { + throw EncodeMtg2Exception("mars2grib option 'mars2grib-options." + key + "' must be boolean", Here()); + } + + validatedEncoderConf.set(key, rawEncoderConf.getBool(key)); + } + + return std::make_unique(validatedEncoderConf); +} + +} // namespace + EncodeMtg2::EncodeMtg2(const ComponentConfiguration& compConf) : ChainedAction{compConf}, opts_{cf::parseActionConfig(compConf)}, - encoder_{}, + encoder_{makeEncoder(compConf)}, cache_{opts_.cached ? std::optional{Cache{}} : std::optional{}} {} @@ -49,6 +100,7 @@ std::unique_ptr encode(metkit::mars2grib::Mars2Grib& const auto mars = dm::dumpRecord(marsRec); const auto misc = dm::dumpUnscopedRecord(miscRec); + if (!cache) { return encoder.encode(values, size, mars, misc); } @@ -116,7 +168,7 @@ void EncodeMtg2::executeImpl(Message msg) { } // Call the GRIB2 encoder in metkit - const auto sample = encode(encoder_, cache_, values, size, marsRec, miscRec); + const auto sample = encode(*encoder_, cache_, values, size, marsRec, miscRec); eckit::Buffer buf{sample->messageSize()}; sample->copyInto(reinterpret_cast(buf.data()), buf.size()); diff --git a/src/multio/action/encode-mtg2/EncodeMtg2.h b/src/multio/action/encode-mtg2/EncodeMtg2.h index 329a1924b..0d160f5a8 100644 --- a/src/multio/action/encode-mtg2/EncodeMtg2.h +++ b/src/multio/action/encode-mtg2/EncodeMtg2.h @@ -10,6 +10,7 @@ #pragma once +#include #include #include "metkit/mars2grib/api/Mars2Grib.h" @@ -44,15 +45,11 @@ class EncodeMtg2 : public ChainedAction { void executeImpl(message::Message msg) override; private: - // Internal constructor delegate with prepared configuration for specific - // encoder - explicit EncodeMtg2(const ComponentConfiguration& compConf, const eckit::LocalConfiguration& encoderConf); - void print(std::ostream& os) const override; // TODO pgeier this option will be renamed and the action should get it own struct with parsing capabilities again EncodeMtg2Options opts_; - metkit::mars2grib::Mars2Grib encoder_; + std::unique_ptr encoder_; std::optional cache_; }; diff --git a/src/multio/action/encode-mtg2/fakeDoubleLoop.cc b/src/multio/action/encode-mtg2/fakeDoubleLoop.cc index 64cf872d4..25e7b4ce6 100644 --- a/src/multio/action/encode-mtg2/fakeDoubleLoop.cc +++ b/src/multio/action/encode-mtg2/fakeDoubleLoop.cc @@ -19,6 +19,7 @@ #include "eckit/config/LocalConfiguration.h" #include "eckit/config/YAMLConfiguration.h" #include "eckit/filesystem/PathName.h" +#include "eckit/types/DateTime.h" namespace multio::action::encode_mtg2::fake_double_loop { @@ -34,7 +35,9 @@ enum class TypeOfStatisticalProcessing : std::int64_t Minimum = 3, Difference = 4, StandardDeviation = 6, - InverseDifference = 8 + InverseDifference = 8, + Severity = 100, + Mode = 101 }; @@ -54,6 +57,10 @@ TypeOfStatisticalProcessing typeOfStatisticalProcessingFromInt(std::int64_t valu return TypeOfStatisticalProcessing::StandardDeviation; case 8: return TypeOfStatisticalProcessing::InverseDifference; + case 100: + return TypeOfStatisticalProcessing::Severity; + case 101: + return TypeOfStatisticalProcessing::Mode; default: { std::ostringstream os; os << "Unknown typeOfStatisticalProcessing value: " << value; @@ -74,6 +81,8 @@ bool isValidStattypeOperation(TypeOfStatisticalProcessing operation) { case TypeOfStatisticalProcessing::Accumulation: case TypeOfStatisticalProcessing::Difference: case TypeOfStatisticalProcessing::InverseDifference: + case TypeOfStatisticalProcessing::Severity: + case TypeOfStatisticalProcessing::Mode: return false; } @@ -95,6 +104,8 @@ std::string stattypeOperationCode(TypeOfStatisticalProcessing operation) { case TypeOfStatisticalProcessing::Accumulation: case TypeOfStatisticalProcessing::Difference: case TypeOfStatisticalProcessing::InverseDifference: + case TypeOfStatisticalProcessing::Severity: + case TypeOfStatisticalProcessing::Mode: break; } @@ -137,7 +148,8 @@ class LocalStatisticsOperationMapping { for (const auto& mapping : mappingConf.getSubConfigurations()) { const auto param = mapping.getInt64("param"); const auto typeOfStatisticalProcessing = mapping.getInt64("typeOfStatisticalProcessing"); - + // std::cout << "MIVAL: Mapping param: " << param << " to typeOfStatisticalProcessing: " + // << typeOfStatisticalProcessing << std::endl; operationMappings.emplace(param, typeOfStatisticalProcessingFromInt(typeOfStatisticalProcessing)); } @@ -181,6 +193,13 @@ bool requiresFakeDoubleLoopRepresentation(const dm::FullMarsRecord& marsRec) { return false; } +bool isSeasonal(const dm::FullMarsRecord& marsRec) { + std::string klass = marsRec.klass.get(); + std::string stream = marsRec.stream.get(); + + return (klass == "od" || klass == "rd" || klass == "c3") && (stream == "sfmd" || stream == "shmd"); +} + std::optional operationCodeFromParam(std::int64_t param) { // This is the full @@ -228,7 +247,7 @@ std::string reconstructStatType(const dm::FullMarsRecord& marsRec) { // Create statType by concatenating operation code and period code if (operationCode && periodCode) { - return *operationCode + *periodCode; + return *periodCode + *operationCode; } else { std::ostringstream os; @@ -238,7 +257,49 @@ std::string reconstructStatType(const dm::FullMarsRecord& marsRec) { } } -} // namespace detail +long computeFcmonth(const dm::FullMarsRecord& marsRec) { + if (!marsRec.step.isSet()) { + throw eckit::SeriousBug("Cannot compute fcmonth for seasonal record without step", Here()); + } + + const eckit::Date epochDate{marsRec.date.get()}; + const long epochTime = marsRec.time.get(); + const auto epochHour = epochTime / 10000; + const auto epochMinute = (epochTime % 10000) / 100; + const eckit::DateTime epochDateTime{epochDate, eckit::Time{epochHour, epochMinute, 0}}; + const eckit::DateTime currentDateTime + = epochDateTime + static_cast(marsRec.step.get().toHours() * 3600); + + const auto isBeginningOfMonth = [](const eckit::DateTime& dt) { + return dt.date().day() == 1 && dt.time().hours() == 0 && dt.time().minutes() == 0 && dt.time().seconds() == 0; + }; + + if (!isBeginningOfMonth(epochDateTime)) { + std::ostringstream os; + os << "Cannot compute fcmonth: epochDateTime is not at the beginning of a month: " << epochDateTime; + throw eckit::SeriousBug(os.str(), Here()); + } + + if (!isBeginningOfMonth(currentDateTime)) { + std::ostringstream os; + os << "Cannot compute fcmonth: currentDateTime is not at the beginning of a month: " << currentDateTime; + throw eckit::SeriousBug(os.str(), Here()); + } + + const long fcmonth = static_cast((currentDateTime.date().year() - epochDateTime.date().year()) * 12 + + (currentDateTime.date().month() - epochDateTime.date().month())); + + if (fcmonth < 0) { + std::ostringstream os; + os << "Cannot compute fcmonth: currentDateTime precedes epochDateTime: " << currentDateTime << " < " + << epochDateTime; + throw eckit::SeriousBug(os.str(), Here()); + } + + return fcmonth; +} + +} // namespace detail void fakeDoubleLoop(dm::FullMarsRecord& marsRec) { @@ -249,6 +310,11 @@ void fakeDoubleLoop(dm::FullMarsRecord& marsRec) { marsRec.timespan.set(dm::TypeParser::parse("none")); } } + if (detail::isSeasonal(marsRec)) { + const long fcmonth = detail::computeFcmonth(marsRec); + marsRec.fcmonth.set(fcmonth); + marsRec.step.unset(); + } } -} // namespace multio::action::encode_mtg2::fake_double_loop \ No newline at end of file +} // namespace multio::action::encode_mtg2::fake_double_loop diff --git a/src/multio/action/print/Print.cc b/src/multio/action/print/Print.cc index 06b45aaea..dbb35b8be 100644 --- a/src/multio/action/print/Print.cc +++ b/src/multio/action/print/Print.cc @@ -11,16 +11,34 @@ #include "Print.h" #include +#include +#include #include "eckit/config/Configuration.h" +#include "eckit/config/LocalConfiguration.h" #include "eckit/exception/Exceptions.h" #include "eckit/log/Log.h" +#include "multio/datamod/MarsMiscGeo.h" +#include "multio/datamod/core/EntryDumper.h" + +#include "multio/datamod/ContainerInterop.h" +#include "multio/datamod/MarsMiscGeo.h" +#include "multio/datamod/core/EntryDumper.h" +#include "multio/datamod/core/EntryParser.h" +#include "multio/datamod/core/Record.h" +#include "multio/message/Parametrization.h" +#include "multio/util/PrecisionTag.h" + namespace multio::action::print { +namespace dm = multio::datamod; + Print::Print(const ComponentConfiguration& compConf) : ChainedAction(compConf) { stream_ = compConf.parsedConfig().getString("stream", "info"); onlyFields_ = compConf.parsedConfig().getBool("only-fields", false); + marsStream_ = (stream_ == "mars"); + count_ = 1; if (stream_ == "info") { os_ = &eckit::Log::info(); @@ -31,6 +49,9 @@ Print::Print(const ComponentConfiguration& compConf) : ChainedAction(compConf) { else if (stream_ == "cout") { os_ = &std::cout; } + else if (stream_ == "mars") { + os_ = &std::cout; + } else { os_ = &eckit::Log::debug(); } @@ -38,16 +59,59 @@ Print::Print(const ComponentConfiguration& compConf) : ChainedAction(compConf) { prefix_ = compConf.parsedConfig().getString("prefix", ""); } +void Print::printPrefix(std::ostream& os) const { + if (!prefix_.empty()) { + os << prefix_ << ": "; + } +} + +void Print::printMars(std::ostream& os, const message::Message& msg) const { + if (msg.tag() == message::Message::Tag::Field) { + auto mars = dm::readRecord(msg.metadata()); + auto md = dm::dumpRecord(mars); + + // printPrefix(os); + os << prefix_ << ": Field: " << std::setw(6) << count_++ << " :: \"mars\":"; + os << md << std::endl; + return; + } + + if (msg.tag() == message::Message::Tag::Flush) { + count_ = 1; + // printPrefix(os); + long flushKind = msg.metadata().getOpt("flushKind").value_or(-1); + if (flushKind == 1) { + long step = msg.metadata().getOpt("step").value_or(-1); + os << prefix_ << ": Flush: step=" << step << std::endl; + } + else { + os << prefix_ << ": Flush: " << flushKind << std::endl; + } + os << std::endl << std::endl; + } +} + void Print::executeImpl(message::Message msg) { ASSERT(os_); bool doOutput = onlyFields_ ? (msg.tag() == message::Message::Tag::Field) : true; if (doOutput) { - if (!prefix_.empty()) { - std::cout << prefix_ << ": "; + if (marsStream_) { + printMars(*os_, msg); + } + else { + printPrefix(*os_); + *os_ << msg << std::endl; } - std::cout << msg << std::endl; } - executeNext(std::move(msg)); + // try { + executeNext(std::move(msg)); + // } + // catch (...) { + // std::cerr << "Received \"mars\":"; + // printMars(std::cerr, msg); + // std::cerr << "# =======================================================================================" << std::endl; + // std::cerr << std::endl << std::endl << std::endl << std::endl << std::endl << std::endl << std::endl; + // } } void Print::print(std::ostream& os) const { diff --git a/src/multio/action/print/Print.h b/src/multio/action/print/Print.h index 40b1b8271..3cb91ffdb 100644 --- a/src/multio/action/print/Print.h +++ b/src/multio/action/print/Print.h @@ -30,9 +30,13 @@ class Print : public ChainedAction { private: void print(std::ostream& os) const override; + void printPrefix(std::ostream& os) const; + void printMars(std::ostream& os, const message::Message& msg) const; bool onlyFields_; std::string stream_; + bool marsStream_; + mutable long count_; std::ostream* os_; std::string prefix_; diff --git a/src/multio/action/statistics-mtg2/Statistics.cc b/src/multio/action/statistics-mtg2/Statistics.cc index 1667d4ac1..0116664c7 100644 --- a/src/multio/action/statistics-mtg2/Statistics.cc +++ b/src/multio/action/statistics-mtg2/Statistics.cc @@ -25,6 +25,7 @@ #include "multio/datamod/core/EntryParser.h" #include "multio/datamod/types/StatType.h" #include "multio/message/Message.h" +#include "multio/util/DateTime.h" #include "multio/util/Timing.h" #include "multio/action/statistics-mtg2/cfg/StatisticsConfiguration.h" @@ -411,9 +412,20 @@ void Statistics::emitStatistics(TemporalStatistics& ts, message::Peer source, me auto opname = (*it)->operation(); if (opname != "instant") { if (currentLoop == 1) { - const std::int64_t timespan = ts.win().currPointInHours() - ts.win().creationPointInHours(); + const std::int64_t timespan = ts.cwin().currPointInHours() - ts.cwin().creationPointInHours(); dm::dumpEntry(dm::TIMESPAN, dm::TIMESPAN.makeEntry(timespan), md); paramMapping_.applyMapping(md, opname, !opt_.disableStrictMapping()); + std::int64_t ldm = util::lastDayOfTheMonth(ts.cwin().creationPoint().date().year(), ts.cwin().creationPoint().date().month()); + if (ts.periodName() == "month" && ts.cwin().creationPoint().date().day() != 1) { + std::cout << "Skipping first month because it is not a full month :: " << ts.cwin().creationPoint() + << std::endl; + return; // Skip the first month if it is not a full month, as discussed with DGOV and scientists + } + if (ts.periodName() == "day" && ts.cwin().creationPoint().time().hours() != 1) { + std::cout << "Skipping first day because it is not a full day :: " << ts.cwin().creationPoint() + << std::endl; + return; // Skip the first day if it is not a full day, as discussed with DGOV and scientists + } } else { if (!opt_.disableSquashing() @@ -433,6 +445,7 @@ void Statistics::emitStatistics(TemporalStatistics& ts, message::Peer source, me dm::dumpEntry(dm::TIMESPAN, timespan, md); } else { + auto currentStatType = dm::SingleStatType{outputFreqencyToStatTypeDuration(outputFrequency_), operationNameToStatTypeOperation(opname)}; diff --git a/src/multio/action/statistics-mtg2/TemporalStatistics.h b/src/multio/action/statistics-mtg2/TemporalStatistics.h index 46d5a75da..f8d5422b7 100644 --- a/src/multio/action/statistics-mtg2/TemporalStatistics.h +++ b/src/multio/action/statistics-mtg2/TemporalStatistics.h @@ -37,6 +37,8 @@ class TemporalStatistics { const OperationWindow& cwin() const; OperationWindow& win(); + std::string periodName() const { return periodUpdater_->name(); }; + message::Metadata& metadata(); void print(std::ostream& os) const; diff --git a/src/multio/action/statistics-mtg2/TimeUtils.cc b/src/multio/action/statistics-mtg2/TimeUtils.cc index 7f7b0456c..000dace56 100644 --- a/src/multio/action/statistics-mtg2/TimeUtils.cc +++ b/src/multio/action/statistics-mtg2/TimeUtils.cc @@ -12,7 +12,7 @@ eckit::DateTime epochDateTime(const message::Message& msg, const StatisticsConfi eckit::DateTime currentDateTime(const message::Message& msg, const StatisticsConfiguration& cfg) { - return epochDateTime(msg, cfg) + static_cast(cfg.step() * cfg.timeIncrementInSeconds()); + return epochDateTime(msg, cfg) + static_cast(cfg.step() * 3600); } diff --git a/src/multio/action/statistics-mtg2/cfg/StatisticsConfiguration.cc b/src/multio/action/statistics-mtg2/cfg/StatisticsConfiguration.cc index f74708a4e..3057c6761 100644 --- a/src/multio/action/statistics-mtg2/cfg/StatisticsConfiguration.cc +++ b/src/multio/action/statistics-mtg2/cfg/StatisticsConfiguration.cc @@ -132,7 +132,7 @@ eckit::DateTime StatisticsConfiguration::computeEpoch() const { eckit::DateTime StatisticsConfiguration::computeCurr() const { - return epoch() + static_cast(std::max(step(), static_cast(0)) * timeIncrementInSeconds()); + return epoch() + static_cast(std::max(step(), static_cast(0)) * 3600); } diff --git a/src/multio/tools/utils/distGrib1ToGrib2Logging.cc b/src/multio/tools/utils/distGrib1ToGrib2Logging.cc index 489cbcc07..f0aaf6b4e 100644 --- a/src/multio/tools/utils/distGrib1ToGrib2Logging.cc +++ b/src/multio/tools/utils/distGrib1ToGrib2Logging.cc @@ -194,6 +194,8 @@ const char* toString(ExtractionOutcomeCode code) { return "ArchiveFailedSinkWrite"; case ExtractionOutcomeCode::ExtractFailedUnknownException: return "ExtractFailedUnknownException"; + case ExtractionOutcomeCode::ExtractFailedComplexExclusion: + return "ExtractFailedComplexExclusion"; } return "UnknownExtractionOutcomeCode"; } diff --git a/src/multio/tools/utils/grib2MarsMisc.cc b/src/multio/tools/utils/grib2MarsMisc.cc index f1b262eb9..0d7a6c2e3 100644 --- a/src/multio/tools/utils/grib2MarsMisc.cc +++ b/src/multio/tools/utils/grib2MarsMisc.cc @@ -466,7 +466,7 @@ namespace extract { void handlePackingType(metkit::codes::CodesHandle& h, const std::string& packingType, dm::FullMarsRecord& mars) { const static std::unordered_map packingMap{ {"grid_simple", "ccsds"}, {"grid_complex", "complex"}, {"spectral_complex", "complex"}, - {"grid_ccsds", "ccsds"}, {"grid_ieee", "ccsds"}, {"grid_second_order", "ccsds"}}; + {"grid_ccsds", "ccsds"}, {"grid_ieee", "ccsds"}, {"grid_second_order", "ccsds"}}; const auto packingTypeVal = packingMap.find(packingType); if (packingTypeVal == packingMap.cend()) { @@ -912,11 +912,10 @@ MessageDisposition classifyTimespanNonPositive(const TimeSpanEqualToZeroHandling } MessageDisposition classifyComplexExclusion() { - return MessageDisposition::ComplexExclusion; + return MessageDisposition::ComplexExclusion; } - ExtractionOutcome makeOutcome(MessageDisposition disposition, ExtractionOutcomeCode code, std::string reason, std::string detail = {}) { return ExtractionOutcome{disposition, code, std::move(reason), std::move(detail)}; @@ -1229,8 +1228,9 @@ Grib2MarsMiscResult grib2MarsMisc(const eckit::message::Message& msg, const Grib } - if (marsConfig.has("param") && marsConfig.has("levtype") && marsConfig.has("levelist") ) { - if ( marsConfig.getLong("param") == 152 && marsConfig.getString("levtype") == "ml" && marsConfig.getLong("levelist") == 100000 ) { + if (marsConfig.has("param") && marsConfig.has("levtype") && marsConfig.has("levelist")) { + if (marsConfig.getLong("param") == 152 && marsConfig.getString("levtype") == "ml" + && marsConfig.getLong("levelist") == 100000) { const auto disposition = classifyComplexExclusion(); const auto code = (disposition == MessageDisposition::ComplexExclusion) ? ExtractionOutcomeCode::ExtractFailedComplexExclusion diff --git a/src/multiom/ifs2mars/output-manager/model_data2multio_mod.F90 b/src/multiom/ifs2mars/output-manager/model_data2multio_mod.F90 index 060023a72..b3a9a5b1f 100644 --- a/src/multiom/ifs2mars/output-manager/model_data2multio_mod.F90 +++ b/src/multiom/ifs2mars/output-manager/model_data2multio_mod.F90 @@ -1095,6 +1095,7 @@ PP_THREAD_SAFE FUNCTION MODEL_DATA2MULTIO_GET_MARS_FROM_ATM( THIS, YDMSG, MSG, P USE :: IFS2MARS_MOD, ONLY: IFS2MARS_SET_ANALYSIS USE :: IFS2MARS_MOD, ONLY: IFS2MARS_SET_ENSEMBLE USE :: IFS2MARS_MOD, ONLY: IFS2MARS_SET_SYSTEM_METHOD + USE :: IFS2MARS_MOD, ONLY: ATM2MARS_SET_SATELLITE USE :: IFS2MARS_MOD, ONLY: ATM2MARS_SET_PARAM USE :: IFS2MARS_MOD, ONLY: IFS2MARS_SET_DATETIME USE :: IFS2MARS_MOD, ONLY: IFS2MARS_SET_GEOMETRY @@ -1146,6 +1147,7 @@ PP_THREAD_SAFE FUNCTION MODEL_DATA2MULTIO_GET_MARS_FROM_ATM( THIS, YDMSG, MSG, P INTEGER(KIND=JPIB_K), PARAMETER :: ERRFLAG_UNEXPECTED_REPRESENTATION=14_JPIB_K INTEGER(KIND=JPIB_K), PARAMETER :: ERRFLAG_UNABLE_TO_SET_TABLES_VERSION=15_JPIB_K INTEGER(KIND=JPIB_K), PARAMETER :: ERRFLAG_UNABLE_TO_SET_MODEL=16_JPIB_K + INTEGER(KIND=JPIB_K), PARAMETER :: ERRFLAG_UNABLE_TO_SET_SATELLITE=17_JPIB_K ! Local variables declared by the preprocessor for debugging purposes PP_DEBUG_DECL_VARS @@ -1176,6 +1178,7 @@ PP_THREAD_SAFE FUNCTION MODEL_DATA2MULTIO_GET_MARS_FROM_ATM( THIS, YDMSG, MSG, P PP_TRYCALL(ERRFLAG_UNABLE_TO_SET_ANALYSIS) IFS2MARS_SET_ANALYSIS( YDMSG, THIS%MODEL_PAR_, MSG, PAR, HOOKS ) PP_TRYCALL(ERRFLAG_UNABLE_TO_SET_ENSEMBLE) IFS2MARS_SET_ENSEMBLE( YDMSG, THIS%MODEL_PAR_, MSG, PAR, HOOKS ) PP_TRYCALL(ERRFLAG_UNABLE_TO_SET_ENSEMBLE) IFS2MARS_SET_SYSTEM_METHOD( YDMSG, THIS%MODEL_PAR_, MSG, PAR, HOOKS ) + PP_TRYCALL(ERRFLAG_UNABLE_TO_SET_SATELLITE) ATM2MARS_SET_SATELLITE( YDMSG, THIS%MODEL_PAR_, MSG, PAR, HOOKS ) PP_TRYCALL(ERRFLAG_UNABLE_TO_SET_PARAM) ATM2MARS_SET_PARAM ( YDMSG, THIS%MODEL_PAR_, MSG, PAR, HOOKS ) PP_TRYCALL(ERRFLAG_UNABLE_TO_SET_DATETIME) IFS2MARS_SET_DATETIME( YDMSG, THIS%MODEL_PAR_, MSG, PAR, HOOKS, IS_VALID ) PP_TRYCALL(ERRFLAG_UNABLE_TO_SET_TABLES_VERSION) IFS2MARS_SET_TABLES_VERSION( YDMSG, THIS%MODEL_PAR_, MSG, PAR, HOOKS ) @@ -1250,6 +1253,8 @@ PP_THREAD_SAFE FUNCTION MODEL_DATA2MULTIO_GET_MARS_FROM_ATM( THIS, YDMSG, MSG, P PP_DEBUG_PUSH_MSG_TO_FRAME( 'Unable to set the tables version' ) CASE (ERRFLAG_UNABLE_TO_SET_MODEL) PP_DEBUG_PUSH_MSG_TO_FRAME( 'Unable to set the model' ) + CASE (ERRFLAG_UNABLE_TO_SET_SATELLITE) + PP_DEBUG_PUSH_MSG_TO_FRAME( 'Unable to set satellite keys (channel, ident, instrument)' ) CASE DEFAULT PP_DEBUG_PUSH_MSG_TO_FRAME( 'Unhandled error' ) END SELECT @@ -2474,7 +2479,7 @@ PP_THREAD_SAFE FUNCTION MODEL_DATA2MULTIO_WRITE_WAM_DP( THIS, YDMSG, VALUES_DP, ERR = MIOMD%DELETE() PP_DEBUG_DEVELOP_COND_THROW( ERR.NE.MULTIO_SUCCESS, ERRFLAG_UNABLE_TO_DELETE_MIOMD ) - + ENDIF !> Free the message/parametrization @@ -2908,6 +2913,7 @@ PP_THREAD_SAFE FUNCTION MODEL_DATA2MULTIO_FLUSH_STEP( THIS, KSTEP, HOOKS ) RESUL ! Local variables CHARACTER(LEN=128) :: CLTMP INTEGER(KIND=JPIB_K) :: STATUS + INTEGER(KIND=JPIB_K) :: LOCAL_STEP ! Error flags INTEGER(KIND=JPIB_K), PARAMETER :: ERRFLAG_PROFILE_FLUSH=1_JPIB_K @@ -2931,15 +2937,19 @@ PP_THREAD_SAFE FUNCTION MODEL_DATA2MULTIO_FLUSH_STEP( THIS, KSTEP, HOOKS ) RESUL ! Initialization of good path return value PP_SET_ERR_SUCCESS( RET ) + + ! Compute local step (step in hours) + LOCAL_STEP = (KSTEP * INT( THIS%MODEL_PAR_%SIM_%TSTEP, KIND=JPIB_K ) )/ 3600_JPIB_K + ! Profile IF ( THIS%PROFILE_ ) THEN - PP_TRYCALL(ERRFLAG_PROFILE_FLUSH) PROFILE_FLUSH( THIS%PROFILE_DATA_, KSTEP, HOOKS ) + PP_TRYCALL(ERRFLAG_PROFILE_FLUSH) PROFILE_FLUSH( THIS%PROFILE_DATA_, LOCAL_STEP, HOOKS ) ENDIF ! If needed log step IF ( THIS%VERBOSE_ ) THEN CLTMP = REPEAT(' ',128) - WRITE(CLTMP, '(I10)', IOSTAT=STATUS ) KSTEP + WRITE(CLTMP, '(I10)', IOSTAT=STATUS ) LOCAL_STEP PP_DEBUG_CRITICAL_COND_THROW( STATUS .NE. 0, ERRFLAG_UNABLE_TO_WRITE ) PP_TRYCALL(ERRFLAG_UNABLE_TO_LOG_TIME) LOG_CURR_TIME( THIS%LOG_UNIT_, 'FLUSH STEP: '//TRIM(ADJUSTL(CLTMP)), HOOKS ) ENDIF @@ -2949,7 +2959,7 @@ PP_THREAD_SAFE FUNCTION MODEL_DATA2MULTIO_FLUSH_STEP( THIS, KSTEP, HOOKS ) RESUL ! PP_TRYCALL(ERRFLAG_ENCODER_COMMIT) THIS%MULTIOM_ENCODER_%COMMIT( HOOKS ) ! Send to MultIO the flush for the last step - PP_TRYCALL(ERRFLAG_UNABLE_TO_FLUSH_MULTIO) MULTIO_FLUSH( THIS%MIO_, KSTEP, HOOKS ) + PP_TRYCALL(ERRFLAG_UNABLE_TO_FLUSH_MULTIO) MULTIO_FLUSH( THIS%MIO_, LOCAL_STEP, HOOKS ) ! Trace end of procedure (on success) PP_TRACE_EXIT_PROCEDURE_ON_SUCCESS() @@ -3047,6 +3057,7 @@ PP_THREAD_SAFE FUNCTION MODEL_DATA2MULTIO_FLUSH_LAST_STEP( THIS, KSTEP, HOOKS ) ! Local variables CHARACTER(LEN=128) :: CLTMP INTEGER(KIND=JPIB_K) :: STATUS + INTEGER(KIND=JPIB_K) :: LOCAL_STEP ! Error flags INTEGER(KIND=JPIB_K), PARAMETER :: ERRFLAG_PROFILE_FLUSH=1_JPIB_K @@ -3070,21 +3081,24 @@ PP_THREAD_SAFE FUNCTION MODEL_DATA2MULTIO_FLUSH_LAST_STEP( THIS, KSTEP, HOOKS ) ! Initialization of good path return value PP_SET_ERR_SUCCESS( RET ) + ! Compute local step (step in hours) + LOCAL_STEP = (KSTEP * INT( THIS%MODEL_PAR_%SIM_%TSTEP, KIND=JPIB_K ) )/ 3600_JPIB_K + ! Profile IF ( THIS%PROFILE_ ) THEN - PP_TRYCALL(ERRFLAG_PROFILE_FLUSH) PROFILE_FLUSH_LAST_STEP( THIS%PROFILE_DATA_, KSTEP, HOOKS ) + PP_TRYCALL(ERRFLAG_PROFILE_FLUSH) PROFILE_FLUSH_LAST_STEP( THIS%PROFILE_DATA_, LOCAL_STEP, HOOKS ) ENDIF ! If needed log step IF ( THIS%VERBOSE_ ) THEN CLTMP = REPEAT(' ',128) - WRITE(CLTMP, '(I10)', IOSTAT=STATUS ) KSTEP + WRITE(CLTMP, '(I10)', IOSTAT=STATUS ) LOCAL_STEP PP_DEBUG_CRITICAL_COND_THROW( STATUS .NE. 0, ERRFLAG_UNABLE_TO_WRITE ) PP_TRYCALL(ERRFLAG_UNABLE_TO_LOG_TIME) LOG_CURR_TIME( THIS%LOG_UNIT_, 'FLUSH STEP: '//TRIM(ADJUSTL(CLTMP)), HOOKS ) ENDIF ! Send to MultIO the flush for the last step - PP_TRYCALL(ERRFLAG_UNABLE_TO_FLUSH_MULTIO) MULTIO_FLUSH_LAST_STEP( THIS%MIO_, KSTEP, HOOKS ) + PP_TRYCALL(ERRFLAG_UNABLE_TO_FLUSH_MULTIO) MULTIO_FLUSH_LAST_STEP( THIS%MIO_, LOCAL_STEP, HOOKS ) ! Trace end of procedure (on success) PP_TRACE_EXIT_PROCEDURE_ON_SUCCESS() @@ -3183,6 +3197,7 @@ PP_THREAD_SAFE FUNCTION MODEL_DATA2MULTIO_FLUSH_STEP_AND_TRIGGER_RESTART( THIS, ! Local variables CHARACTER(LEN=128) :: CLTMP INTEGER(KIND=JPIB_K) :: STATUS + INTEGER(KIND=JPIB_K) :: LOCAL_STEP ! Error flags INTEGER(KIND=JPIB_K), PARAMETER :: ERRFLAG_PROFILE_FLUSH=1_JPIB_K @@ -3207,15 +3222,18 @@ PP_THREAD_SAFE FUNCTION MODEL_DATA2MULTIO_FLUSH_STEP_AND_TRIGGER_RESTART( THIS, ! Initialization of good path return value PP_SET_ERR_SUCCESS( RET ) + ! Compute local step (step in hours) + LOCAL_STEP = (KSTEP * INT( THIS%MODEL_PAR_%SIM_%TSTEP, KIND=JPIB_K ) )/ 3600_JPIB_K + ! Profile IF ( THIS%PROFILE_ ) THEN - PP_TRYCALL(ERRFLAG_PROFILE_FLUSH) PROFILE_FLUSH_AND_RESTART( THIS%PROFILE_DATA_, KSTEP, HOOKS ) + PP_TRYCALL(ERRFLAG_PROFILE_FLUSH) PROFILE_FLUSH_AND_RESTART( THIS%PROFILE_DATA_, LOCAL_STEP, HOOKS ) ENDIF ! If needed log step IF ( THIS%VERBOSE_ ) THEN CLTMP = REPEAT(' ',128) - WRITE(CLTMP, '(I10)', IOSTAT=STATUS ) KSTEP + WRITE(CLTMP, '(I10)', IOSTAT=STATUS ) LOCAL_STEP PP_DEBUG_CRITICAL_COND_THROW( STATUS .NE. 0, ERRFLAG_UNABLE_TO_WRITE ) PP_TRYCALL(ERRFLAG_UNABLE_TO_LOG_TIME) LOG_CURR_TIME( THIS%LOG_UNIT_, 'FLUSH STEP: '//TRIM(ADJUSTL(CLTMP)), HOOKS ) ENDIF @@ -3225,7 +3243,7 @@ PP_THREAD_SAFE FUNCTION MODEL_DATA2MULTIO_FLUSH_STEP_AND_TRIGGER_RESTART( THIS, ! PP_TRYCALL(ERRFLAG_ENCODER_COMMIT) THIS%MULTIOM_ENCODER_%COMMIT( HOOKS ) ! Send to MultIO the flush for the last step - PP_TRYCALL(ERRFLAG_UNABLE_TO_FLUSH_MULTIO) MULTIO_FLUSH_AND_TRIGGER_RESTART( THIS%MIO_, KSTEP, HOOKS ) + PP_TRYCALL(ERRFLAG_UNABLE_TO_FLUSH_MULTIO) MULTIO_FLUSH_AND_TRIGGER_RESTART( THIS%MIO_, LOCAL_STEP, HOOKS ) ! Trace end of procedure (on success) PP_TRACE_EXIT_PROCEDURE_ON_SUCCESS() diff --git a/src/multiom/tools/multiom_tools_utils_mod.F90 b/src/multiom/tools/multiom_tools_utils_mod.F90 index 7dc30e6be..99e759892 100644 --- a/src/multiom/tools/multiom_tools_utils_mod.F90 +++ b/src/multiom/tools/multiom_tools_utils_mod.F90 @@ -28,12 +28,15 @@ MODULE MULTIOM_TOOLS_UTILS_MOD ! Verbosity of the hooks LOGICAL :: HOOK_VERBOSE=.FALSE. +INTEGER(KIND=JPIB_K) :: MSG_COUNT=0_JPIB_K +INTEGER(KIND=JPIB_K) :: TIMESTEP_IN_SECONDS=3600_JPIB_K +INTEGER(KIND=JPIB_K), PARAMETER :: HOURS2SECONDS=3600_JPIB_K ! Format of the print INTEGER(KIND=JPIB_K), PARAMETER :: CELL_SIZE = 16_JPIB_K -INTEGER(KIND=JPIB_K), PARAMETER :: NCELLS = 8_JPIB_K +INTEGER(KIND=JPIB_K), PARAMETER :: NCELLS = 9_JPIB_K INTEGER(KIND=JPIB_K), PARAMETER :: SEP_SIZE = 3_JPIB_K -CHARACTER(LEN=*), PARAMETER :: PRINT_FORMAT = '(1x," | ",A," | ",A," | ",A," | ",A," | ",A," |" ,A," | ",A," | ",A," | ")' +CHARACTER(LEN=*), PARAMETER :: PRINT_FORMAT = '(1x," | ",A," | ",A," | ",A," | ",A," | ",A," | ",A," |" ,A," | ",A," | ",A," | ")' ! Whitelist of public symbols (Procedures) @@ -696,6 +699,7 @@ PP_THREAD_SAFE FUNCTION INITIALIZE_OUTPUT_MANAGER( CMDARGS, TOPOLOGY, & ! Get the total number of processors NUMBER_OF_PROCESSORS = PARAMETERS%SIM_%NPROC_IO + TIMESTEP_IN_SECONDS = INT( PARAMETERS%SIM_%TSTEP, KIND=JPIB_K ) ! Get the processor list from the command line arguments PP_TRYCALL(ERRFLAG_GET_PROCESSOR_LIST) CMDARGS%GET_PROCESSOR_LIST( PROCESSOR_LIST, NUMBER_OF_PROCESSORS, HOOKS ) @@ -914,6 +918,7 @@ PP_THREAD_SAFE FUNCTION INITIALIZE_DIST_OUTPUT_MANAGER( CMDARGS, MPI_RANK, MPI_S ! Get the total number of processors NUMBER_OF_PROCESSORS = PARAMETERS%SIM_%NPROC_IO + TIMESTEP_IN_SECONDS = INT( PARAMETERS%SIM_%TSTEP, KIND=JPIB_K ) ! Error handling PP_DEBUG_CRITICAL_COND_THROW( MPI_SIZE .NE. NUMBER_OF_PROCESSORS, ERRFLAG_WRONG_NUM_PROCESSORS ) @@ -1225,6 +1230,7 @@ PP_THREAD_SAFE FUNCTION INITIALIZE_TABLE_OF_CONTENTS( CMDARGS, TOC, BIG_ENDIAN_R ! Get the total number of processors NUMBER_OF_PROCESSORS = PARAMETERS%SIM_%NPROC_IO + TIMESTEP_IN_SECONDS = INT( PARAMETERS%SIM_%TSTEP, KIND=JPIB_K ) ! Get the processor list from the command line arguments PP_TRYCALL(ERRFLAG_GET_PROCESSOR_LIST) CMDARGS%GET_PROCESSOR_LIST( PROCESSOR_LIST, NUMBER_OF_PROCESSORS, HOOKS ) @@ -1461,6 +1467,7 @@ PP_THREAD_SAFE FUNCTION PRINT_HEADER_PVT( CMDARGS, OUTPUT_UNIT, HOOKS ) RESULT(R ! Print the header WRITE( UNIT=OUTPUT_UNIT, FMT=PRINT_FORMAT, IOSTAT=WRITE_STAT ) & & NORMALIZE_STRING( 'solver' ) , & +& NORMALIZE_STRING( 'procId' ) , & & NORMALIZE_STRING( 'param' ) , & & NORMALIZE_STRING( 'repres' ) , & & NORMALIZE_STRING( 'levtype' ) , & @@ -1680,6 +1687,7 @@ PP_THREAD_SAFE FUNCTION PRINT_SIMULATION_INIT( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, WRITE( UNIT=OUTPUT_UNIT, FMT='(A)', IOSTAT=WRITE_STAT ) '' WRITE( UNIT=OUTPUT_UNIT, FMT='(1x,A)', IOSTAT=WRITE_STAT ) 'Begin of simulation' PP_DEBUG_CRITICAL_COND_THROW( WRITE_STAT .NE. 0, ERRFLAG_UNABLE_TO_WRITE_TO_STRING ) + MSG_COUNT = 0_JPIB_K ! Print the header separator PP_TRYCALL(ERRFLAG_UNABLE_TO_WRITE_TO_STRING) PRINT_HEADER_PVT( CMDARGS, OUTPUT_UNIT, HOOKS ) @@ -1776,6 +1784,7 @@ PP_THREAD_SAFE FUNCTION PRINT_ATM_MESSAGE( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ CHARACTER(LEN=32) :: CPARAM CHARACTER(LEN=32) :: CSTEP CHARACTER(LEN=32) :: CLEVEL + CHARACTER(LEN=32) :: CPROCID CHARACTER(LEN=1024) :: DUMP_PATH LOGICAL :: MATCH @@ -1817,7 +1826,7 @@ PP_THREAD_SAFE FUNCTION PRINT_ATM_MESSAGE( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ & TOC_ENTRY%REPRES_ID_, & & TOC_ENTRY%PREFIX_ID_, & & MESSAGE%ILEVG_, & -& TOC_ENTRY%STEP_ID_, & +& TOC_ENTRY%STEP_ID_*TIMESTEP_IN_SECONDS/HOURS2SECONDS, & & MATCH, & & HOOKS ) @@ -1835,12 +1844,16 @@ PP_THREAD_SAFE FUNCTION PRINT_ATM_MESSAGE( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ PP_TRYCALL(ERRFLAG_UNABLE_TO_CONVERT_CLEVTYPE) ILEVTYPE2CLEVTYPE( ILEVTYPE, CLEVTYPE, HOOKS ) ! Convert integers to string + CPROCID = REPEAT(' ',32) + WRITE(CPROCID,'(I32)', IOSTAT=WRITE_STAT) TOC_ENTRY%PROC_ID_ + PP_DEBUG_CRITICAL_COND_THROW( WRITE_STAT .NE. 0, ERRFLAG_UNABLE_TO_WRITE_TO_STRING ) + CPARAM = REPEAT(' ',32) WRITE(CPARAM,'(I32)', IOSTAT=WRITE_STAT) TOC_ENTRY%PARAM_ID_ PP_DEBUG_CRITICAL_COND_THROW( WRITE_STAT .NE. 0, ERRFLAG_UNABLE_TO_WRITE_TO_STRING ) CSTEP = REPEAT(' ',32) - WRITE(CSTEP,'(I32)', IOSTAT=WRITE_STAT) TOC_ENTRY%STEP_ID_ + WRITE(CSTEP,'(I32)', IOSTAT=WRITE_STAT) TOC_ENTRY%STEP_ID_*TIMESTEP_IN_SECONDS/HOURS2SECONDS PP_DEBUG_CRITICAL_COND_THROW( WRITE_STAT .NE. 0, ERRFLAG_UNABLE_TO_WRITE_TO_STRING ) CLEVEL = REPEAT(' ',32) @@ -1850,6 +1863,7 @@ PP_THREAD_SAFE FUNCTION PRINT_ATM_MESSAGE( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ ! Print the header WRITE( UNIT=OUTPUT_UNIT, FMT=PRINT_FORMAT, IOSTAT=WRITE_STAT ) & & NORMALIZE_STRING( 'atm.' ) , & +& NORMALIZE_STRING( TRIM(ADJUSTL(CPROCID)) ) , & & NORMALIZE_STRING( TRIM(ADJUSTL(CPARAM)) ) , & & NORMALIZE_STRING( TRIM(ADJUSTL(CREPRES)) ) , & & NORMALIZE_STRING( TRIM(ADJUSTL(CLEVTYPE)) ) , & @@ -1860,6 +1874,8 @@ PP_THREAD_SAFE FUNCTION PRINT_ATM_MESSAGE( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ PP_DEBUG_CRITICAL_COND_THROW( WRITE_STAT .NE. 0, ERRFLAG_UNABLE_TO_WRITE_TO_STRING ) ENDIF + MSG_COUNT = MSG_COUNT + 1_JPIB_K + ! Trace end of procedure (on success) PP_TRACE_EXIT_PROCEDURE_ON_SUCCESS() @@ -1966,6 +1982,7 @@ PP_THREAD_SAFE FUNCTION PRINT_WAM_MESSAGE( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ CHARACTER(LEN=32) :: CLEVEL CHARACTER(LEN=32) :: CFREQ CHARACTER(LEN=32) :: CANGLE + CHARACTER(LEN=32) :: CPROCID CHARACTER(LEN=1024) :: DUMP_PATH LOGICAL :: MATCH @@ -2009,7 +2026,7 @@ PP_THREAD_SAFE FUNCTION PRINT_WAM_MESSAGE( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ & TOC_ENTRY%PREFIX_ID_, & & MESSAGE%IFREQ, & & MESSAGE%IANGLE, & -& TOC_ENTRY%STEP_ID_, & +& TOC_ENTRY%STEP_ID_*TIMESTEP_IN_SECONDS/HOURS2SECONDS, & & MATCH, & & HOOKS ) ELSE @@ -2019,7 +2036,7 @@ PP_THREAD_SAFE FUNCTION PRINT_WAM_MESSAGE( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ & TOC_ENTRY%REPRES_ID_, & & TOC_ENTRY%PREFIX_ID_, & & MESSAGE%KLEV, & -& TOC_ENTRY%STEP_ID_, & +& TOC_ENTRY%STEP_ID_*TIMESTEP_IN_SECONDS/HOURS2SECONDS, & & MATCH, & & HOOKS ) ENDIF @@ -2038,12 +2055,16 @@ PP_THREAD_SAFE FUNCTION PRINT_WAM_MESSAGE( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ PP_TRYCALL(ERRFLAG_UNABLE_TO_CONVERT_CLEVTYPE) ILEVTYPE2CLEVTYPE( ILEVTYPE, CLEVTYPE, HOOKS ) ! Convert integers to string + CPROCID = REPEAT(' ',32) + WRITE(CPROCID,'(I32)', IOSTAT=WRITE_STAT) TOC_ENTRY%PROC_ID_ + PP_DEBUG_CRITICAL_COND_THROW( WRITE_STAT .NE. 0, ERRFLAG_UNABLE_TO_WRITE_TO_STRING ) + CPARAM = REPEAT(' ',32) WRITE(CPARAM,'(I32)', IOSTAT=WRITE_STAT) TOC_ENTRY%PARAM_ID_ PP_DEBUG_CRITICAL_COND_THROW( WRITE_STAT .NE. 0, ERRFLAG_UNABLE_TO_WRITE_TO_STRING ) CSTEP = REPEAT(' ',32) - WRITE(CSTEP,'(I32)', IOSTAT=WRITE_STAT) TOC_ENTRY%STEP_ID_ + WRITE(CSTEP,'(I32)', IOSTAT=WRITE_STAT) TOC_ENTRY%STEP_ID_*TIMESTEP_IN_SECONDS/HOURS2SECONDS PP_DEBUG_CRITICAL_COND_THROW( WRITE_STAT .NE. 0, ERRFLAG_UNABLE_TO_WRITE_TO_STRING ) IF ( TOC_ENTRY%PARAM_ID_ .EQ. 140250 ) THEN @@ -2055,6 +2076,7 @@ PP_THREAD_SAFE FUNCTION PRINT_WAM_MESSAGE( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ ! Print the header WRITE( UNIT=OUTPUT_UNIT, FMT=PRINT_FORMAT, IOSTAT=WRITE_STAT ) & & NORMALIZE_STRING( 'wam.' ) , & +& NORMALIZE_STRING( TRIM(ADJUSTL(CPROCID)) ) , & & NORMALIZE_STRING( TRIM(ADJUSTL(CPARAM)) ) , & & NORMALIZE_STRING( TRIM(ADJUSTL(CREPRES)) ) , & & NORMALIZE_STRING( TRIM(ADJUSTL(CLEVTYPE)) ) , & @@ -2075,6 +2097,7 @@ PP_THREAD_SAFE FUNCTION PRINT_WAM_MESSAGE( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ ! Print the header WRITE( UNIT=OUTPUT_UNIT, FMT=PRINT_FORMAT, IOSTAT=WRITE_STAT ) & & NORMALIZE_STRING( 'wam.' ) , & +& NORMALIZE_STRING( TRIM(ADJUSTL(CPROCID)) ) , & & NORMALIZE_STRING( TRIM(ADJUSTL(CPARAM)) ) , & & NORMALIZE_STRING( TRIM(ADJUSTL(CREPRES)) ) , & & NORMALIZE_STRING( TRIM(ADJUSTL(CLEVTYPE)) ) , & @@ -2086,7 +2109,7 @@ PP_THREAD_SAFE FUNCTION PRINT_WAM_MESSAGE( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ ENDIF ENDIF - + MSG_COUNT = MSG_COUNT + 1_JPIB_K ! Trace end of procedure (on success) @@ -2185,6 +2208,7 @@ PP_THREAD_SAFE FUNCTION PRINT_FLUSH( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ENDIAN ! Local variables INTEGER(KIND=JPIB_K) :: WRITE_STAT CHARACTER(LEN=32) :: CSTEP + CHARACTER(LEN=32) :: CMSG_COUNT ! Local error flags INTEGER(KIND=JPIB_K), PARAMETER :: ERRFLAG_UNABLE_TO_WRITE_TO_STRING = 1_JPIB_K @@ -2206,12 +2230,15 @@ PP_THREAD_SAFE FUNCTION PRINT_FLUSH( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, BIG_ENDIAN ! Convert step to string CSTEP = REPEAT(' ',32) - WRITE(CSTEP,'(I32)') TOC_ENTRY%STEP_ + CMSG_COUNT = REPEAT(' ',32) + WRITE(CSTEP,'(I32)') TOC_ENTRY%STEP_*TIMESTEP_IN_SECONDS/HOURS2SECONDS + WRITE(CMSG_COUNT,'(I32)') MSG_COUNT + MSG_COUNT = 0_JPIB_K ! Print the header separator PP_TRYCALL(ERRFLAG_UNABLE_TO_WRITE_TO_STRING) PRINT_HEADER_PVT( CMDARGS, OUTPUT_UNIT, HOOKS ) - WRITE( UNIT=OUTPUT_UNIT, FMT='(1x,A)', IOSTAT=WRITE_STAT ) 'Flush step: '//TRIM(ADJUSTL(CSTEP)) + WRITE( UNIT=OUTPUT_UNIT, FMT='(1x,A)', IOSTAT=WRITE_STAT ) 'Flush step: '//TRIM(ADJUSTL(CSTEP))//' Message count: '//TRIM(ADJUSTL(CMSG_COUNT)) PP_DEBUG_CRITICAL_COND_THROW( WRITE_STAT .NE. 0, ERRFLAG_UNABLE_TO_WRITE_TO_STRING ) WRITE( UNIT=OUTPUT_UNIT, FMT='(A)', IOSTAT=WRITE_STAT ) ' ' PP_DEBUG_CRITICAL_COND_THROW( WRITE_STAT .NE. 0, ERRFLAG_UNABLE_TO_WRITE_TO_STRING ) @@ -2305,6 +2332,7 @@ PP_THREAD_SAFE FUNCTION PRINT_FLUSH_AND_RESTART( CMDARGS, OUTPUT_UNIT, TOC_ENTRY ! Local variables INTEGER(KIND=JPIB_K) :: WRITE_STAT CHARACTER(LEN=32) :: CSTEP + CHARACTER(LEN=32) :: CMSG_COUNT ! Local error flags INTEGER(KIND=JPIB_K), PARAMETER :: ERRFLAG_UNABLE_TO_WRITE_TO_STRING = 1_JPIB_K @@ -2326,7 +2354,10 @@ PP_THREAD_SAFE FUNCTION PRINT_FLUSH_AND_RESTART( CMDARGS, OUTPUT_UNIT, TOC_ENTRY ! Convert step to string CSTEP = REPEAT(' ',32) - WRITE(CSTEP,'(I32)') TOC_ENTRY%STEP_ + CMSG_COUNT = REPEAT(' ',32) + WRITE(CSTEP,'(I32)') TOC_ENTRY%STEP_*TIMESTEP_IN_SECONDS/HOURS2SECONDS + WRITE(CMSG_COUNT,'(I32)') MSG_COUNT + MSG_COUNT = 0_JPIB_K ! Print the header separator PP_TRYCALL(ERRFLAG_UNABLE_TO_WRITE_TO_STRING) PRINT_HEADER_PVT( CMDARGS, OUTPUT_UNIT, HOOKS ) @@ -2443,6 +2474,8 @@ PP_THREAD_SAFE FUNCTION PRINT_FLUSH_LAST_STEP( CMDARGS, OUTPUT_UNIT, TOC_ENTRY, PP_SET_ERR_SUCCESS( RET ) + MSG_COUNT = 0_JPIB_K + ! Print the header separator PP_TRYCALL(ERRFLAG_UNABLE_TO_WRITE_TO_STRING) PRINT_HEADER_PVT( CMDARGS, OUTPUT_UNIT, HOOKS ) WRITE( UNIT=OUTPUT_UNIT, FMT='(1x,A)', IOSTAT=WRITE_STAT ) 'Flush last step: ' @@ -3154,7 +3187,7 @@ PP_THREAD_SAFE FUNCTION ENCODE_ATM_MESSAGE( CMDARGS, OUTPUT_MANAGER, TOC_ENTRY, & TOC_ENTRY%REPRES_ID_, & & TOC_ENTRY%PREFIX_ID_, & & MESSAGE%ILEVG_, & -& TOC_ENTRY%STEP_ID_, & +& TOC_ENTRY%STEP_ID_*TIMESTEP_IN_SECONDS/HOURS2SECONDS, & & MATCH, & & HOOKS ) @@ -3365,7 +3398,7 @@ PP_THREAD_SAFE FUNCTION ENCODE_WAM_MESSAGE( CMDARGS, OUTPUT_MANAGER, TOC_ENTRY, & TOC_ENTRY%PREFIX_ID_, & & MESSAGE%IFREQ, & & MESSAGE%IANGLE, & -& TOC_ENTRY%STEP_ID_, & +& TOC_ENTRY%STEP_ID_*TIMESTEP_IN_SECONDS/HOURS2SECONDS, & & MATCH, & & HOOKS ) ELSE @@ -3375,7 +3408,7 @@ PP_THREAD_SAFE FUNCTION ENCODE_WAM_MESSAGE( CMDARGS, OUTPUT_MANAGER, TOC_ENTRY, & TOC_ENTRY%REPRES_ID_, & & TOC_ENTRY%PREFIX_ID_, & & MESSAGE%KLEV, & -& TOC_ENTRY%STEP_ID_, & +& TOC_ENTRY%STEP_ID_*TIMESTEP_IN_SECONDS/HOURS2SECONDS, & & MATCH, & & HOOKS ) ENDIF