Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update the embedded date library #22

Merged
merged 2 commits into from
Mar 25, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions NEWS.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
# tzdb (development version)

* Updated the embedded date library
(SHA 9ea5654c1206e19245dc21d8a2c433e090c8c3f5) (#22).

* Updated the time zone database to 2022a (#21).

* R >=3.4.0 is now required. This is consistent with the standards of the
Expand Down
21 changes: 21 additions & 0 deletions inst/include/date/ptz.h
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,11 @@
// Posix::time_zone tz{"EST5EDT,M3.2.0,M11.1.0"};
// zoned_time<system_clock::duration, Posix::time_zone> zt{tz, system_clock::now()};
//
// In C++17 CTAD simplifies this to:
//
// Posix::time_zone tz{"EST5EDT,M3.2.0,M11.1.0"};
// zoned_time zt{tz, system_clock::now()};
//
// If the rule set is missing (everything starting with ','), then the rule is that the
// alternate offset is never enabled.
//
Expand Down Expand Up @@ -678,6 +683,8 @@ read_date(const string_t& s, unsigned i, rule& r)
++i;
unsigned n;
i = read_unsigned(s, i, 3, n, "Expected to find the Julian day [1, 365]");
if (!(1 <= n && n <= 365))
throw_invalid(s, i-1, "Expected Julian day to be in the range [1, 365]");
r.mode_ = rule::J;
r.n_ = n;
}
Expand All @@ -686,16 +693,22 @@ read_date(const string_t& s, unsigned i, rule& r)
++i;
unsigned m;
i = read_unsigned(s, i, 2, m, "Expected to find month [1, 12]");
if (!(1 <= m && m <= 12))
throw_invalid(s, i-1, "Expected month to be in the range [1, 12]");
if (i == s.size() || s[i] != '.')
throw_invalid(s, i, "Expected '.' after month");
++i;
unsigned n;
i = read_unsigned(s, i, 1, n, "Expected to find week number [1, 5]");
if (!(1 <= n && n <= 5))
throw_invalid(s, i-1, "Expected week number to be in the range [1, 5]");
if (i == s.size() || s[i] != '.')
throw_invalid(s, i, "Expected '.' after weekday index");
++i;
unsigned wd;
i = read_unsigned(s, i, 1, wd, "Expected to find day of week [0, 6]");
if (wd > 6)
throw_invalid(s, i-1, "Expected day of week to be in the range [0, 6]");
r.mode_ = rule::M;
r.m_ = month{m};
r.wd_ = weekday{wd};
Expand All @@ -705,6 +718,8 @@ read_date(const string_t& s, unsigned i, rule& r)
{
unsigned n;
i = read_unsigned(s, i, 3, n);
if (n > 365)
throw_invalid(s, i-1, "Expected Julian day to be in the range [0, 365]");
r.mode_ = rule::N;
r.n_ = n;
}
Expand Down Expand Up @@ -786,16 +801,22 @@ read_unsigned_time(const string_t& s, unsigned i, std::chrono::seconds& t)
throw_invalid(s, i, "Expected to read unsigned time, but found end of string");
unsigned x;
i = read_unsigned(s, i, 2, x, "Expected to find hours [0, 24]");
if (x > 24)
throw_invalid(s, i-1, "Expected hours to be in the range [0, 24]");
t = hours{x};
if (i != s.size() && s[i] == ':')
{
++i;
i = read_unsigned(s, i, 2, x, "Expected to find minutes [0, 59]");
if (x > 59)
throw_invalid(s, i-1, "Expected minutes to be in the range [0, 59]");
t += minutes{x};
if (i != s.size() && s[i] == ':')
{
++i;
i = read_unsigned(s, i, 2, x, "Expected to find seconds [0, 59]");
if (x > 59)
throw_invalid(s, i-1, "Expected seconds to be in the range [0, 59]");
t += seconds{x};
}
}
Expand Down
2 changes: 1 addition & 1 deletion inst/include/date/tz.h
Original file line number Diff line number Diff line change
Expand Up @@ -845,7 +845,7 @@ class time_zone
load_data(std::istream& inf, std::int32_t tzh_leapcnt, std::int32_t tzh_timecnt,
std::int32_t tzh_typecnt, std::int32_t tzh_charcnt);
#else // !USE_OS_TZDB
DATE_API sys_info get_info_impl(sys_seconds tp, int timezone) const;
DATE_API sys_info get_info_impl(sys_seconds tp, int tz_int) const;
DATE_API void adjust_infos(const std::vector<detail::Rule>& rules);
DATE_API void parse_info(std::istream& in);
#endif // !USE_OS_TZDB
Expand Down
70 changes: 9 additions & 61 deletions src/tz.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -198,7 +198,6 @@ namespace
using co_task_mem_ptr = std::unique_ptr<wchar_t[], task_mem_deleter>;
}

// tzdb-edit-start
static
std::wstring
convert_utf8_to_utf16(const std::string& s)
Expand Down Expand Up @@ -227,7 +226,6 @@ convert_utf8_to_utf16(const std::string& s)

return out;
}
// tzdb-edit-stop

// We might need to know certain locations even if not using the remote API,
// so keep these routines out of that block for now.
Expand Down Expand Up @@ -298,8 +296,6 @@ get_download_folder()

# endif // !_WIN32


// tzdb-edit-start
/*
* This class is provided to mimic the following usage of `ifstream`:
*
Expand Down Expand Up @@ -332,18 +328,20 @@ class file_streambuf
char buffer_[buffer_size_];

public:
file_streambuf(const std::string& filename)
: file_(file_open(filename))
{
}

~file_streambuf()
{
if (file_)
{
::fclose(file_);
}
}
file_streambuf(const file_streambuf&) = delete;
file_streambuf& operator=(const file_streambuf&) = delete;

file_streambuf(const std::string& filename)
: file_(file_open(filename))
{
}

protected:
virtual
Expand Down Expand Up @@ -380,7 +378,6 @@ class file_streambuf
return file;
}
};
// tzdb-edit-stop

#endif // !USE_OS_TZDB

Expand Down Expand Up @@ -418,9 +415,9 @@ access_install()
}

void
set_install(const std::string& s)
set_install(const std::string& install)
{
access_install() = s;
access_install() = install;
}

static
Expand Down Expand Up @@ -674,19 +671,8 @@ load_timezone_mappings_from_xml_file(const std::string& input_path)
std::vector<detail::timezone_mapping> mappings;
std::string line;

// tzdb-edit-start
// std::ifstream is(input_path);
// if (!is.is_open())
// {
// // We don't emit file exceptions because that's an implementation detail.
// std::string msg = "Error opening time zone mapping file \"";
// msg += input_path;
// msg += "\".";
// throw std::runtime_error(msg);
// }
file_streambuf ibuf(input_path);
std::istream is(&ibuf);
// tzdb-edit-stop

auto error = [&input_path, &line_num](const char* info)
{
Expand Down Expand Up @@ -816,9 +802,6 @@ load_timezone_mappings_from_xml_file(const std::string& input_path)
}
}

// tzdb-edit-start
// is.close();
// tzdb-edit-stop
return mappings;
}

Expand Down Expand Up @@ -2969,11 +2952,8 @@ bool
file_exists(const std::string& filename)
{
#ifdef _WIN32
// tzdb-edit-start
// return ::_access(filename.c_str(), 0) == 0;
std::wstring wfilename = convert_utf8_to_utf16(filename);
return ::_waccess(wfilename.c_str(), 0) == 0;
// tzdb-edit-stop
#else
return ::access(filename.c_str(), F_OK) == 0;
#endif
Expand Down Expand Up @@ -3545,34 +3525,6 @@ remote_install(const std::string& version)

#endif // HAS_REMOTE_API

// tzdb-edit-start
// static
// std::string
// get_version(const std::string& path)
// {
// std::string version;
// std::ifstream infile(path + "version");
// if (infile.is_open())
// {
// infile >> version;
// if (!infile.fail())
// return version;
// }
// else
// {
// infile.open(path + "NEWS");
// while (infile)
// {
// infile >> version;
// if (version == "Release")
// {
// infile >> version;
// return version;
// }
// }
// }
// throw std::runtime_error("Unable to get Timezone database version from " + path);
// }
static
std::string
get_version(const std::string& path)
Expand Down Expand Up @@ -3612,7 +3564,6 @@ get_version(const std::string& path)

throw std::runtime_error("Unable to get Timezone database version from " + path);
}
// tzdb-edit-stop

static
std::unique_ptr<tzdb>
Expand Down Expand Up @@ -3682,16 +3633,13 @@ init_tzdb()

for (const auto& filename : files)
{
// tzdb-edit-start
// std::ifstream infile(path + filename);
std::string file_path = path + filename;
if (!file_exists(file_path))
{
continue;
}
file_streambuf inbuf(file_path);
std::istream infile(&inbuf);
// tzdb-edit-stop
while (infile)
{
std::getline(infile, line);
Expand Down