Updated opm-common to latest

This commit is contained in:
Magne Sjaastad
2021-04-16 19:47:27 +02:00
parent 9cd36fab5b
commit 4c7c895b87
25 changed files with 540 additions and 149 deletions

View File

@@ -155,8 +155,7 @@ void RifOpmHdf5Summary::buildMetaData()
else
{
// Fallback to using opm-reader for time step data
std::vector<std::chrono::system_clock::time_point> timePoints;
timePoints = m_eSmry->dates();
auto timePoints = m_eSmry->dates();
for ( const auto& d : timePoints )
{

View File

@@ -19,72 +19,18 @@
#ifndef OPM_FILESYSTEM_HPP
#define OPM_FILESYSTEM_HPP
// Check for feature test macro for <filesystem>
# if defined(__cpp_lib_filesystem)
# define INCLUDE_STD_FILESYSTEM_EXPERIMENTAL 0
// Check for feature test macro for <experimental/filesystem>
# elif defined(__cpp_lib_experimental_filesystem)
# define INCLUDE_STD_FILESYSTEM_EXPERIMENTAL 1
// We can't check if headers exist...
// Let's assume experimental to be safe
# elif !defined(__has_include)
# define INCLUDE_STD_FILESYSTEM_EXPERIMENTAL 1
// Check if the header "<filesystem>" exists
# elif __has_include(<filesystem>)
// If we're compiling on Visual Studio and are not compiling with C++17, we need to use experimental
# ifdef _MSC_VER
// Check and include header that defines "_HAS_CXX17"
# if __has_include(<yvals_core.h>)
# include <yvals_core.h>
// Check for enabled C++17 support
# if defined(_HAS_CXX17) && _HAS_CXX17
// We're using C++17, so let's use the normal version
# define INCLUDE_STD_FILESYSTEM_EXPERIMENTAL 0
# endif
# endif
// If the marco isn't defined yet, that means any of the other VS specific checks failed, so we need to use experimental
# ifndef INCLUDE_STD_FILESYSTEM_EXPERIMENTAL
# define INCLUDE_STD_FILESYSTEM_EXPERIMENTAL 1
# endif
// Not on Visual Studio. Let's use the normal version
# else // #ifdef _MSC_VER
# define INCLUDE_STD_FILESYSTEM_EXPERIMENTAL 0
# endif
// Check if the header "<filesystem>" exists
# elif __has_include(<experimental/filesystem>)
# define INCLUDE_STD_FILESYSTEM_EXPERIMENTAL 1
// Fail if neither header is available with a nice error message
# else
# error Could not find system header "<filesystem>" or "<experimental/filesystem>"
# endif
// We priously determined that we need the experimental version
# if INCLUDE_STD_FILESYSTEM_EXPERIMENTAL
// Include it
# define _SILENCE_EXPERIMENTAL_FILESYSTEM_DEPRECATION_WARNING
# include <experimental/filesystem>
// We have a decent compiler and can use the normal version
#if !defined(_WIN32) && (__cplusplus < 201703L || (defined(__GNUC__) && __GNUC__ < 8 && !defined(__clang__)))
#include <experimental/filesystem>
#else
// Include it
#include <filesystem>
#endif
#include <string>
namespace Opm
{
#if INCLUDE_STD_FILESYSTEM_EXPERIMENTAL
#if !defined(_WIN32) && (__cplusplus < 201703L || (defined(__GNUC__) && __GNUC__ < 8 && !defined(__clang__)))
namespace filesystem = std::experimental::filesystem;
#else
namespace filesystem = std::filesystem;

View File

@@ -0,0 +1,121 @@
/*
Copyright 2020 Equinor ASA.
This file is part of the Open Porous Media project (OPM).
OPM is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
OPM is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with OPM. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef OPM_ERROR_HPP
#define OPM_ERROR_HPP
#include <stdexcept>
#include <string>
#include <vector>
#include <opm/common/OpmLog/KeywordLocation.hpp>
namespace Opm {
/*
The OpmInputError is a custom exception class which can be used to signal
errors in input handling. The importance of the OpmInputError exception is
*not* the tecnical functionality it provides, but rather the convention
surrounding it, when and how it should be used.
The OpmInputError should be used in situations which are "close to user
input", the root cause can either be incorrect user input or a bug/limitation
in opm. OpmInputError should only be used in situations where we have a good
understanding of the underlying issue, and can provide a good error message.
The local error handling should be complete when the OpmInputError is
instantiated, it should not be caught and rethrown in order to e.g. add
additional context or log messages. In order to avoid inadvertendly catching
this exception in a catch all block.
*/
class OpmInputError : public std::exception {
public:
/*
The message string will be used as format string in the fmt::format()
function as, and optional {} markers can be used to inject keyword,
filename and linenumber into the final what() message. The placeholders
must use named arguments
{keyword} -> loc.keyword
{file} -> loc.filename
{line} -> loc.lineno
additionally, the message can contain any number of positional
arguments to add further context to the message.
KeywordLocation loc("KW", "file.inc", 100);
OpmInputError("Error at line {line} in file {file} - keyword: {keyword} ignored", location);
OpmInputError("Error at line {line} in file {file} - keyword: {keyword} has invalid argument {}", invalid_argument);
*/
template<typename ... Args>
OpmInputError(const std::string& reason, const KeywordLocation& location, const Args& ...furtherLocations)
: locations { location, furtherLocations... }
, m_what {
locations.size() == 1
? formatSingle(reason, locations[0])
: formatMultiple(reason, locations)
}
{ }
/*
Allows for the initialisation of an OpmInputError from another exception.
Usage:
try {
.
.
.
} catch (const Opm::OpmInputError&) {
throw;
} catch (const std::exception& e) {
std::throw_with_nested(Opm::OpmInputError(e, location));
}
*/
OpmInputError(const std::exception& error, const KeywordLocation& location)
: locations { location }
, m_what { formatException(error, locations[0]) }
{ }
const char * what() const throw()
{
return this->m_what.c_str();
}
static std::string format(const std::string& msg_format, const KeywordLocation& loc);
private:
// The location member is here for debugging; depending on the msg_fmt
// passed in the constructor we might not have captured all the information
// in the location argument passed to the constructor.
std::vector<KeywordLocation> locations;
std::string m_what;
static std::string formatException(const std::exception& e, const KeywordLocation& loc);
static std::string formatSingle(const std::string& reason, const KeywordLocation&);
static std::string formatMultiple(const std::string& reason, const std::vector<KeywordLocation>&);
};
}
#endif

View File

@@ -0,0 +1,136 @@
/*
Copyright 2020 Equinor ASA.
This file is part of the Open Porous Media project (OPM).
OPM is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
OPM is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with OPM. If not, see <http://www.gnu.org/licenses/>.
*/
#include <cstring>
#include <string>
#include <unordered_map>
#include <vector>
#ifndef OPM_SERIALIZER_HPP
#define OPM_SERIALIZER_HPP
namespace Opm {
/*
This is a very basic serialization class used to support serialization of
small state objects from opm common. The main serialization code used in
opm/flow is initiated and controlled from the restart code, and therefor
slightly cumbersome to use for objects which should be serialized not as part
of the restart code.
*/
class Serializer {
public:
Serializer() = default;
explicit Serializer(const std::vector<char>& buffer_arg) :
buffer(buffer_arg)
{}
template <typename T>
void put(const T& value) {
this->pack(std::addressof(value), sizeof(T));
}
template <typename T>
void put(const T* ) {
throw std::logic_error("Serializer can not pack pointers");
}
template <typename T>
T get() {
T value;
std::memcpy(&value, &this->buffer[this->read_pos], sizeof(T));
this->read_pos += sizeof(T);
return value;
}
template<typename T>
void put_vector(const std::vector<T>& values) {
this->put(values.size());
this->pack(values.data(), values.size() * sizeof(T));
}
template<typename T>
std::vector<T> get_vector() {
std::size_t size = this->get<std::size_t>();
std::vector<T> values(size);
for (std::size_t index=0; index < size; index++)
values[index] = this->get<T>();
return values;
}
template<typename K, typename T>
void put_map(const std::unordered_map<K,T>& values) {
this->put(values.size());
for (const auto& value_pair : values) {
this->put(value_pair.first);
this->put(value_pair.second);
}
}
template<typename K, typename T>
std::unordered_map<K,T> get_map() {
std::unordered_map<K,T> values;
auto size = this->get<std::size_t>();
for (std::size_t index = 0; index < size; index++) {
auto key = this->get<K>();
auto value = this->get<T>();
values.insert( std::make_pair(key,value) );
}
return values;
}
std::vector<char> buffer;
private:
void pack(const void * ptr, std::size_t value_size) {
std::size_t write_pos = this->buffer.size();
std::size_t new_size = write_pos + value_size;
this->buffer.resize( new_size );
std::memcpy(&this->buffer[write_pos], ptr, value_size);
}
std::size_t read_pos = 0;
};
template <>
void inline Serializer::put(const std::string& value) {
this->put(value.size());
if (value.empty())
return;
this->pack(value.c_str(), value.size());
}
template<>
std::string inline Serializer::get<std::string>() {
std::string::size_type length = this->get<std::string::size_type>();
if (length == 0)
return std::string{};
this->read_pos += length;
return {std::addressof(this->buffer[this->read_pos - length]), length};
}
}
#endif

View File

@@ -22,9 +22,25 @@
#include <chrono>
#include <ctime>
#include <string>
#include <unordered_map>
namespace Opm {
using time_point = std::chrono::time_point<std::chrono::system_clock, std::chrono::duration<int64_t, std::ratio<1,1000>>>;
namespace TimeService {
std::time_t to_time_t(const time_point& tp);
time_point from_time_t(std::time_t t);
time_point now();
std::time_t advance(const std::time_t tp, const double sec);
std::time_t makeUTCTime(std::tm timePoint);
const std::unordered_map<std::string , int>& eclipseMonthIndices();
bool valid_month(const std::string& month_name);
}
class TimeStampUTC
{
public:

View File

@@ -22,7 +22,9 @@
#define OPM_ROOTFINDERS_HEADER
#include <opm/common/ErrorMacros.hpp>
#include <opm/common/OpmLog/OpmLog.hpp>
#include <string>
#include <algorithm>
#include <limits>
#include <cmath>
@@ -35,15 +37,18 @@ namespace Opm
{
static double handleBracketingFailure(const double x0, const double x1, const double f0, const double f1)
{
OPM_THROW(std::runtime_error, "Error in parameters, zero not bracketed: [a, b] = ["
<< x0 << ", " << x1 << "] f(a) = " << f0 << " f(b) = " << f1);
std::ostringstream sstr;
sstr << "Error in parameters, zero not bracketed: [a, b] = ["
<< x0 << ", " << x1 << "] f(a) = " << f0 << " f(b) = " << f1;
OpmLog::debug(sstr.str());
OPM_THROW_NOLOG(std::runtime_error, sstr.str());
return -1e100; // Never reached.
}
static double handleTooManyIterations(const double x0, const double x1, const int maxiter)
{
OPM_THROW(std::runtime_error, "Maximum number of iterations exceeded: " << maxiter << "\n"
<< "Current interval is [" << std::min(x0, x1) << ", "
<< std::max(x0, x1) << "]");
<< std::max(x0, x1) << "] abs(x0-x1) " << std::abs(x0-x1));
return -1e100; // Never reached.
}
};
@@ -64,7 +69,7 @@ namespace Opm
OPM_REPORT;
std::cerr << "Maximum number of iterations exceeded: " << maxiter
<< ", current interval is [" << std::min(x0, x1) << ", "
<< std::max(x0, x1) << "]";
<< std::max(x0, x1) << "] abs(x0-x1) " << std::abs(x0-x1);
return 0.5*(x0 + x1);
}
};
@@ -124,7 +129,7 @@ namespace Opm
iterations_used = 0;
// In every iteraton, x1 is the last point computed,
// and x0 is the last point computed that makes it a bracket.
while (fabs(x1 - x0) >= 1e-9*eps) {
while (fabs(x1 - x0) >= eps) {
double xnew = regulaFalsiStep(x0, x1, f0, f1);
double fnew = f(xnew);
// cout << "xnew = " << xnew << " fnew = " << fnew << endl;
@@ -221,7 +226,7 @@ namespace Opm
iterations_used = 0;
// In every iteraton, x1 is the last point computed,
// and x0 is the last point computed that makes it a bracket.
while (fabs(x1 - x0) >= 1e-9*eps) {
while (fabs(x1 - x0) >= eps) {
double xnew = regulaFalsiStep(x0, x1, f0, f1);
double fnew = f(xnew);
// cout << "xnew = " << xnew << " fnew = " << fnew << endl;
@@ -327,7 +332,7 @@ namespace Opm
// and x0 is the last point computed that makes it a bracket.
double width = fabs(x1 - x0);
double contraction = 1.0;
while (width >= 1e-9 * eps) {
while (width >= eps) {
// If we are contracting sufficiently to at least halve
// the interval width in two iterations we use regula
// falsi. Otherwise, we take a bisection step to avoid

View File

@@ -19,7 +19,11 @@
#include <array>
#include <math.h>
#ifndef CALCULATE_CELLVOL
#define CALCULATE_CELLVOL
double calculateCellVol(const std::array<double,8>& X, const std::array<double,8>& Y, const std::array<double,8>& Z);
double calculateCylindricalCellVol(const double R1, const double R2, const double dTheta, const double dZ);
#endif

View File

@@ -24,12 +24,6 @@
#include <vector>
#include <type_traits>
#include <cmath>
// Make sure Windows macro definitions are
// undefined here, to be able to use std::min/max.
#undef max
#undef min
#include <algorithm>
namespace Opm {

View File

@@ -72,7 +72,7 @@ private:
std::array<int, 3> nijk;
std::array<int, 3> host_nijk;
int nactive, m_nncs;
int nactive;
mutable bool m_nncs_loaded;
std::vector<int> act_index;

View File

@@ -28,6 +28,7 @@
#include <stdint.h>
#include <opm/common/utility/FileSystem.hpp>
#include <opm/common/utility/TimeService.hpp>
#include <opm/io/eclipse/SummaryNode.hpp>
namespace Opm { namespace EclIO {
@@ -48,11 +49,11 @@ public:
const std::vector<float>& get(const std::string& name) const;
const std::vector<float>& get(const SummaryNode& node) const;
std::vector<std::chrono::system_clock::time_point> dates() const;
std::vector<time_point> dates() const;
std::vector<float> get_at_rstep(const std::string& name) const;
std::vector<float> get_at_rstep(const SummaryNode& node) const;
std::vector<std::chrono::system_clock::time_point> dates_at_rstep() const;
std::vector<time_point> dates_at_rstep() const;
void LoadData(const std::vector<std::string>& vectList) const;
void LoadData() const;
@@ -62,7 +63,7 @@ public:
// Added based on requirements from ResInsight
void use_lodsmry_file(bool enable);
std::chrono::system_clock::time_point startdate() const { return startdat; }
time_point startdate() const { return startdat; }
const std::vector<std::string>& keywordList() const;
std::vector<std::string> keywordList(const std::string& pattern) const;
@@ -80,7 +81,6 @@ public:
void ijk_from_global_index(int glob, int &i, int &j, int &k) const;
private:
bool useLodsmryFile; // Added by ResInsight use
Opm::filesystem::path inputFileName, lodFileName;
@@ -107,7 +107,7 @@ private:
std::vector<SummaryNode> summaryNodes;
std::unordered_map<std::string, std::string> kwunits;
std::chrono::system_clock::time_point startdat;
time_point startdat;
std::vector<std::string> checkForMultipleResultFiles(const Opm::filesystem::path& rootN, bool formatted) const;

View File

@@ -35,7 +35,12 @@ namespace Opm { namespace EclIO {
class EclFile
{
public:
struct Formatted {
bool value;
};
explicit EclFile(const std::string& filename, bool preload = false);
EclFile(const std::string& filename, Formatted fmt, bool preload = false);
bool formattedInput() const { return formatted; }
void loadData(); // load all data
@@ -114,6 +119,7 @@ private:
void loadBinaryArray(std::fstream& fileH, std::size_t arrIndex);
void loadFormattedArray(const std::string& fileStr, std::size_t arrIndex, int64_t fromPos);
void load(bool preload);
std::vector<unsigned int> get_bin_logi_raw_values(int arrIndex) const;
std::vector<std::string> get_fmt_real_raw_str_values(int arrIndex) const;

View File

@@ -35,6 +35,7 @@ namespace Opm { namespace EclIO {
bool isEOF(std::fstream* fileH);
bool fileExists(const std::string& filename);
bool isFormatted(const std::string& filename);
bool is_number(const std::string& numstr);
std::tuple<int, int> block_size_data_binary(eclArrType arrType);
std::tuple<int, int, int> block_size_data_formatted(eclArrType arrType);

View File

@@ -21,6 +21,7 @@
#define OPM_IO_OUTPUTSTREAM_HPP_INCLUDED
#include <opm/io/eclipse/PaddedOutputString.hpp>
#include <opm/common/utility/TimeService.hpp>
#include <array>
#include <chrono>
@@ -362,7 +363,7 @@ namespace Opm { namespace EclIO { namespace OutputStream {
class SummarySpecification
{
public:
using StartTime = std::chrono::system_clock::time_point;
using StartTime = time_point;
enum class UnitConvention
{

View File

@@ -41,8 +41,7 @@ struct RstGroup {
std::string name;
int parent_group;
int prod_active_cmode;
int gconprod_cmode;
int prod_cmode;
int winj_cmode;
int ginj_cmode;
int guide_rate_def;

View File

@@ -0,0 +1,87 @@
/*
Copyright 2020 Equinor ASA.
This file is part of the Open Porous Media project (OPM).
OPM is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
OPM is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with OPM. If not, see <http://www.gnu.org/licenses/>.
*/
#include <algorithm>
#include <numeric>
#include <utility>
#include <fmt/format.h>
#include <opm/common/utility/OpmInputError.hpp>
namespace Opm {
namespace {
template<typename ... Args>
std::string formatImpl(const std::string& msg_format, const KeywordLocation& loc, const Args& ...arguments) {
return fmt::format(msg_format,
arguments...,
fmt::arg("keyword", loc.keyword),
fmt::arg("file", loc.filename),
fmt::arg("line", loc.lineno)
);
}
}
std::string OpmInputError::formatException(const std::exception& e, const KeywordLocation& loc) {
const std::string defaultMessage { R"(Problem with keyword {keyword}
In {file} line {line}.
Internal error: {})" } ;
return formatImpl(defaultMessage, loc, e.what());
}
/*
For the format() function it is possible to have an alternative function with
a variaditic template which can be forwarded directly to the fmt::format()
function, that is an elegant way to pass arbitrary additional arguments. That
will require the OpmInputError::format() to become a templated function and
the fmtlib dependendcy will be imposed on downstream modules.
*/
std::string OpmInputError::format(const std::string& msg_format, const KeywordLocation& loc) {
return formatImpl(msg_format, loc);
}
std::string OpmInputError::formatSingle(const std::string& reason, const KeywordLocation& location) {
const std::string defaultMessage { R"(Problem with keyword {keyword}
In {file} line {line}
{})" } ;
return formatImpl(defaultMessage, location, reason);
}
namespace {
std::string locationStringLine(const KeywordLocation& loc) {
return OpmInputError::format("\n {keyword} in {file}, line {line}", loc);
}
}
std::string OpmInputError::formatMultiple(const std::string& reason, const std::vector<KeywordLocation>& locations) {
std::vector<std::string> locationStrings;
std::transform(locations.begin(), locations.end(), std::back_inserter(locationStrings), &locationStringLine);
const std::string messages { std::accumulate(locationStrings.begin(), locationStrings.end(), std::string {}) } ;
return fmt::format(R"(Problem with keywords {}
{})", messages, reason);
}
}

View File

@@ -23,34 +23,83 @@
#include <ctime>
#include <utility>
namespace Opm {
namespace TimeService {
namespace {
std::time_t advance(const std::time_t tp, const double sec)
{
using namespace std::chrono;
const std::unordered_map<std::string, int> month_indices = {
{"JAN", 1},
{"FEB", 2},
{"MAR", 3},
{"APR", 4},
{"MAI", 5},
{"MAY", 5},
{"JUN", 6},
{"JUL", 7},
{"JLY", 7},
{"AUG", 8},
{"SEP", 9},
{"OCT", 10},
{"OKT", 10},
{"NOV", 11},
{"DEC", 12},
{"DES", 12}};
}
using TP = time_point<system_clock>;
using DoubSec = duration<double, seconds::period>;
const auto t = system_clock::from_time_t(tp) +
duration_cast<TP::duration>(DoubSec(sec));
const time_t system_clock_epoch = std::chrono::system_clock::to_time_t({});
return system_clock::to_time_t(t);
}
time_point from_time_t(std::time_t t) {
auto diff = std::difftime(t, system_clock_epoch);
return time_point(std::chrono::seconds(static_cast<std::chrono::seconds::rep>(diff)));
}
std::time_t makeUTCTime(std::tm timePoint)
{
const auto ltime = std::mktime(&timePoint);
auto tmval = *std::gmtime(&ltime); // Mutable.
std::time_t to_time_t(const time_point& tp) {
return std::chrono::duration_cast<std::chrono::seconds>(tp.time_since_epoch()).count() + system_clock_epoch;
}
// offset = ltime - tmval
// == #seconds by which 'ltime' is AHEAD of tmval.
const auto offset =
std::difftime(ltime, std::mktime(&tmval));
// Advance 'ltime' by 'offset' so that std::gmtime(return value) will
// have the same broken-down elements as 'tp'.
return advance(ltime, offset);
}
time_point now() {
time_point epoch;
auto default_now = std::chrono::system_clock::now();
return epoch + std::chrono::duration_cast<Opm::time_point::duration>(default_now.time_since_epoch());
}
std::time_t advance(const std::time_t tp, const double sec)
{
const auto t = Opm::TimeService::from_time_t(tp) + std::chrono::duration_cast<Opm::time_point::duration>(std::chrono::duration<double>(sec));
return Opm::TimeService::to_time_t(t);
}
std::time_t makeUTCTime(std::tm timePoint)
{
const auto ltime = std::mktime(&timePoint);
auto tmval = *std::gmtime(&ltime); // Mutable.
// offset = ltime - tmval
// == #seconds by which 'ltime' is AHEAD of tmval.
const auto offset =
std::difftime(ltime, std::mktime(&tmval));
// Advance 'ltime' by 'offset' so that std::gmtime(return value) will
// have the same broken-down elements as 'tp'.
return advance(ltime, offset);
}
const std::unordered_map<std::string , int>& eclipseMonthIndices() {
return month_indices;
}
bool valid_month(const std::string& month_name) {
return (month_indices.count(month_name) != 0);
}
}
}
namespace {
std::tm makeTm(const Opm::TimeStampUTC& tp) {
@@ -144,7 +193,7 @@ Opm::TimeStampUTC& Opm::TimeStampUTC::microseconds(const int us)
std::time_t Opm::asTimeT(const TimeStampUTC& tp)
{
return makeUTCTime(makeTm(tp));
return Opm::TimeService::makeUTCTime(makeTm(tp));
}
std::time_t Opm::asLocalTimeT(const TimeStampUTC& tp)
@@ -154,7 +203,7 @@ std::time_t Opm::asLocalTimeT(const TimeStampUTC& tp)
}
Opm::TimeStampUTC Opm::operator+(const Opm::TimeStampUTC& lhs, std::chrono::duration<double> delta) {
return Opm::TimeStampUTC( advance(Opm::asTimeT(lhs) , delta.count()) );
return Opm::TimeStampUTC( Opm::TimeService::advance(Opm::asTimeT(lhs) , delta.count()) );
}

View File

@@ -42,10 +42,6 @@
#include <map>
#include <cmath>
#if _WIN32
#include <algorithm>
#endif
using namespace std;
/*

View File

@@ -18,7 +18,10 @@
#include <algorithm>
#include <cassert>
#define _USE_MATH_DEFINES
#include <cmath>
#include <opm/common/utility/numeric/calculateCellVol.hpp>
#include <opm/common/ErrorMacros.hpp>
@@ -131,4 +134,11 @@ double calculateCellVol(const std::array<double,8>& X, const std::array<double,8
}
/*
Cell volume calculation for a cell from a cylindrical grid, given by the
inner and outer radius of the cell, and its spans in the angle and Z.
*/
double calculateCylindricalCellVol(const double r_inner, const double r_outer, const double delta_theta, const double delta_z)
{
return M_PI * std::abs((std::pow(r_outer,2) - std::pow(r_inner,2)) * delta_theta * delta_z) / 360.0;
}

View File

@@ -16,9 +16,6 @@
along with OPM. If not, see <http://www.gnu.org/licenses/>.
*/
#define _USE_MATH_DEFINES
#include <cmath> // For definition of M_PI
#include <opm/io/eclipse/EGrid.hpp>
#include <opm/io/eclipse/EInit.hpp>
#include <opm/io/eclipse/EclUtil.hpp>
@@ -33,6 +30,9 @@
#include <string>
#include <sstream>
#define _USE_MATH_DEFINES
#include <math.h>
namespace Opm { namespace EclIO {
using NNCentry = std::tuple<int, int, int, int, int,int, float>;

View File

@@ -29,7 +29,7 @@
#include <opm/common/utility/FileSystem.hpp>
#include <opm/common/utility/String.hpp>
#include <opm/common/utility/numeric/cmp.hpp>
#include <opm/parser/eclipse/EclipseState/Schedule/TimeMap.hpp>
#include <opm/common/utility/TimeService.hpp>
namespace Opm {
namespace EclIO {
@@ -99,7 +99,7 @@ int make_num(const std::string& nums_string) {
}
TimeStampUTC make_timestamp(const std::string& date_string) {
const auto& month_index = TimeMap::eclipseMonthIndices();
const auto& month_index = TimeService ::eclipseMonthIndices();
auto dash_pos1 = date_string.find('-');
auto dash_pos2 = date_string.rfind('-');
auto day = std::stoi( date_string.substr(0, dash_pos1 ) );
@@ -287,9 +287,7 @@ bool cmp(const ESmry& smry, const ERsm& rsm) {
return false;
for (std::size_t time_index = 0; time_index < rsm_days.size(); time_index++) {
using namespace std::chrono;
using TP = time_point<system_clock>;
auto smry_days = duration_cast<TP::duration>(summary_dates[time_index] - summary_dates[0]).count() / 86400.0 ;
auto smry_days = std::chrono::duration_cast<std::chrono::seconds>(summary_dates[time_index] - summary_dates[0]).count() / 86400.0 ;
if (!cmp::scalar_equal(smry_days, rsm_days[time_index])) {
fmt::print(stderr, "time_index: {} summary.days: {} rsm.days: {}", time_index, smry_days, rsm_days[time_index]);

View File

@@ -22,6 +22,7 @@
#include <opm/io/eclipse/EclFile.hpp>
#include <opm/io/eclipse/EclUtil.hpp>
#include <opm/io/eclipse/EclOutput.hpp>
#include <opm/common/utility/TimeService.hpp>
#include <algorithm>
#include <chrono>
@@ -67,7 +68,7 @@
namespace {
std::chrono::system_clock::time_point make_date(const std::vector<int>& datetime) {
Opm::time_point make_date(const std::vector<int>& datetime) {
auto day = datetime[0];
auto month = datetime[1];
auto year = datetime[2];
@@ -84,7 +85,7 @@ std::chrono::system_clock::time_point make_date(const std::vector<int>& datetime
const auto ts = Opm::TimeStampUTC{ Opm::TimeStampUTC::YMD{ year, month, day}}.hour(hour).minutes(minute).seconds(second);
return std::chrono::system_clock::from_time_t( Opm::asTimeT(ts) );
return Opm::TimeService::from_time_t( Opm::asTimeT(ts) );
}
@@ -1084,8 +1085,11 @@ std::vector<std::string> ESmry::checkForMultipleResultFiles(const Opm::filesyste
{
const std::string file = itr->path().filename().string();
if ((file.find(fileFilter) != std::string::npos) && (file.find("SMSPEC") == std::string::npos)) {
fileList.push_back(pathRootN + "/" + file);
if (file.find(fileFilter) != std::string::npos) {
std::string num_string = itr->path().extension().string().substr(2);
if (Opm::EclIO::is_number(num_string))
fileList.push_back(pathRootN + "/" + file);
}
}
@@ -1278,9 +1282,9 @@ std::vector<std::string> ESmry::keywordList(const std::string& pattern) const
{
std::vector<std::string> list;
for (auto key : keyword)
if (fnmatch( pattern.c_str(), key.c_str(), 0 ) == 0 )
list.push_back(key);
for (auto key : keyword)
if (fnmatch( pattern.c_str(), key.c_str(), 0 ) == 0 )
list.push_back(key);
return list;
}
@@ -1291,24 +1295,18 @@ const std::vector<SummaryNode>& ESmry::summaryNodeList() const {
return summaryNodes;
}
std::vector<std::chrono::system_clock::time_point> ESmry::dates() const {
std::vector<Opm::time_point> ESmry::dates() const {
double time_unit = 24 * 3600;
std::vector<std::chrono::system_clock::time_point> d;
using namespace std::chrono;
using TP = time_point<system_clock>;
using DoubSec = duration<double, seconds::period>;
std::vector<Opm::time_point> d;
for (const auto& t : this->get("TIME"))
d.push_back( this->startdat + duration_cast<TP::duration>(DoubSec(t * time_unit)));
d.push_back( this->startdat + std::chrono::duration_cast<std::chrono::seconds>( std::chrono::duration<double, std::chrono::seconds::period>( t * time_unit)));
return d;
}
std::vector<std::chrono::system_clock::time_point> ESmry::dates_at_rstep() const {
std::vector<time_point> ESmry::dates_at_rstep() const {
const auto& full_vector = this->dates();
return this->rstep_vector(full_vector);
}
}} // namespace Opm::ecl

View File

@@ -52,15 +52,15 @@ namespace {
const std::vector<std::string> month_names = {"JAN", "FEB", "MAR", "APR", "MAY", "JUN", "JUL", "AUG", "SEP", "OCT", "NOV", "DEC"};
std::string format_date(const std::chrono::system_clock::time_point& tp) {
auto ts = Opm::TimeStampUTC( std::chrono::system_clock::to_time_t(tp) );
std::string format_date(const Opm::time_point& tp) {
auto ts = Opm::TimeStampUTC( Opm::TimeService::to_time_t(tp) );
char buffer[12];
std::snprintf(buffer, 12, "%2d-%3s-%4d", ts.day(), month_names[ts.month() - 1].c_str(), ts.year());
return std::string(buffer, 11);
}
const std::string block_header_line(const std::string& run_name) {
std::string date_string = format_date( std::chrono::system_clock::from_time_t( std::time(nullptr)));
std::string date_string = format_date( Opm::TimeService::from_time_t( std::time(nullptr)));
return "SUMMARY OF RUN " + run_name + " at: " + date_string + " OPM FLOW " + PROJECT_VERSION_NAME;
}

View File

@@ -38,22 +38,17 @@
namespace Opm { namespace EclIO {
EclFile::EclFile(const std::string& filename, bool preload) : inputFilename(filename)
{
if (!fileExists(filename))
throw std::runtime_error("Can not open EclFile: {}");
void EclFile::load(bool preload) {
std::fstream fileH;
formatted = isFormatted(filename);
if (formatted) {
fileH.open(filename, std::ios::in);
fileH.open(this->inputFilename, std::ios::in);
} else {
fileH.open(filename, std::ios::in | std::ios::binary);
fileH.open(this->inputFilename, std::ios::in | std::ios::binary);
}
if (!fileH)
//throw std::runtime_error(fmt::format("Can not open EclFile: {}", this->inputFilename));
throw std::runtime_error("Can not open EclFile: {}");
int n = 0;
@@ -103,6 +98,25 @@ EclFile::EclFile(const std::string& filename, bool preload) : inputFilename(file
}
EclFile::EclFile(const std::string& filename, EclFile::Formatted fmt, bool preload) :
formatted(fmt.value),
inputFilename(filename)
{
this->load(preload);
}
EclFile::EclFile(const std::string& filename, bool preload) :
inputFilename(filename)
{
if (!fileExists(filename))
throw std::runtime_error("Can not open EclFile: {}");
formatted = isFormatted(filename);
this->load(preload);
}
void EclFile::loadBinaryArray(std::fstream& fileH, std::size_t arrIndex)
{
fileH.seekg (ifStreamPos[arrIndex], fileH.beg);

View File

@@ -71,6 +71,17 @@ bool Opm::EclIO::fileExists(const std::string& filename){
return fileH.good();
}
bool Opm::EclIO::is_number(const std::string& numstr)
{
for (char const &c : numstr)
if (std::isdigit(c) == 0)
return false;
return true;
}
bool Opm::EclIO::isFormatted(const std::string& filename)
{
const auto p = filename.find_last_of(".");

View File

@@ -48,8 +48,8 @@ RstGroup::RstGroup(const ::Opm::UnitSystem& unit_system,
const double * xgrp) :
name(trim_copy(zwel[0])),
parent_group(igrp[header.nwgmax + VI::IGroup::ParentGroup] ),
prod_active_cmode(igrp[header.nwgmax + VI::IGroup::ProdActiveCMode]),
gconprod_cmode(igrp[header.nwgmax + VI::IGroup::GConProdCMode]),
// prod_active_cmode(igrp[header.nwgmax + VI::IGroup::ProdActiveCMode]),
prod_cmode(igrp[header.nwgmax + VI::IGroup::GConProdCMode]),
winj_cmode(igrp[header.nwgmax + VI::IGroup::WInjCMode]),
ginj_cmode(igrp[header.nwgmax + VI::IGroup::GInjCMode]),
guide_rate_def(igrp[header.nwgmax + VI::IGroup::GuideRateDef]),