// <chrono> -*- C++ -*-

// Copyright (C) 2008-2025 Free Software Foundation, Inc.
//
// This file is part of the GNU ISO C++ Library.  This library 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, or (at your option)
// any later version.

// This library 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.

// Under Section 7 of GPL version 3, you are granted additional
// permissions described in the GCC Runtime Library Exception, version
// 3.1, as published by the Free Software Foundation.

// You should have received a copy of the GNU General Public License and
// a copy of the GCC Runtime Library Exception along with this program;
// see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
// <http://www.gnu.org/licenses/>.

// [time]

/** @file include/chrono
 *  This is a Standard C++ Library header.
 *  @ingroup chrono
 */

#ifndef _GLIBCXX_CHRONO
#define _GLIBCXX_CHRONO 1

#ifdef _GLIBCXX_SYSHDR
#pragma GCC system_header
#endif

#ifdef _GLIBCXX_NO_FREESTANDING_CHRONO
# include <bits/requires_hosted.h> // for <ctime> and clocks
#endif

#if __cplusplus < 201103L
# include <bits/c++0x_warning.h>
#else

#define __glibcxx_want_chrono
#define __glibcxx_want_chrono_udls
#include <bits/version.h>

#include <bits/chrono.h>

#if __cpp_lib_bitops >= 201907L
# include <bit> // __countr_zero
#endif
#ifdef __glibcxx_chrono_cxx20
# include <bits/stl_algo.h>     // upper_bound
# include <bits/range_access.h> // begin/end for arrays
#endif
#if __cpp_lib_chrono >= 201803L // C++20 && HOSTED && USE_CXX11_ABI
# include <sstream>
# include <string>
# include <vector>
# include <bits/shared_ptr.h>
# include <bits/unique_ptr.h>
#endif
#if __glibcxx_chrono_cxx20 >= 202306L // C++26
# include <bits/functional_hash.h>
#endif

namespace std _GLIBCXX_VISIBILITY(default)
{
_GLIBCXX_BEGIN_NAMESPACE_VERSION

  /**
   * @defgroup chrono Time
   * @ingroup utilities
   *
   * Classes and functions for time.
   *
   * @since C++11
   */

  /** @namespace std::chrono
   *  @brief ISO C++ 2011 namespace for date and time utilities
   *  @ingroup chrono
   */
  namespace chrono
  {
#ifdef __glibcxx_chrono_cxx20
    /// @addtogroup chrono
    /// @{
    struct local_t { };
    template<typename _Duration>
      using local_time = time_point<local_t, _Duration>;
    using local_seconds = local_time<seconds>;
    using local_days = local_time<days>;

#if _GLIBCXX_HOSTED
    class utc_clock;
    class tai_clock;
    class gps_clock;

    template<typename _Duration>
      using utc_time = time_point<utc_clock, _Duration>;
    using utc_seconds = utc_time<seconds>;

    template<typename _Duration>
      using tai_time = time_point<tai_clock, _Duration>;
    using tai_seconds = tai_time<seconds>;

    template<typename _Duration>
      using gps_time = time_point<gps_clock, _Duration>;
    using gps_seconds = gps_time<seconds>;

    template<> struct is_clock<utc_clock> : true_type { };
    template<> struct is_clock<tai_clock> : true_type { };
    template<> struct is_clock<gps_clock> : true_type { };

    template<> inline constexpr bool is_clock_v<utc_clock> = true;
    template<> inline constexpr bool is_clock_v<tai_clock> = true;
    template<> inline constexpr bool is_clock_v<gps_clock> = true;

    struct leap_second_info
    {
      bool is_leap_second;
      seconds elapsed;
    };

    template<typename _Duration>
      leap_second_info
      get_leap_second_info(const utc_time<_Duration>& __ut);

    /** A clock that measures Universal Coordinated Time (UTC).
     *
     * The epoch is 1970-01-01 00:00:00.
     *
     * @since C++20
     */
    class utc_clock
    {
    public:
      using rep                       = system_clock::rep;
      using period                    = system_clock::period;
      using duration                  = chrono::duration<rep, period>;
      using time_point                = chrono::time_point<utc_clock>;
      static constexpr bool is_steady = false;

      [[nodiscard]]
      static time_point
      now()
      { return from_sys(system_clock::now()); }

      template<typename _Duration>
	[[nodiscard]]
	static sys_time<common_type_t<_Duration, seconds>>
	to_sys(const utc_time<_Duration>& __t)
	{
	  using _CDur = common_type_t<_Duration, seconds>;
	  const auto __li = chrono::get_leap_second_info(__t);
	  sys_time<_CDur> __s{__t.time_since_epoch() - __li.elapsed};
	  if (__li.is_leap_second)
	    __s = chrono::floor<seconds>(__s) + seconds{1} - _CDur{1};
	  return __s;
	}

      template<typename _Duration>
	[[nodiscard]]
	static utc_time<common_type_t<_Duration, seconds>>
	from_sys(const sys_time<_Duration>& __t);
    };

    /** A clock that measures International Atomic Time.
     *
     * The epoch is 1958-01-01 00:00:00.
     *
     * @since C++20
     */
    class tai_clock
    {
    public:
      using rep                       = system_clock::rep;
      using period                    = system_clock::period;
      using duration                  = chrono::duration<rep, period>;
      using time_point                = chrono::time_point<tai_clock>;
      static constexpr bool is_steady = false;

      [[nodiscard]]
      static time_point
      now();  // in src/c++20/clock.cc

      template<typename _Duration>
	[[nodiscard]]
	static utc_time<common_type_t<_Duration, seconds>>
	to_utc(const tai_time<_Duration>& __t)
	{
	  using _CDur = common_type_t<_Duration, seconds>;
	  return utc_time<_CDur>{__t.time_since_epoch()} - 378691210s;
	}

      template<typename _Duration>
	[[nodiscard]]
	static tai_time<common_type_t<_Duration, seconds>>
	from_utc(const utc_time<_Duration>& __t)
	{
	  using _CDur = common_type_t<_Duration, seconds>;
	  return tai_time<_CDur>{__t.time_since_epoch()} + 378691210s;
	}
    };

    /** A clock that measures GPS time.
     *
     * The epoch is 1980-01-06 00:00:00.
     *
     * @since C++20
     */
    class gps_clock
    {
    public:
      using rep                       = system_clock::rep;
      using period                    = system_clock::period;
      using duration                  = chrono::duration<rep, period>;
      using time_point                = chrono::time_point<gps_clock>;
      static constexpr bool is_steady = false;

      [[nodiscard]]
      static time_point
      now();  // in src/c++20/clock.cc

      template<typename _Duration>
	[[nodiscard]]
	static utc_time<common_type_t<_Duration, seconds>>
	to_utc(const gps_time<_Duration>& __t)
	{
	  using _CDur = common_type_t<_Duration, seconds>;
	  return utc_time<_CDur>{__t.time_since_epoch()} + 315964809s;
	}

      template<typename _Duration>
	[[nodiscard]]
	static gps_time<common_type_t<_Duration, seconds>>
	from_utc(const utc_time<_Duration>& __t)
	{
	  using _CDur = common_type_t<_Duration, seconds>;
	  return gps_time<_CDur>{__t.time_since_epoch()} - 315964809s;
	}
    };
#endif // _GLIBCXX_HOSTED

    template<typename _DestClock, typename _SourceClock>
      struct clock_time_conversion
      { };

    // Identity conversions

    template<typename _Clock>
      struct clock_time_conversion<_Clock, _Clock>
      {
	template<typename _Duration>
	  time_point<_Clock, _Duration>
	  operator()(const time_point<_Clock, _Duration>& __t) const
	  { return __t; }
      };

#if _GLIBCXX_HOSTED
    template<>
      struct clock_time_conversion<system_clock, system_clock>
      {
	template<typename _Duration>
	  sys_time<_Duration>
	  operator()(const sys_time<_Duration>& __t) const
	  { return __t; }
      };

    template<>
      struct clock_time_conversion<utc_clock, utc_clock>
      {
	template<typename _Duration>
	  utc_time<_Duration>
	  operator()(const utc_time<_Duration>& __t) const
	  { return __t; }
      };

    // Conversions between system_clock and utc_clock

    template<>
      struct clock_time_conversion<utc_clock, system_clock>
      {
	template<typename _Duration>
	  utc_time<common_type_t<_Duration, seconds>>
	  operator()(const sys_time<_Duration>& __t) const
	  { return utc_clock::from_sys(__t); }
      };

    template<>
      struct clock_time_conversion<system_clock, utc_clock>
      {
	template<typename _Duration>
	  sys_time<common_type_t<_Duration, seconds>>
	  operator()(const utc_time<_Duration>& __t) const
	  { return utc_clock::to_sys(__t); }
      };

    template<typename _Tp, typename _Clock>
      inline constexpr bool __is_time_point_for_v = false;

    template<typename _Clock, typename _Duration>
      inline constexpr bool
       __is_time_point_for_v<time_point<_Clock, _Duration>, _Clock> = true;

    // Conversions between system_clock and other clocks

    template<typename _SourceClock>
      struct clock_time_conversion<system_clock, _SourceClock>
      {
	template<typename _Duration, typename _Src = _SourceClock>
	  auto
	  operator()(const time_point<_SourceClock, _Duration>& __t) const
	  -> decltype(_Src::to_sys(__t))
	  {
	    using _Ret = decltype(_SourceClock::to_sys(__t));
	    static_assert(__is_time_point_for_v<_Ret, system_clock>);
	    return _SourceClock::to_sys(__t);
	  }
      };

    template<typename _DestClock>
      struct clock_time_conversion<_DestClock, system_clock>
      {
	template<typename _Duration, typename _Dest = _DestClock>
	  auto
	  operator()(const sys_time<_Duration>& __t) const
	  -> decltype(_Dest::from_sys(__t))
	  {
	    using _Ret = decltype(_DestClock::from_sys(__t));
	    static_assert(__is_time_point_for_v<_Ret, _DestClock>);
	    return _DestClock::from_sys(__t);
	  }
      };

    // Conversions between utc_clock and other clocks

    template<typename _SourceClock>
      struct clock_time_conversion<utc_clock, _SourceClock>
      {
	template<typename _Duration, typename _Src = _SourceClock>
	  auto
	  operator()(const time_point<_SourceClock, _Duration>& __t) const
	  -> decltype(_Src::to_utc(__t))
	  {
	    using _Ret = decltype(_SourceClock::to_utc(__t));
	    static_assert(__is_time_point_for_v<_Ret, utc_clock>);
	    return _SourceClock::to_utc(__t);
	  }
      };

    template<typename _DestClock>
      struct clock_time_conversion<_DestClock, utc_clock>
      {
	template<typename _Duration, typename _Dest = _DestClock>
	  auto
	  operator()(const utc_time<_Duration>& __t) const
	  -> decltype(_Dest::from_utc(__t))
	  {
	    using _Ret = decltype(_DestClock::from_utc(__t));
	    static_assert(__is_time_point_for_v<_Ret, _DestClock>);
	    return _DestClock::from_utc(__t);
	  }
      };
#endif // _GLIBCXX_HOSTED

    /// @cond undocumented
    namespace __detail
    {
      template<typename _DestClock, typename _SourceClock, typename _Duration>
       concept __clock_convs
	  = requires (const time_point<_SourceClock, _Duration>& __t) {
	    clock_time_conversion<_DestClock, _SourceClock>{}(__t);
	  };

#if _GLIBCXX_HOSTED
      template<typename _DestClock, typename _SourceClock, typename _Duration>
       concept __clock_convs_sys
	  = requires (const time_point<_SourceClock, _Duration>& __t) {
	    clock_time_conversion<_DestClock, system_clock>{}(
	      clock_time_conversion<system_clock, _SourceClock>{}(__t));
	  };

      template<typename _DestClock, typename _SourceClock, typename _Duration>
       concept __clock_convs_utc
	  = requires (const time_point<_SourceClock, _Duration>& __t) {
	    clock_time_conversion<_DestClock, utc_clock>{}(
	      clock_time_conversion<utc_clock, _SourceClock>{}(__t));
	  };

      template<typename _DestClock, typename _SourceClock, typename _Duration>
	concept __clock_convs_sys_utc
	  = requires (const time_point<_SourceClock, _Duration>& __t) {
	    clock_time_conversion<_DestClock, utc_clock>{}(
	      clock_time_conversion<utc_clock, system_clock>{}(
		clock_time_conversion<system_clock, _SourceClock>{}(__t)));
	  };

      template<typename _DestClock, typename _SourceClock, typename _Duration>
       concept __clock_convs_utc_sys
	  = requires (const time_point<_SourceClock, _Duration>& __t) {
	    clock_time_conversion<_DestClock, system_clock>{}(
	      clock_time_conversion<system_clock, utc_clock>{}(
		clock_time_conversion<utc_clock, _SourceClock>{}(__t)));
	  };
#endif // _GLIBCXX_HOSTED
    } // namespace __detail
    /// @endcond

    /// Convert a time point to a different clock.
    template<typename _DestClock, typename _SourceClock, typename _Duration>
      [[nodiscard]]
      inline auto
      clock_cast(const time_point<_SourceClock, _Duration>& __t)
      requires __detail::__clock_convs<_DestClock, _SourceClock, _Duration>
#if _GLIBCXX_HOSTED
	|| __detail::__clock_convs_sys<_DestClock, _SourceClock, _Duration>
	|| __detail::__clock_convs_utc<_DestClock, _SourceClock, _Duration>
	|| __detail::__clock_convs_sys_utc<_DestClock, _SourceClock, _Duration>
	|| __detail::__clock_convs_utc_sys<_DestClock, _SourceClock, _Duration>
#endif // _GLIBCXX_HOSTED
      {
       constexpr bool __direct
	 = __detail::__clock_convs<_DestClock, _SourceClock, _Duration>;
       if constexpr (__direct)
	 {
	   return clock_time_conversion<_DestClock, _SourceClock>{}(__t);
	 }
#if _GLIBCXX_HOSTED
       else
	 {
	   constexpr bool __convert_via_sys_clock
	     = __detail::__clock_convs_sys<_DestClock, _SourceClock, _Duration>;
	   constexpr bool __convert_via_utc_clock
	     = __detail::__clock_convs_utc<_DestClock, _SourceClock, _Duration>;
	   if constexpr (__convert_via_sys_clock)
	     {
	       static_assert(!__convert_via_utc_clock,
		 "clock_cast requires a unique best conversion, but "
		 "conversion is possible via system_clock and also via"
		 "utc_clock");
	       return clock_time_conversion<_DestClock, system_clock>{}(
			clock_time_conversion<system_clock, _SourceClock>{}(__t));
	     }
	   else if constexpr (__convert_via_utc_clock)
	     {
	       return clock_time_conversion<_DestClock, utc_clock>{}(
			clock_time_conversion<utc_clock, _SourceClock>{}(__t));
	     }
	   else
	     {
	       constexpr bool __convert_via_sys_and_utc_clocks
		 = __detail::__clock_convs_sys_utc<_DestClock,
						   _SourceClock,
						   _Duration>;

	       if constexpr (__convert_via_sys_and_utc_clocks)
		 {
		   constexpr bool __convert_via_utc_and_sys_clocks
		     = __detail::__clock_convs_utc_sys<_DestClock,
						       _SourceClock,
						       _Duration>;
		   static_assert(!__convert_via_utc_and_sys_clocks,
		     "clock_cast requires a unique best conversion, but "
		     "conversion is possible via system_clock followed by "
		     "utc_clock, and also via utc_clock followed by "
		     "system_clock");
		   return clock_time_conversion<_DestClock, utc_clock>{}(
			    clock_time_conversion<utc_clock, system_clock>{}(
			      clock_time_conversion<system_clock, _SourceClock>{}(__t)));
		 }
	       else
		 {
		   return clock_time_conversion<_DestClock, system_clock>{}(
			    clock_time_conversion<system_clock, utc_clock>{}(
			      clock_time_conversion<utc_clock, _SourceClock>{}(__t)));
		 }
	     }
	 }
#endif // _GLIBCXX_HOSTED
      }

    // CALENDRICAL TYPES

    // CLASS DECLARATIONS
    class day;
    class month;
    class year;
    class weekday;
    class weekday_indexed;
    class weekday_last;
    class month_day;
    class month_day_last;
    class month_weekday;
    class month_weekday_last;
    class year_month;
    class year_month_day;
    class year_month_day_last;
    class year_month_weekday;
    class year_month_weekday_last;

    struct last_spec
    {
      explicit last_spec() = default;

      friend constexpr month_day_last
      operator/(int __m, last_spec) noexcept;

      friend constexpr month_day_last
      operator/(last_spec, int __m) noexcept;
    };

    inline constexpr last_spec last{};

    namespace __detail
    {
      // Helper to __add_modulo and __sub_modulo.
      template <unsigned __d, typename _Tp>
      consteval auto
      __modulo_offset()
      {
	using _Up = make_unsigned_t<_Tp>;
	auto constexpr __a = _Up(-1) - _Up(255 + __d - 2);
	auto constexpr __b = _Up(__d * (__a / __d) - 1);
	// Notice: b <= a - 1 <= _Up(-1) - (255 + d - 1) and b % d = d - 1.
	return _Up(-1) - __b; // >= 255 + d - 1
      }

      // Compute the remainder of the Euclidean division of __x + __y divided by
      // __d without overflowing.  Typically, __x <= 255 + d - 1 is sum of
      // weekday/month with a shift in [0, d - 1] and __y is a duration count.
      template <unsigned __d, typename _Tp>
      constexpr unsigned
      __add_modulo(unsigned __x, _Tp __y)
      {
	using _Up = make_unsigned_t<_Tp>;
	// For __y >= 0, _Up(__y) has the same mathematical value as __y and
	// this function simply returns (__x + _Up(__y)) % d.  Typically, this
	// doesn't overflow since the range of _Up contains many more positive
	// values than _Tp's.  For __y < 0, _Up(__y) has a mathematical value in
	// the upper-half range of _Up so that adding a positive value to it
	// might overflow.  Moreover, most likely, _Up(__y) != __y mod d.  To
	// fix both issues we subtract from _Up(__y) an __offset >=
	// 255 + d - 1 to make room for the addition to __x and shift the modulo
	// to the correct value.
	auto const __offset = __y >= 0 ? _Up(0) : __modulo_offset<__d, _Tp>();
	return (__x + _Up(__y) - __offset) % __d;
      }

      // Similar to __add_modulo but for __x - __y.
      template <unsigned __d, typename _Tp>
      constexpr unsigned
      __sub_modulo(unsigned __x, _Tp __y)
      {
	using _Up = make_unsigned_t<_Tp>;
	auto const __offset = __y <= 0 ? _Up(0) : __modulo_offset<__d, _Tp>();
	return (__x - _Up(__y) - __offset) % __d;
      }

      inline constexpr unsigned __days_per_month[12]
	= { 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };
    }

    // DAY

    class day
    {
    private:
      unsigned char _M_d;

    public:
      day() = default;

      explicit constexpr
      day(unsigned __d) noexcept
      : _M_d(__d)
      { }

      constexpr day&
      operator++() noexcept
      {
	++_M_d;
	return *this;
      }

      constexpr day
      operator++(int) noexcept
      {
	auto __ret = *this;
	++(*this);
	return __ret;
      }

      constexpr day&
      operator--() noexcept
      {
	--_M_d;
	return *this;
      }

      constexpr day
      operator--(int) noexcept
      {
	auto __ret = *this;
	--(*this);
	return __ret;
      }

      constexpr day&
      operator+=(const days& __d) noexcept
      {
	*this = *this + __d;
	return *this;
      }

      constexpr day&
      operator-=(const days& __d) noexcept
      {
	*this = *this - __d;
	return *this;
      }

      constexpr explicit
      operator unsigned() const noexcept
      { return _M_d; }

      constexpr bool
      ok() const noexcept
      { return 1 <= _M_d && _M_d <= 31; }

      friend constexpr bool
      operator==(const day& __x, const day& __y) noexcept
      { return unsigned{__x} == unsigned{__y}; }

      friend constexpr strong_ordering
      operator<=>(const day& __x, const day& __y) noexcept
      { return unsigned{__x} <=> unsigned{__y}; }

      friend constexpr day
      operator+(const day& __x, const days& __y) noexcept
      { return day(unsigned{__x} + __y.count()); }

      friend constexpr day
      operator+(const days& __x, const day& __y) noexcept
      { return __y + __x; }

      friend constexpr day
      operator-(const day& __x, const days& __y) noexcept
      { return __x + -__y; }

      friend constexpr days
      operator-(const day& __x, const day& __y) noexcept
      { return days{int(unsigned{__x}) - int(unsigned{__y})}; }

      friend constexpr month_day
      operator/(const month& __m, const day& __d) noexcept;

      friend constexpr month_day
      operator/(int __m, const day& __d) noexcept;

      friend constexpr month_day
      operator/(const day& __d, const month& __m) noexcept;

      friend constexpr month_day
      operator/(const day& __d, int __m) noexcept;

      friend constexpr year_month_day
      operator/(const year_month& __ym, const day& __d) noexcept;
    };

    // MONTH

    class month
    {
    private:
      unsigned char _M_m;

    public:
      month() = default;

      explicit constexpr
      month(unsigned __m) noexcept
      : _M_m(__m)
      { }

      constexpr month&
      operator++() noexcept
      {
	*this += months{1};
	return *this;
      }

      constexpr month
      operator++(int) noexcept
      {
	auto __ret = *this;
	++(*this);
	return __ret;
      }

      constexpr month&
      operator--() noexcept
      {
	*this -= months{1};
	return *this;
      }

      constexpr month
      operator--(int) noexcept
      {
	auto __ret = *this;
	--(*this);
	return __ret;
      }

      constexpr month&
      operator+=(const months& __m) noexcept
      {
	*this = *this + __m;
	return *this;
      }

      constexpr month&
      operator-=(const months& __m) noexcept
      {
	*this = *this - __m;
	return *this;
      }

      explicit constexpr
      operator unsigned() const noexcept
      { return _M_m; }

      constexpr bool
      ok() const noexcept
      { return 1 <= _M_m && _M_m <= 12; }

      friend constexpr bool
      operator==(const month& __x, const month& __y) noexcept
      { return unsigned{__x} == unsigned{__y}; }

      friend constexpr strong_ordering
      operator<=>(const month& __x, const month& __y) noexcept
      { return unsigned{__x} <=> unsigned{__y}; }

      friend constexpr month
      operator+(const month& __x, const months& __y) noexcept
      {
	// modulo(x + (y - 1), 12) = modulo(x + (y - 1) + 12, 12)
	//                         = modulo((x + 11) + y    , 12)
	return month{1 + __detail::__add_modulo<12>(
	  unsigned{__x} + 11, __y.count())};
      }

      friend constexpr month
      operator+(const months& __x,  const month& __y) noexcept
      { return __y + __x; }

      friend constexpr month
      operator-(const month& __x, const months& __y) noexcept
      {
	// modulo(x + (-y - 1), 12) = modulo(x + (-y - 1) + 12, 12)
	//                          = modulo((x + 11) - y     , 12)
	return month{1 + __detail::__sub_modulo<12>(
	  unsigned{__x} + 11, __y.count())};
      }

      friend constexpr months
      operator-(const month& __x,  const month& __y) noexcept
      {
	const auto __dm = int(unsigned(__x)) - int(unsigned(__y));
	return months{__dm < 0 ? 12 + __dm : __dm};
      }

      friend constexpr year_month
      operator/(const year& __y, const month& __m) noexcept;

      friend constexpr month_day
      operator/(const month& __m, int __d) noexcept;

      friend constexpr month_day_last
      operator/(const month& __m, last_spec) noexcept;

      friend constexpr month_day_last
      operator/(last_spec, const month& __m) noexcept;

      friend constexpr month_weekday
      operator/(const month& __m, const weekday_indexed& __wdi) noexcept;

      friend constexpr month_weekday
      operator/(const weekday_indexed& __wdi, const month& __m) noexcept;

      friend constexpr month_weekday_last
      operator/(const month& __m, const weekday_last& __wdl) noexcept;

      friend constexpr month_weekday_last
      operator/(const weekday_last& __wdl, const month& __m) noexcept;
    };

    inline constexpr month January{1};
    inline constexpr month February{2};
    inline constexpr month March{3};
    inline constexpr month April{4};
    inline constexpr month May{5};
    inline constexpr month June{6};
    inline constexpr month July{7};
    inline constexpr month August{8};
    inline constexpr month September{9};
    inline constexpr month October{10};
    inline constexpr month November{11};
    inline constexpr month December{12};

    // YEAR

    class year
    {
    private:
      short _M_y;

    public:
      year() = default;

      explicit constexpr
      year(int __y) noexcept
      : _M_y{static_cast<short>(__y)}
      { }

      static constexpr year
      min() noexcept
      { return year{-32767}; }

      static constexpr year
      max() noexcept
      { return year{32767}; }

      constexpr year&
      operator++() noexcept
      {
	++_M_y;
	return *this;
      }

      constexpr year
      operator++(int) noexcept
      {
	auto __ret = *this;
	++(*this);
	return __ret;
      }

      constexpr year&
      operator--() noexcept
      {
	--_M_y;
	return *this;
      }

      constexpr year
      operator--(int) noexcept
      {
	auto __ret = *this;
	--(*this);
	return __ret;
      }

      constexpr year&
      operator+=(const years& __y) noexcept
      {
	*this = *this + __y;
	return *this;
      }

      constexpr year&
      operator-=(const years& __y) noexcept
      {
	*this = *this - __y;
	return *this;
      }

      constexpr year
      operator+() const noexcept
      { return *this; }

      constexpr year
      operator-() const noexcept
      { return year{-_M_y}; }

      constexpr bool
      is_leap() const noexcept
      {
	// Testing divisibility by 100 first gives better performance [1], i.e.,
	//     return _M_y % 100 == 0 ? _M_y % 400 == 0 : _M_y % 16 == 0;
	// Furthermore, if _M_y % 100 == 0, then _M_y % 400 == 0 is equivalent
	// to _M_y % 16 == 0, so we can simplify it to
	//     return _M_y % 100 == 0 ? _M_y % 16 == 0 : _M_y % 4 == 0.  // #1
	// Similarly, we can replace 100 with 25 (which is good since
	// _M_y % 25 == 0 requires one fewer instruction than _M_y % 100 == 0
	// [2]):
	//     return _M_y % 25 == 0 ? _M_y % 16 == 0 : _M_y % 4 == 0.  // #2
	// Indeed, first assume _M_y % 4 != 0.  Then _M_y % 16 != 0 and hence,
	// _M_y % 4 == 0 and _M_y % 16 == 0 are both false.  Therefore, #2
	// returns false as it should (regardless of _M_y % 25.) Now assume
	// _M_y % 4 == 0.  In this case, _M_y % 25 == 0 if, and only if,
	// _M_y % 100 == 0, that is, #1 and #2 are equivalent.  Finally, #2 is
	// equivalent to
	//     return (_M_y & (_M_y % 25 == 0 ? 15 : 3)) == 0.

	// References:
	// [1] https://github.com/cassioneri/calendar
	// [2] https://godbolt.org/z/55G8rn77e
	// [3] https://gcc.gnu.org/pipermail/libstdc++/2021-June/052815.html

	return (_M_y & (_M_y % 25 == 0 ? 15 : 3)) == 0;
      }

      explicit constexpr
      operator int() const noexcept
      { return _M_y; }

      constexpr bool
      ok() const noexcept
      { return min()._M_y <= _M_y && _M_y <= max()._M_y; }

      friend constexpr bool
      operator==(const year& __x, const year& __y) noexcept
      { return int{__x} == int{__y}; }

      friend constexpr strong_ordering
      operator<=>(const year& __x, const year& __y) noexcept
      { return int{__x} <=> int{__y}; }

      friend constexpr year
      operator+(const year& __x, const years& __y) noexcept
      { return year{int{__x} + static_cast<int>(__y.count())}; }

      friend constexpr year
      operator+(const years& __x, const year& __y) noexcept
      { return __y + __x; }

      friend constexpr year
      operator-(const year& __x, const years& __y) noexcept
      { return __x + -__y; }

      friend constexpr years
      operator-(const year& __x, const year& __y) noexcept
      { return years{int{__x} - int{__y}}; }

      friend constexpr year_month
      operator/(const year& __y, int __m) noexcept;

      friend constexpr year_month_day
      operator/(const year& __y, const month_day& __md) noexcept;

      friend constexpr year_month_day
      operator/(const month_day& __md, const year& __y) noexcept;

      friend constexpr year_month_day_last
      operator/(const year& __y, const month_day_last& __mdl) noexcept;

      friend constexpr year_month_day_last
      operator/(const month_day_last& __mdl, const year& __y) noexcept;

      friend constexpr year_month_weekday
      operator/(const year& __y, const month_weekday& __mwd) noexcept;

      friend constexpr year_month_weekday
      operator/(const month_weekday& __mwd, const year& __y) noexcept;

      friend constexpr year_month_weekday_last
      operator/(const year& __y, const month_weekday_last& __mwdl) noexcept;

      friend constexpr year_month_weekday_last
      operator/(const month_weekday_last& __mwdl, const year& __y) noexcept;
    };

    // WEEKDAY

    class weekday
    {
    private:
      unsigned char _M_wd;

      static constexpr weekday
      _S_from_days(const days& __d)
      {
	return weekday{__detail::__add_modulo<7>(4, __d.count())};
      }

    public:
      weekday() = default;

      explicit constexpr
      weekday(unsigned __wd) noexcept
      : _M_wd(__wd == 7 ? 0 : __wd) // __wd % 7 ?
      { }

      constexpr
      weekday(const sys_days& __dp) noexcept
      : weekday{_S_from_days(__dp.time_since_epoch())}
      { }

      explicit constexpr
      weekday(const local_days& __dp) noexcept
      : weekday{sys_days{__dp.time_since_epoch()}}
      { }

      constexpr weekday&
      operator++() noexcept
      {
	*this += days{1};
	return *this;
      }

      constexpr weekday
      operator++(int) noexcept
      {
	auto __ret = *this;
	++(*this);
	return __ret;
      }

      constexpr weekday&
      operator--() noexcept
      {
	*this -= days{1};
	return *this;
      }

      constexpr weekday
      operator--(int) noexcept
      {
	auto __ret = *this;
	--(*this);
	return __ret;
      }

      constexpr weekday&
      operator+=(const days& __d) noexcept
      {
	*this = *this + __d;
	return *this;
      }

      constexpr weekday&
      operator-=(const days& __d) noexcept
      {
	*this = *this - __d;
	return *this;
      }

      constexpr unsigned
      c_encoding() const noexcept
      { return _M_wd; }

      constexpr unsigned
      iso_encoding() const noexcept
      { return _M_wd == 0u ? 7u : _M_wd; }

      constexpr bool
      ok() const noexcept
      { return _M_wd <= 6; }

      constexpr weekday_indexed
      operator[](unsigned __index) const noexcept;

      constexpr weekday_last
      operator[](last_spec) const noexcept;

      friend constexpr bool
      operator==(const weekday& __x, const weekday& __y) noexcept
      { return __x._M_wd == __y._M_wd; }

      friend constexpr weekday
      operator+(const weekday& __x, const days& __y) noexcept
      {
	return weekday{__detail::__add_modulo<7>(__x._M_wd, __y.count())};
      }

      friend constexpr weekday
      operator+(const days& __x, const weekday& __y) noexcept
      { return __y + __x; }

      friend constexpr weekday
      operator-(const weekday& __x, const days& __y) noexcept
      {
	return weekday{__detail::__sub_modulo<7>(__x._M_wd, __y.count())};
      }

      friend constexpr days
      operator-(const weekday& __x, const weekday& __y) noexcept
      {
	const auto __n = __x.c_encoding() - __y.c_encoding();
	return static_cast<int>(__n) >= 0 ? days{__n} : days{__n + 7};
      }
    };

    inline constexpr weekday Sunday{0};
    inline constexpr weekday Monday{1};
    inline constexpr weekday Tuesday{2};
    inline constexpr weekday Wednesday{3};
    inline constexpr weekday Thursday{4};
    inline constexpr weekday Friday{5};
    inline constexpr weekday Saturday{6};

    // WEEKDAY_INDEXED

    class weekday_indexed
    {
    private:
      chrono::weekday _M_wd;
      unsigned char _M_index;

    public:
      weekday_indexed() = default;

      constexpr
      weekday_indexed(const chrono::weekday& __wd, unsigned __index) noexcept
      : _M_wd(__wd), _M_index(__index)
      { }

      constexpr chrono::weekday
      weekday() const noexcept
      { return _M_wd; }

      constexpr unsigned
      index() const noexcept
      { return _M_index; };

      constexpr bool
      ok() const noexcept
      { return _M_wd.ok() && 1 <= _M_index && _M_index <= 5; }

      friend constexpr bool
      operator==(const weekday_indexed& __x, const weekday_indexed& __y) noexcept
      { return __x.weekday() == __y.weekday() && __x.index() == __y.index(); }

      friend constexpr month_weekday
      operator/(const month& __m, const weekday_indexed& __wdi) noexcept;

      friend constexpr month_weekday
      operator/(int __m, const weekday_indexed& __wdi) noexcept;

      friend constexpr month_weekday
      operator/(const weekday_indexed& __wdi, const month& __m) noexcept;

      friend constexpr month_weekday
      operator/(const weekday_indexed& __wdi, int __m) noexcept;

      friend constexpr year_month_weekday
      operator/(const year_month& __ym, const weekday_indexed& __wdi) noexcept;
    };

    constexpr weekday_indexed
    weekday::operator[](unsigned __index) const noexcept
    { return {*this, __index}; }

    // WEEKDAY_LAST

    class weekday_last
    {
    private:
      chrono::weekday _M_wd;

    public:
      explicit constexpr
      weekday_last(const chrono::weekday& __wd) noexcept
      : _M_wd{__wd}
      { }

      constexpr chrono::weekday
      weekday() const noexcept
      { return _M_wd; }

      constexpr bool
      ok() const noexcept
      { return _M_wd.ok(); }

      friend constexpr bool
      operator==(const weekday_last& __x, const weekday_last& __y) noexcept
      { return __x.weekday() == __y.weekday(); }

      friend constexpr month_weekday_last
      operator/(int __m, const weekday_last& __wdl) noexcept;

      friend constexpr month_weekday_last
      operator/(const weekday_last& __wdl, int __m) noexcept;

      friend constexpr year_month_weekday_last
      operator/(const year_month& __ym, const weekday_last& __wdl) noexcept;
    };

    constexpr weekday_last
    weekday::operator[](last_spec) const noexcept
    { return weekday_last{*this}; }

    // MONTH_DAY

    class month_day
    {
    private:
      chrono::month _M_m;
      chrono::day _M_d;

    public:
      month_day() = default;

      constexpr
      month_day(const chrono::month& __m, const chrono::day& __d) noexcept
      : _M_m{__m}, _M_d{__d}
      { }

      constexpr chrono::month
      month() const noexcept
      { return _M_m; }

      constexpr chrono::day
      day() const noexcept
      { return _M_d; }

      constexpr bool
      ok() const noexcept
      {
	return _M_m.ok()
	  && 1u <= unsigned(_M_d)
	  && unsigned(_M_d) <= __detail::__days_per_month[unsigned(_M_m) - 1];
      }

      friend constexpr bool
      operator==(const month_day& __x, const month_day& __y) noexcept
      { return __x.month() == __y.month() && __x.day() == __y.day(); }

      friend constexpr strong_ordering
      operator<=>(const month_day& __x, const month_day& __y) noexcept
	= default;

      friend constexpr month_day
      operator/(const chrono::month& __m, const chrono::day& __d) noexcept
      { return {__m, __d}; }

      friend constexpr month_day
      operator/(const chrono::month& __m, int __d) noexcept
      { return {__m, chrono::day(unsigned(__d))}; }

      friend constexpr month_day
      operator/(int __m, const chrono::day& __d) noexcept
      { return {chrono::month(unsigned(__m)), __d}; }

      friend constexpr month_day
      operator/(const chrono::day& __d, const chrono::month& __m) noexcept
      { return {__m, __d}; }

      friend constexpr month_day
      operator/(const chrono::day& __d, int __m) noexcept
      { return {chrono::month(unsigned(__m)), __d}; }

      friend constexpr year_month_day
      operator/(int __y, const month_day& __md) noexcept;

      friend constexpr year_month_day
      operator/(const month_day& __md, int __y) noexcept;
    };

    // MONTH_DAY_LAST

    class month_day_last
    {
    private:
      chrono::month _M_m;

    public:
      explicit constexpr
      month_day_last(const chrono::month& __m) noexcept
      : _M_m{__m}
      { }

      constexpr chrono::month
      month() const noexcept
      { return _M_m; }

      constexpr bool
      ok() const noexcept
      { return _M_m.ok(); }

      friend constexpr bool
      operator==(const month_day_last& __x, const month_day_last& __y) noexcept
      { return __x.month() == __y.month(); }

      friend constexpr strong_ordering
      operator<=>(const month_day_last& __x, const month_day_last& __y) noexcept
	= default;

      friend constexpr month_day_last
      operator/(const chrono::month& __m, last_spec) noexcept
      { return month_day_last{__m}; }

      friend constexpr month_day_last
      operator/(int __m, last_spec) noexcept
      { return chrono::month(unsigned(__m)) / last; }

      friend constexpr month_day_last
      operator/(last_spec, const chrono::month& __m) noexcept
      { return __m / last; }

      friend constexpr month_day_last
      operator/(last_spec, int __m) noexcept
      { return __m / last; }

      friend constexpr year_month_day_last
      operator/(int __y, const month_day_last& __mdl) noexcept;

      friend constexpr year_month_day_last
      operator/(const month_day_last& __mdl, int __y) noexcept;
    };

    // MONTH_WEEKDAY

    class month_weekday
    {
    private:
      chrono::month _M_m;
      chrono::weekday_indexed _M_wdi;

    public:
      constexpr
      month_weekday(const chrono::month& __m,
		    const chrono::weekday_indexed& __wdi) noexcept
      : _M_m{__m}, _M_wdi{__wdi}
      { }

      constexpr chrono::month
      month() const noexcept
      { return _M_m; }

      constexpr chrono::weekday_indexed
      weekday_indexed() const noexcept
      { return _M_wdi; }

      constexpr bool
      ok() const noexcept
      { return _M_m.ok() && _M_wdi.ok(); }

      friend constexpr bool
      operator==(const month_weekday& __x, const month_weekday& __y) noexcept
      {
	return __x.month() == __y.month()
	  && __x.weekday_indexed() == __y.weekday_indexed();
      }

      friend constexpr month_weekday
      operator/(const chrono::month& __m,
		const chrono::weekday_indexed& __wdi) noexcept
      { return {__m, __wdi}; }

      friend constexpr month_weekday
      operator/(int __m, const chrono::weekday_indexed& __wdi) noexcept
      { return chrono::month(unsigned(__m)) / __wdi; }

      friend constexpr month_weekday
      operator/(const chrono::weekday_indexed& __wdi,
		const chrono::month& __m) noexcept
      { return __m / __wdi; }

      friend constexpr month_weekday
      operator/(const chrono::weekday_indexed& __wdi, int __m) noexcept
      { return __m / __wdi; }

      friend constexpr year_month_weekday
      operator/(int __y, const month_weekday& __mwd) noexcept;

      friend constexpr year_month_weekday
      operator/(const month_weekday& __mwd, int __y) noexcept;
    };

    // MONTH_WEEKDAY_LAST

    class month_weekday_last
    {
    private:
      chrono::month _M_m;
      chrono::weekday_last _M_wdl;

    public:
      constexpr
      month_weekday_last(const chrono::month& __m,
			 const chrono::weekday_last& __wdl) noexcept
      :_M_m{__m}, _M_wdl{__wdl}
      { }

      constexpr chrono::month
      month() const noexcept
      { return _M_m; }

      constexpr chrono::weekday_last
      weekday_last() const noexcept
      { return _M_wdl; }

      constexpr bool
      ok() const noexcept
      { return _M_m.ok() && _M_wdl.ok(); }

      friend constexpr bool
      operator==(const month_weekday_last& __x,
		 const month_weekday_last& __y) noexcept
      {
	return __x.month() == __y.month()
	  && __x.weekday_last() == __y.weekday_last();
      }

      friend constexpr month_weekday_last
      operator/(const chrono::month& __m,
		const chrono::weekday_last& __wdl) noexcept
      { return {__m, __wdl}; }

      friend constexpr month_weekday_last
      operator/(int __m, const chrono::weekday_last& __wdl) noexcept
      { return chrono::month(unsigned(__m)) / __wdl; }

      friend constexpr month_weekday_last
      operator/(const chrono::weekday_last& __wdl,
		const chrono::month& __m) noexcept
      { return __m / __wdl; }

      friend constexpr month_weekday_last
      operator/(const chrono::weekday_last& __wdl, int __m) noexcept
      { return chrono::month(unsigned(__m)) / __wdl; }

      friend constexpr year_month_weekday_last
      operator/(int __y, const month_weekday_last& __mwdl) noexcept;

      friend constexpr year_month_weekday_last
      operator/(const month_weekday_last& __mwdl, int __y) noexcept;
    };

    // YEAR_MONTH

    namespace __detail
    {
      // [time.cal.ym], [time.cal.ymd], etc constrain the 'months'-based
      // addition/subtraction operator overloads like so:
      //
      //   Constraints: if the argument supplied by the caller for the months
      //   parameter is convertible to years, its implicit conversion sequence
      //   to years is worse than its implicit conversion sequence to months.
      //
      // We realize this constraint by templatizing the 'months'-based
      // overloads (using a dummy defaulted template parameter), so that
      // overload resolution doesn't select the 'months'-based overload unless
      // the implicit conversion sequence to 'months' is better than that to
      // 'years'.
      using __months_years_conversion_disambiguator = void;
    }

    class year_month
    {
    private:
      chrono::year _M_y;
      chrono::month _M_m;

    public:
      year_month() = default;

      constexpr
      year_month(const chrono::year& __y, const chrono::month& __m) noexcept
      : _M_y{__y}, _M_m{__m}
      { }

      constexpr chrono::year
      year() const noexcept
      { return _M_y; }

      constexpr chrono::month
      month() const noexcept
      { return _M_m; }

      template<typename = __detail::__months_years_conversion_disambiguator>
	constexpr year_month&
	operator+=(const months& __dm) noexcept
	{
	  *this = *this + __dm;
	  return *this;
	}

      template<typename = __detail::__months_years_conversion_disambiguator>
	constexpr year_month&
	operator-=(const months& __dm) noexcept
	{
	  *this = *this - __dm;
	  return *this;
	}

      constexpr year_month&
      operator+=(const years& __dy)  noexcept
      {
	*this = *this + __dy;
	return *this;
      }

      constexpr year_month&
      operator-=(const years& __dy)  noexcept
      {
	*this = *this - __dy;
	return *this;
      }

      constexpr bool
      ok() const noexcept
      { return _M_y.ok() && _M_m.ok(); }

      friend constexpr bool
      operator==(const year_month& __x, const year_month& __y) noexcept
      { return __x.year() == __y.year() && __x.month() == __y.month(); }

      friend constexpr strong_ordering
      operator<=>(const year_month& __x, const year_month& __y) noexcept
	= default;

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month
	operator+(const year_month& __ym, const months& __dm) noexcept
	{
	  // TODO: Optimize?
	  auto __m = __ym.month() + __dm;
	  auto __i = int(unsigned(__ym.month())) - 1 + __dm.count();
	  auto __y = (__i < 0
		      ? __ym.year() + years{(__i - 11) / 12}
		      : __ym.year() + years{__i / 12});
	  return __y / __m;
	}

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month
	operator+(const months& __dm, const year_month& __ym) noexcept
	{ return __ym + __dm; }

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month
	operator-(const year_month& __ym, const months& __dm) noexcept
	{ return __ym + -__dm; }

      friend constexpr months
      operator-(const year_month& __x, const year_month& __y) noexcept
      {
	return (__x.year() - __y.year()
		+ months{static_cast<int>(unsigned{__x.month()})
			 - static_cast<int>(unsigned{__y.month()})});
      }

      friend constexpr year_month
      operator+(const year_month& __ym, const years& __dy) noexcept
      { return (__ym.year() + __dy) / __ym.month(); }

      friend constexpr year_month
      operator+(const years& __dy, const year_month& __ym) noexcept
      { return __ym + __dy; }

      friend constexpr year_month
      operator-(const year_month& __ym, const years& __dy) noexcept
      { return __ym + -__dy; }

      friend constexpr year_month
      operator/(const chrono::year& __y, const chrono::month& __m) noexcept
      { return {__y, __m}; }

      friend constexpr year_month
      operator/(const chrono::year& __y, int __m) noexcept
      { return {__y, chrono::month(unsigned(__m))}; }

      friend constexpr year_month_day
      operator/(const year_month& __ym, int __d) noexcept;

      friend constexpr year_month_day_last
      operator/(const year_month& __ym, last_spec) noexcept;
    };

    // YEAR_MONTH_DAY

    class year_month_day
    {
    private:
      chrono::year _M_y;
      chrono::month _M_m;
      chrono::day _M_d;

      static constexpr year_month_day _S_from_days(const days& __dp) noexcept;

      constexpr days _M_days_since_epoch() const noexcept;

    public:
      year_month_day() = default;

      constexpr
      year_month_day(const chrono::year& __y, const chrono::month& __m,
		     const chrono::day& __d) noexcept
      : _M_y{__y}, _M_m{__m}, _M_d{__d}
      { }

      constexpr
      year_month_day(const year_month_day_last& __ymdl) noexcept;

      constexpr
      year_month_day(const sys_days& __dp) noexcept
      : year_month_day(_S_from_days(__dp.time_since_epoch()))
      { }

      explicit constexpr
      year_month_day(const local_days& __dp) noexcept
      : year_month_day(sys_days{__dp.time_since_epoch()})
      { }

      template<typename = __detail::__months_years_conversion_disambiguator>
	constexpr year_month_day&
	operator+=(const months& __m) noexcept
	{
	  *this = *this + __m;
	  return *this;
	}

      template<typename = __detail::__months_years_conversion_disambiguator>
	constexpr year_month_day&
	operator-=(const months& __m) noexcept
	{
	  *this = *this - __m;
	  return *this;
	}

      constexpr year_month_day&
      operator+=(const years& __y) noexcept
      {
	*this = *this + __y;
	return *this;
      }

      constexpr year_month_day&
      operator-=(const years& __y) noexcept
      {
	*this = *this - __y;
	return *this;
      }

      constexpr chrono::year
      year() const noexcept
      { return _M_y; }

      constexpr chrono::month
      month() const noexcept
      { return _M_m; }

      constexpr chrono::day
      day() const noexcept
      { return _M_d; }

      constexpr
      operator sys_days() const noexcept
      { return sys_days{_M_days_since_epoch()}; }

      explicit constexpr
      operator local_days() const noexcept
      { return local_days{sys_days{*this}.time_since_epoch()}; }

      constexpr bool ok() const noexcept;

      friend constexpr bool
      operator==(const year_month_day& __x, const year_month_day& __y) noexcept
      {
	return __x.year() == __y.year()
	  && __x.month() == __y.month()
	  && __x.day() == __y.day();
      }

      friend constexpr strong_ordering
      operator<=>(const year_month_day& __x, const year_month_day& __y) noexcept
	= default;

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month_day
	operator+(const year_month_day& __ymd, const months& __dm) noexcept
	{ return (__ymd.year() / __ymd.month() + __dm) / __ymd.day(); }

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month_day
	operator+(const months& __dm, const year_month_day& __ymd) noexcept
	{ return __ymd + __dm; }

      friend constexpr year_month_day
      operator+(const year_month_day& __ymd, const years& __dy) noexcept
      { return (__ymd.year() + __dy) / __ymd.month() / __ymd.day(); }

      friend constexpr year_month_day
      operator+(const years& __dy, const year_month_day& __ymd) noexcept
      { return __ymd + __dy; }

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month_day
	operator-(const year_month_day& __ymd, const months& __dm) noexcept
	{ return __ymd + -__dm; }

      friend constexpr year_month_day
      operator-(const year_month_day& __ymd, const years& __dy) noexcept
      { return __ymd + -__dy; }

      friend constexpr year_month_day
      operator/(const year_month& __ym, const chrono::day& __d) noexcept
      { return {__ym.year(), __ym.month(), __d}; }

      friend constexpr year_month_day
      operator/(const year_month& __ym, int __d) noexcept
      { return __ym / chrono::day{unsigned(__d)}; }

      friend constexpr year_month_day
      operator/(const chrono::year& __y, const month_day& __md) noexcept
      { return __y / __md.month() / __md.day(); }

      friend constexpr year_month_day
      operator/(int __y, const month_day& __md) noexcept
      { return chrono::year{__y} / __md; }

      friend constexpr year_month_day
      operator/(const month_day& __md, const chrono::year& __y) noexcept
      { return __y / __md; }

      friend constexpr year_month_day
      operator/(const month_day& __md, int __y) noexcept
      { return chrono::year(__y) / __md; }
    };

    // Construct from days since 1970/01/01.
    // Proposition 6.3 of Neri and Schneider,
    // "Euclidean Affine Functions and Applications to Calendar Algorithms".
    // https://arxiv.org/abs/2102.06959
    constexpr year_month_day
    year_month_day::_S_from_days(const days& __dp) noexcept
    {
      constexpr auto __z2    = static_cast<uint32_t>(-1468000);
      constexpr auto __r2_e3 = static_cast<uint32_t>(536895458);

      const auto __r0 = static_cast<uint32_t>(__dp.count()) + __r2_e3;

      const auto __n1 = 4 * __r0 + 3;
      const auto __q1 = __n1 / 146097;
      const auto __r1 = __n1 % 146097 / 4;

      constexpr auto __p32 = static_cast<uint64_t>(1) << 32;
      const auto __n2 = 4 * __r1 + 3;
      const auto __u2 = static_cast<uint64_t>(2939745) * __n2;
      const auto __q2 = static_cast<uint32_t>(__u2 / __p32);
      const auto __r2 = static_cast<uint32_t>(__u2 % __p32) / 2939745 / 4;

      constexpr auto __p16 = static_cast<uint32_t>(1) << 16;
      const auto __n3 = 2141 * __r2 + 197913;
      const auto __q3 = __n3 / __p16;
      const auto __r3 = __n3 % __p16 / 2141;

      const auto __y0 = 100 * __q1 + __q2;
      const auto __m0 = __q3;
      const auto __d0 = __r3;

      const auto __j  = __r2 >= 306;
      const auto __y1 = __y0 + __j;
      const auto __m1 = __j ? __m0 - 12 : __m0;
      const auto __d1 = __d0 + 1;

      return year_month_day{chrono::year{static_cast<int>(__y1 + __z2)},
			    chrono::month{__m1}, chrono::day{__d1}};
    }

    // Days since 1970/01/01.
    // Proposition 6.2 of Neri and Schneider,
    // "Euclidean Affine Functions and Applications to Calendar Algorithms".
    // https://arxiv.org/abs/2102.06959
    constexpr days
    year_month_day::_M_days_since_epoch() const noexcept
    {
      auto constexpr __z2    = static_cast<uint32_t>(-1468000);
      auto constexpr __r2_e3 = static_cast<uint32_t>(536895458);

      const auto __y1 = static_cast<uint32_t>(static_cast<int>(_M_y)) - __z2;
      const auto __m1 = static_cast<uint32_t>(static_cast<unsigned>(_M_m));
      const auto __d1 = static_cast<uint32_t>(static_cast<unsigned>(_M_d));

      const auto __j  = static_cast<uint32_t>(__m1 < 3);
      const auto __y0 = __y1 - __j;
      const auto __m0 = __j ? __m1 + 12 : __m1;
      const auto __d0 = __d1 - 1;

      const auto __q1 = __y0 / 100;
      const auto __yc = 1461 * __y0 / 4 - __q1 + __q1 / 4;
      const auto __mc = (979 *__m0 - 2919) / 32;
      const auto __dc = __d0;

      return days{static_cast<int32_t>(__yc + __mc + __dc - __r2_e3)};
    }

    // YEAR_MONTH_DAY_LAST

    class year_month_day_last
    {
    private:
      chrono::year _M_y;
      chrono::month_day_last _M_mdl;

    public:
      constexpr
      year_month_day_last(const chrono::year& __y,
			  const chrono::month_day_last& __mdl) noexcept
      : _M_y{__y}, _M_mdl{__mdl}
      { }

      template<typename = __detail::__months_years_conversion_disambiguator>
	constexpr year_month_day_last&
	operator+=(const months& __m) noexcept
	{
	  *this = *this + __m;
	  return *this;
	}

      template<typename = __detail::__months_years_conversion_disambiguator>
	constexpr year_month_day_last&
	operator-=(const months& __m) noexcept
	{
	  *this = *this - __m;
	  return *this;
	}

      constexpr year_month_day_last&
      operator+=(const years& __y)  noexcept
      {
	*this = *this + __y;
	return *this;
      }

      constexpr year_month_day_last&
      operator-=(const years& __y)  noexcept
      {
	*this = *this - __y;
	return *this;
      }

      constexpr chrono::year
      year() const noexcept
      { return _M_y; }

      constexpr chrono::month
      month() const noexcept
      { return _M_mdl.month(); }

      constexpr chrono::month_day_last
      month_day_last() const noexcept
      { return _M_mdl; }

      // Return A day representing the last day of this year, month pair.
      constexpr chrono::day
      day() const noexcept
      {
	const auto __m = static_cast<unsigned>(month());

	// The result is unspecified if __m < 1 or __m > 12.  Hence, assume
	// 1 <= __m <= 12.  For __m != 2, day() == 30 or day() == 31 or, in
	// other words, day () == 30 | b, where b is in {0, 1}.

	// If __m in {1, 3, 4, 5, 6, 7}, then b is 1 if, and only if, __m is
	// odd.  Hence, b = __m & 1 = (__m ^ 0) & 1.

	// If __m in {8, 9, 10, 11, 12}, then b is 1 if, and only if, __m is
	// even.  Hence, b = (__m ^ 1) & 1.

	// Therefore, b = (__m ^ c) & 1, where c = 0, if __m < 8, or c = 1 if
	// __m >= 8, that is, c = __m >> 3.

	// Since 30 = (11110)_2 and __m <= 31 = (11111)_2, the "& 1" in b's
	// calculation is unnecessary.

	// The performance of this implementation does not depend on look-up
	// tables being on the L1 cache.
	return chrono::day{__m != 2 ? (__m ^ (__m >> 3)) | 30
	  : _M_y.is_leap() ? 29 : 28};
      }

      constexpr
      operator sys_days() const noexcept
      { return sys_days{year() / month() / day()}; }

      explicit constexpr
      operator local_days() const noexcept
      { return local_days{sys_days{*this}.time_since_epoch()}; }

      constexpr bool
      ok() const noexcept
      { return _M_y.ok() && _M_mdl.ok(); }

      friend constexpr bool
      operator==(const year_month_day_last& __x,
		 const year_month_day_last& __y) noexcept
      {
	return __x.year() == __y.year()
	  && __x.month_day_last() == __y.month_day_last();
      }

      friend constexpr strong_ordering
      operator<=>(const year_month_day_last& __x,
		  const year_month_day_last& __y) noexcept
	= default;

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month_day_last
	operator+(const year_month_day_last& __ymdl,
		  const months& __dm) noexcept
	{ return (__ymdl.year() / __ymdl.month() + __dm) / last; }

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month_day_last
	operator+(const months& __dm,
		  const year_month_day_last& __ymdl) noexcept
	{ return __ymdl + __dm; }

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month_day_last
	operator-(const year_month_day_last& __ymdl,
		  const months& __dm) noexcept
	{ return __ymdl + -__dm; }

      friend constexpr year_month_day_last
      operator+(const year_month_day_last& __ymdl,
		const years& __dy) noexcept
      { return {__ymdl.year() + __dy, __ymdl.month_day_last()}; }

      friend constexpr year_month_day_last
      operator+(const years& __dy,
		const year_month_day_last& __ymdl) noexcept
      { return __ymdl + __dy; }

      friend constexpr year_month_day_last
      operator-(const year_month_day_last& __ymdl,
		const years& __dy) noexcept
      { return __ymdl + -__dy; }

      friend constexpr year_month_day_last
      operator/(const year_month& __ym, last_spec) noexcept
      { return {__ym.year(), chrono::month_day_last{__ym.month()}}; }

      friend constexpr year_month_day_last
      operator/(const chrono::year& __y,
		const chrono::month_day_last& __mdl) noexcept
      { return {__y, __mdl}; }

      friend constexpr year_month_day_last
      operator/(int __y, const chrono::month_day_last& __mdl) noexcept
      { return chrono::year(__y) / __mdl; }

      friend constexpr year_month_day_last
      operator/(const chrono::month_day_last& __mdl,
		const chrono::year& __y) noexcept
      { return __y / __mdl; }

      friend constexpr year_month_day_last
      operator/(const chrono::month_day_last& __mdl, int __y) noexcept
      { return chrono::year(__y) / __mdl; }
    };

    // year_month_day ctor from year_month_day_last
    constexpr
    year_month_day::year_month_day(const year_month_day_last& __ymdl) noexcept
    : _M_y{__ymdl.year()}, _M_m{__ymdl.month()}, _M_d{__ymdl.day()}
    { }

    constexpr bool
    year_month_day::ok() const noexcept
    {
      if (!_M_y.ok() || !_M_m.ok())
	return false;
      return chrono::day{1} <= _M_d && _M_d <= (_M_y / _M_m / last).day();
    }

    // YEAR_MONTH_WEEKDAY

    class year_month_weekday
    {
    private:
      chrono::year _M_y;
      chrono::month _M_m;
      chrono::weekday_indexed _M_wdi;

      static constexpr year_month_weekday
      _S_from_sys_days(const sys_days& __dp)
      {
	year_month_day __ymd{__dp};
	chrono::weekday __wd{__dp};
	auto __index = __wd[(unsigned{__ymd.day()} - 1) / 7 + 1];
	return {__ymd.year(), __ymd.month(), __index};
      }

    public:
      year_month_weekday() = default;

      constexpr
      year_month_weekday(const chrono::year& __y, const chrono::month& __m,
			 const chrono::weekday_indexed& __wdi) noexcept
      : _M_y{__y}, _M_m{__m}, _M_wdi{__wdi}
      { }

      constexpr
      year_month_weekday(const sys_days& __dp) noexcept
      : year_month_weekday{_S_from_sys_days(__dp)}
      { }

      explicit constexpr
      year_month_weekday(const local_days& __dp) noexcept
      : year_month_weekday{sys_days{__dp.time_since_epoch()}}
      { }

      template<typename = __detail::__months_years_conversion_disambiguator>
	constexpr year_month_weekday&
	operator+=(const months& __m) noexcept
	{
	  *this = *this + __m;
	  return *this;
	}

      template<typename = __detail::__months_years_conversion_disambiguator>
	constexpr year_month_weekday&
	operator-=(const months& __m) noexcept
	{
	  *this = *this - __m;
	  return *this;
	}

      constexpr year_month_weekday&
      operator+=(const years& __y) noexcept
      {
	*this = *this + __y;
	return *this;
      }

      constexpr year_month_weekday&
      operator-=(const years& __y) noexcept
      {
	*this = *this - __y;
	return *this;
      }

      constexpr chrono::year
      year() const noexcept
      { return _M_y; }

      constexpr chrono::month
      month() const noexcept
      { return _M_m; }

      constexpr chrono::weekday
      weekday() const noexcept
      { return _M_wdi.weekday(); }

      constexpr unsigned
      index() const noexcept
      { return _M_wdi.index(); }

      constexpr chrono::weekday_indexed
      weekday_indexed() const noexcept
      { return _M_wdi; }

      constexpr
      operator sys_days() const noexcept
      {
	auto __d = sys_days{year() / month() / 1};
	return __d + (weekday() - chrono::weekday(__d)
		      + days{(static_cast<int>(index())-1)*7});
      }

      explicit constexpr
      operator local_days() const noexcept
      { return local_days{sys_days{*this}.time_since_epoch()}; }

      constexpr bool
      ok() const noexcept
      {
	if (!_M_y.ok() || !_M_m.ok() || !_M_wdi.ok())
	  return false;
	if (_M_wdi.index() <= 4)
	  return true;
	days __d = (_M_wdi.weekday()
		    - chrono::weekday{sys_days{_M_y / _M_m / 1}}
		    + days((_M_wdi.index()-1)*7 + 1));
	__glibcxx_assert(__d.count() >= 1);
	return (unsigned)__d.count() <= (unsigned)(_M_y / _M_m / last).day();
      }

      friend constexpr bool
      operator==(const year_month_weekday& __x,
		 const year_month_weekday& __y) noexcept
      {
	return __x.year() == __y.year()
	  && __x.month() == __y.month()
	  && __x.weekday_indexed() == __y.weekday_indexed();
      }

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month_weekday
	operator+(const year_month_weekday& __ymwd, const months& __dm) noexcept
	{
	  return ((__ymwd.year() / __ymwd.month() + __dm)
		  / __ymwd.weekday_indexed());
	}

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month_weekday
	operator+(const months& __dm, const year_month_weekday& __ymwd) noexcept
	{ return __ymwd + __dm; }

      friend constexpr year_month_weekday
      operator+(const year_month_weekday& __ymwd, const years& __dy) noexcept
      { return {__ymwd.year() + __dy, __ymwd.month(), __ymwd.weekday_indexed()}; }

      friend constexpr year_month_weekday
      operator+(const years& __dy, const year_month_weekday& __ymwd) noexcept
      { return __ymwd + __dy; }

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month_weekday
	operator-(const year_month_weekday& __ymwd, const months& __dm) noexcept
	{ return __ymwd + -__dm; }

      friend constexpr year_month_weekday
      operator-(const year_month_weekday& __ymwd, const years& __dy) noexcept
      { return __ymwd + -__dy; }

      friend constexpr year_month_weekday
      operator/(const year_month& __ym,
		const chrono::weekday_indexed& __wdi) noexcept
      { return {__ym.year(), __ym.month(), __wdi}; }

      friend constexpr year_month_weekday
      operator/(const chrono::year& __y, const month_weekday& __mwd) noexcept
      { return {__y, __mwd.month(), __mwd.weekday_indexed()}; }

      friend constexpr year_month_weekday
      operator/(int __y, const month_weekday& __mwd) noexcept
      { return chrono::year(__y) / __mwd; }

      friend constexpr year_month_weekday
      operator/(const month_weekday& __mwd, const chrono::year& __y) noexcept
      { return __y / __mwd; }

      friend constexpr year_month_weekday
      operator/(const month_weekday& __mwd, int __y) noexcept
      { return chrono::year(__y) / __mwd; }
    };

    // YEAR_MONTH_WEEKDAY_LAST

    class year_month_weekday_last
    {
    private:
      chrono::year _M_y;
      chrono::month _M_m;
      chrono::weekday_last _M_wdl;

    public:
      constexpr
      year_month_weekday_last(const chrono::year& __y, const chrono::month& __m,
			      const chrono::weekday_last& __wdl) noexcept
      : _M_y{__y}, _M_m{__m}, _M_wdl{__wdl}
      { }

      template<typename = __detail::__months_years_conversion_disambiguator>
	constexpr year_month_weekday_last&
	operator+=(const months& __m) noexcept
	{
	  *this = *this + __m;
	  return *this;
	}

      template<typename = __detail::__months_years_conversion_disambiguator>
	constexpr year_month_weekday_last&
	operator-=(const months& __m) noexcept
	{
	  *this = *this - __m;
	  return *this;
	}

      constexpr year_month_weekday_last&
      operator+=(const years& __y)  noexcept
      {
	*this = *this + __y;
	return *this;
      }

      constexpr year_month_weekday_last&
      operator-=(const years& __y)  noexcept
      {
	*this = *this - __y;
	return *this;
      }

      constexpr chrono::year
      year() const noexcept
      { return _M_y; }

      constexpr chrono::month
      month() const noexcept
      { return _M_m; }

      constexpr chrono::weekday
      weekday() const noexcept
      { return _M_wdl.weekday(); }

      constexpr chrono::weekday_last
      weekday_last() const noexcept
      { return _M_wdl; }

      constexpr
      operator sys_days() const noexcept
      {
	const auto __d = sys_days{_M_y / _M_m / last};
	return sys_days{(__d - (chrono::weekday{__d}
				- _M_wdl.weekday())).time_since_epoch()};
      }

      explicit constexpr
      operator local_days() const noexcept
      { return local_days{sys_days{*this}.time_since_epoch()}; }

      constexpr bool
      ok() const noexcept
      { return _M_y.ok() && _M_m.ok() && _M_wdl.ok(); }

      friend constexpr bool
      operator==(const year_month_weekday_last& __x,
		 const year_month_weekday_last& __y) noexcept
      {
	return __x.year() == __y.year()
	  && __x.month() == __y.month()
	  && __x.weekday_last() == __y.weekday_last();
      }

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month_weekday_last
	operator+(const year_month_weekday_last& __ymwdl,
		  const months& __dm) noexcept
	{
	  return ((__ymwdl.year() / __ymwdl.month() + __dm)
		  / __ymwdl.weekday_last());
	}

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month_weekday_last
	operator+(const months& __dm,
		  const year_month_weekday_last& __ymwdl) noexcept
	{ return __ymwdl + __dm; }

      friend constexpr year_month_weekday_last
      operator+(const year_month_weekday_last& __ymwdl,
		const years& __dy) noexcept
      { return {__ymwdl.year() + __dy, __ymwdl.month(), __ymwdl.weekday_last()}; }

      friend constexpr year_month_weekday_last
      operator+(const years& __dy,
		const year_month_weekday_last& __ymwdl) noexcept
      { return __ymwdl + __dy; }

      template<typename = __detail::__months_years_conversion_disambiguator>
	friend constexpr year_month_weekday_last
	operator-(const year_month_weekday_last& __ymwdl,
		  const months& __dm) noexcept
	{ return __ymwdl + -__dm; }

      friend constexpr year_month_weekday_last
      operator-(const year_month_weekday_last& __ymwdl,
		const years& __dy) noexcept
      { return __ymwdl + -__dy; }

      friend constexpr year_month_weekday_last
      operator/(const year_month& __ym,
		const chrono::weekday_last& __wdl) noexcept
      { return {__ym.year(), __ym.month(), __wdl}; }

      friend constexpr year_month_weekday_last
      operator/(const chrono::year& __y,
		const chrono::month_weekday_last& __mwdl) noexcept
      { return {__y, __mwdl.month(), __mwdl.weekday_last()}; }

      friend constexpr year_month_weekday_last
      operator/(int __y, const chrono::month_weekday_last& __mwdl) noexcept
      { return chrono::year(__y) / __mwdl; }

      friend constexpr year_month_weekday_last
      operator/(const chrono::month_weekday_last& __mwdl,
		const chrono::year& __y) noexcept
      { return __y / __mwdl; }

      friend constexpr year_month_weekday_last
      operator/(const chrono::month_weekday_last& __mwdl, int __y) noexcept
      { return chrono::year(__y) / __mwdl; }
    };

    // HH_MM_SS

    /// @cond undocumented
    namespace __detail
    {
      consteval long long
      __pow10(unsigned __n)
      {
	long long __r = 1;
	while (__n-- > 0)
	  __r *= 10;
	return __r;
      }
    }
    /// @endcond

    /** Utility for splitting a duration into hours, minutes, and seconds
     *
     * This is a convenience type that provides accessors for the constituent
     * parts (hours, minutes, seconds and subseconds) of a duration.
     *
     * @since C++20
     */
    template<typename _Duration>
      class hh_mm_ss
      {
	static_assert( __is_duration<_Duration>::value );

      private:
	static consteval int
	_S_fractional_width()
	{
	  auto __den = _Duration::period::den;
	  const int __multiplicity_2 = std::__countr_zero((uintmax_t)__den);
	  __den >>= __multiplicity_2;
	  int __multiplicity_5 = 0;
	  while ((__den % 5) == 0)
	    {
	      ++__multiplicity_5;
	      __den /= 5;
	    }
	  if (__den != 1)
	    return 6;

	  int __width = (__multiplicity_2 > __multiplicity_5
			 ? __multiplicity_2 : __multiplicity_5);
	  if (__width > 18)
	    __width = 18;
	  return __width;
	}

	constexpr
	hh_mm_ss(_Duration __d, bool __is_neg)
	: _M_h (duration_cast<chrono::hours>(__d)),
	  _M_m (duration_cast<chrono::minutes>(__d - hours())),
	  _M_s (duration_cast<chrono::seconds>(__d - hours() - minutes())),
	  _M_is_neg(__is_neg)
	{
	  auto __ss = __d - hours() - minutes() - seconds();
	  if constexpr (treat_as_floating_point_v<typename precision::rep>)
	    _M_ss._M_r = __ss.count();
	  else if constexpr (precision::period::den != 1)
	    _M_ss._M_r = duration_cast<precision>(__ss).count();
	}

	static constexpr _Duration
	_S_abs(_Duration __d)
	{
	  if constexpr (numeric_limits<typename _Duration::rep>::is_signed)
	    return chrono::abs(__d);
	  else
	    return __d;
	}

      public:
	static constexpr unsigned fractional_width = {_S_fractional_width()};

	using precision
	  = duration<common_type_t<typename _Duration::rep,
				   chrono::seconds::rep>,
		     ratio<1, __detail::__pow10(fractional_width)>>;

	constexpr hh_mm_ss() noexcept = default;

	constexpr explicit
	hh_mm_ss(_Duration __d)
	: hh_mm_ss(_S_abs(__d), __d < _Duration::zero())
	{ }

	constexpr bool
	is_negative() const noexcept
	{
	  if constexpr (!_S_is_unsigned)
	    return _M_is_neg;
	  else
	    return false;
	}

	constexpr chrono::hours
	hours() const noexcept
	{ return _M_h; }

	constexpr chrono::minutes
	minutes() const noexcept
	{ return _M_m; }

	constexpr chrono::seconds
	seconds() const noexcept
	{ return _M_s; }

	constexpr precision
	subseconds() const noexcept
	{ return static_cast<precision>(_M_ss); }

	constexpr explicit
	operator precision() const noexcept
	{ return to_duration(); }

	constexpr precision
	to_duration() const noexcept
	{
	  if constexpr (!_S_is_unsigned)
	    if (_M_is_neg)
	      return -(_M_h + _M_m + _M_s + subseconds());
	  return _M_h + _M_m + _M_s + subseconds();
	}

      private:
	static constexpr bool _S_is_unsigned
	  = __and_v<is_integral<typename _Duration::rep>,
		    is_unsigned<typename _Duration::rep>>;

	template<typename _Ratio>
	  using __byte_duration = duration<unsigned char, _Ratio>;

	// The type of the _M_ss member that holds the subsecond precision.
	template<typename _Dur>
	  struct __subseconds
	  {
	    typename _Dur::rep _M_r{};

	    constexpr explicit
	    operator _Dur() const noexcept
	    { return _Dur(_M_r); }
	  };

	// An empty class if this precision doesn't need subseconds.
	template<typename _Rep>
	  requires (!treat_as_floating_point_v<_Rep>)
	  struct __subseconds<duration<_Rep, ratio<1>>>
	  {
	    constexpr explicit
	    operator duration<_Rep, ratio<1>>() const noexcept
	    { return {}; }
	  };

	template<typename _Rep, typename _Period>
	  requires (!treat_as_floating_point_v<_Rep>)
	    && ratio_less_v<_Period, ratio<1, 1>>
	    && ratio_greater_equal_v<_Period, ratio<1, 250>>
	  struct __subseconds<duration<_Rep, _Period>>
	  {
	    unsigned char _M_r{};

	    constexpr explicit
	    operator duration<_Rep, _Period>() const noexcept
	    { return duration<_Rep, _Period>(_M_r); }
	  };

	template<typename _Rep, typename _Period>
	  requires (!treat_as_floating_point_v<_Rep>)
	    && ratio_less_v<_Period, ratio<1, 250>>
	    && ratio_greater_equal_v<_Period, ratio<1, 4000000000>>
	  struct __subseconds<duration<_Rep, _Period>>
	  {
	    uint_least32_t _M_r{};

	    constexpr explicit
	    operator duration<_Rep, _Period>() const noexcept
	    { return duration<_Rep, _Period>(_M_r); }
	  };

	chrono::hours		    _M_h{};
	__byte_duration<ratio<60>>  _M_m{};
	__byte_duration<ratio<1>>   _M_s{};
	bool			    _M_is_neg{};
	__subseconds<precision>	    _M_ss{};
      };

    // 12/24 HOURS FUNCTIONS

    constexpr bool
    is_am(const hours& __h) noexcept
    { return 0h <= __h && __h <= 11h; }

    constexpr bool
    is_pm(const hours& __h) noexcept
    { return 12h <= __h && __h <= 23h; }

    constexpr hours
    make12(const hours& __h) noexcept
    {
      if (__h == 0h)
	return 12h;
      else if (__h > 12h)
	return __h - 12h;
      return __h;
    }

    constexpr hours
    make24(const hours& __h, bool __is_pm) noexcept
    {
      if (!__is_pm)
	{
	  if (__h == 12h)
	    return 0h;
	  else
	    return __h;
	}
      else
	{
	  if (__h == 12h)
	    return __h;
	  else
	    return __h + 12h;
	}
    }

#if _GLIBCXX_HOSTED
#if _GLIBCXX_USE_CXX11_ABI || ! _GLIBCXX_USE_DUAL_ABI
    // C++20 [time.zones] Time zones

    struct tzdb;

    struct sys_info
    {
      sys_seconds begin;
      sys_seconds end;
      seconds offset;
      minutes save;
      string abbrev;
    };

    struct local_info
    {
      static constexpr int unique      = 0;
      static constexpr int nonexistent = 1;
      static constexpr int ambiguous   = 2;

      int result;
      sys_info first;
      sys_info second;
    };

    class nonexistent_local_time : public runtime_error
    {
    public:
      template<typename _Duration>
	nonexistent_local_time(const local_time<_Duration>& __tp,
			       const local_info& __i)
	: runtime_error(_S_make_what_str(__tp, __i))
	{ __glibcxx_assert(__i.result == local_info::nonexistent); }

    private:
      template<typename _Duration>
	static string
	_S_make_what_str(const local_time<_Duration>& __tp,
			 const local_info& __i)
	{
	  std::ostringstream __os;
	  __os << __tp << " is in a gap between\n"
	       << local_seconds(__i.first.end.time_since_epoch())
	       + __i.first.offset << ' ' << __i.first.abbrev << " and\n"
	       << local_seconds(__i.second.begin.time_since_epoch())
	       + __i.second.offset << ' ' << __i.second.abbrev
	       << " which are both equivalent to\n"
	       << __i.first.end << " UTC";
	  return std::move(__os).str();
	}
    };

    class ambiguous_local_time : public runtime_error
    {
    public:
      template<typename _Duration>
	ambiguous_local_time(const local_time<_Duration>& __tp,
			     const local_info& __i)
	: runtime_error(_S_make_what_str(__tp, __i))
	{ __glibcxx_assert(__i.result == local_info::ambiguous); }

    private:
      template<typename _Duration>
	static string
	_S_make_what_str(const local_time<_Duration>& __tp,
			 const local_info& __i)
	{
	  std::ostringstream __os;
	  __os << __tp << " is ambiguous.  It could be\n"
	       << __tp << ' ' << __i.first.abbrev << " == "
	       << __tp - __i.first.offset << " UTC or\n"
	       << __tp << ' ' << __i.second.abbrev << " == "
	       << __tp - __i.second.offset << " UTC";
	  return std::move(__os).str();
	}
    };

    template<typename _Duration>
      [[noreturn]] void
      __throw_bad_local_time(const local_time<_Duration>& __tp,
			     const local_info& __i)
      {
#if __cpp_exceptions
	if (__i.result == local_info::nonexistent)
	  throw nonexistent_local_time(__tp, __i);
	throw ambiguous_local_time(__tp, __i);
#else
	__builtin_abort();
#endif
      }

    enum class choose { earliest, latest };

    class time_zone
    {
    public:
      time_zone(time_zone&&) = default;
      time_zone& operator=(time_zone&&) = default;

      ~time_zone();

      [[nodiscard]]
      string_view name() const noexcept { return _M_name; }

      template<typename _Duration>
	sys_info
	get_info(const sys_time<_Duration>& __st) const
	{ return _M_get_sys_info(chrono::floor<seconds>(__st)); }

      template<typename _Duration>
	local_info
	get_info(const local_time<_Duration>& __tp) const
	{ return _M_get_local_info(chrono::floor<seconds>(__tp)); }

      template<typename _Duration>
	sys_time<common_type_t<_Duration, seconds>>
	to_sys(const local_time<_Duration>& __tp) const
	{
	  local_info __info = get_info(__tp);

	  if (__info.result != local_info::unique)
	    __throw_bad_local_time(__tp, __info);

	  return sys_time<_Duration>(__tp.time_since_epoch())
		   - __info.first.offset;
	}

      template<typename _Duration>
	sys_time<common_type_t<_Duration, seconds>>
	to_sys(const local_time<_Duration>& __tp, choose __z) const
	{
	  local_info __info = get_info(__tp);

	  if (__info.result == local_info::nonexistent)
	    return __info.first.end; // Last second of the previous sys_info.

	  sys_time<_Duration> __st(__tp.time_since_epoch());

	  if (__info.result == local_info::ambiguous && __z == choose::latest)
	    return __st - __info.second.offset; // Time in the later sys_info.
	  // else if __z == earliest, use __info.first.offset as below:

	  return __st - __info.first.offset;
	}

      template<typename _Duration>
	local_time<common_type_t<_Duration, seconds>>
	to_local(const sys_time<_Duration>& __tp) const
	{
	  auto __d = (__tp + get_info(__tp).offset).time_since_epoch();
	  return local_time<common_type_t<_Duration, seconds>>(__d);
	}

      [[nodiscard]] friend bool
      operator==(const time_zone& __x, const time_zone& __y) noexcept
      { return __x._M_name == __y._M_name; }

      [[nodiscard]] friend strong_ordering
      operator<=>(const time_zone& __x, const time_zone& __y) noexcept
      { return __x._M_name <=> __y._M_name; }

    private:
      sys_info _M_get_sys_info(sys_seconds) const;
      local_info _M_get_local_info(local_seconds) const;

      friend const tzdb& reload_tzdb();
      friend struct tzdb;
      friend class tzdb_list;

      struct _Impl;

      explicit time_zone(unique_ptr<_Impl> __p);
      string _M_name;
      unique_ptr<_Impl> _M_impl;
    };

    const time_zone* locate_zone(string_view __tz_name);
    const time_zone* current_zone();

    /** The list of `chrono::tzdb` objects
     *
     * A single object of this type is constructed by the C++ runtime,
     * and can be accessed by calling `chrono::get_tzdb_list()`.
     *
     * The front of the list is the current `tzdb` object and can be accessed
     * via `chrono::get_tzdb_list().front()` or `chrono::get_tzdb()` or
     * `*chrono::get_tzdb_list().begin()`.
     *
     * The `chrono::reload_tzdb()` function will check for a newer version
     * and if found, insert it at the front of the list.
     *
     * @since C++20
     */
    class tzdb_list
    {
      struct _Node;

    public:
      tzdb_list(const tzdb_list&) = delete;
      tzdb_list& operator=(const tzdb_list&) = delete;

      /** An iterator into the `tzdb_list`
       *
       * As a extension, in libstdc++ each `tzdb` is reference-counted
       * and the `const_iterator` type shares ownership of the object it
       * refers to. This ensures that a `tzdb` erased from the list will
       * not be destroyed while there is an iterator that refers to it.
       */
      class const_iterator
      {
      public:
	using value_type        = tzdb;
	using reference         = const tzdb&;
	using pointer           = const tzdb*;
	using difference_type   = ptrdiff_t;
	using iterator_category = forward_iterator_tag;

	constexpr const_iterator() = default;
	const_iterator(const const_iterator&) = default;
	const_iterator(const_iterator&&) = default;
	const_iterator& operator=(const const_iterator&) = default;
	const_iterator& operator=(const_iterator&&) = default;

	reference operator*() const noexcept;
	pointer operator->() const noexcept { return &**this; }
	const_iterator& operator++();
	const_iterator operator++(int);

	bool operator==(const const_iterator&) const noexcept = default;

      private:
	explicit const_iterator(const shared_ptr<_Node>&) noexcept;

	friend class tzdb_list;

	shared_ptr<_Node> _M_node;
	void* _M_reserved = nullptr;
      };

      /** Access the current `tzdb` at the front of the list.
       *
       * This returns a reference to the same object as `chrono::get_tzdb()`.
       *
       * @returns A reference to the current tzdb object.
       * @since C++20
       */
      const tzdb& front() const noexcept;

      /** Remove the tzdb object _after_ the one the iterator refers to.
       *
       * Calling this function concurrently with any of `front()`, `begin()`,
       * or `end()` does not cause a data race, but in general this function
       * is not thread-safe. The behaviour may be undefined if erasing an
       * element from the list while another thread is calling the same
       * function, or incrementing an iterator into the list, or accessing
       * the element being erased (unless it is accessed through an iterator).
       *
       * @param __p A dereferenceable iterator.
       * @returns An iterator the element after the one that was erased
       *          (or `end()` if there is no such element).
       * @since C++20
       */
      const_iterator erase_after(const_iterator __p);

      const_iterator begin() const noexcept;
      const_iterator end() const noexcept { return {}; }
      const_iterator cbegin() const noexcept { return begin(); }
      const_iterator cend() const noexcept { return end(); }

    private:
      constexpr explicit tzdb_list(nullptr_t);

      friend tzdb_list& get_tzdb_list();
      friend const tzdb& get_tzdb();
      friend const tzdb& reload_tzdb();
      friend struct tzdb;
      friend class leap_second;
      friend struct time_zone::_Impl;
      friend class time_zone_link;
    };

    class time_zone_link
    {
    public:
      time_zone_link(time_zone_link&&) = default;
      time_zone_link& operator=(time_zone_link&&) = default;

      string_view name() const noexcept { return _M_name; }
      string_view target() const noexcept { return _M_target; }

      friend bool
      operator==(const time_zone_link& __x, const time_zone_link& __y) noexcept
      { return __x.name() == __y.name(); }

      friend strong_ordering
      operator<=>(const time_zone_link& __x, const time_zone_link& __y) noexcept
      { return __x.name() <=> __y.name(); }

    private:
      friend const tzdb& reload_tzdb();
      friend struct tzdb_list::_Node;

      explicit time_zone_link(nullptr_t) { }

      string _M_name;
      string _M_target;
    };

    class leap_second
    {
    public:
      leap_second(const leap_second&) = default;
      leap_second& operator=(const leap_second&) = default;

      [[nodiscard]]
      constexpr sys_seconds
      date() const noexcept
      {
	if (_M_s >= _M_s.zero()) [[likely]]
	  return sys_seconds(_M_s);
	return sys_seconds(-_M_s);
      }

      [[nodiscard]]
      constexpr seconds
      value() const noexcept
      {
	if (_M_s >= _M_s.zero()) [[likely]]
	  return seconds(1);
	return seconds(-1);
      }

      // This can be defaulted because the database will never contain two
      // leap_second objects with the same date but different signs.
      [[nodiscard]] friend constexpr bool
      operator==(const leap_second&, const leap_second&) noexcept = default;

      [[nodiscard]] friend constexpr strong_ordering
      operator<=>(const leap_second& __x, const leap_second& __y) noexcept
      { return __x.date() <=> __y.date(); }

      template<typename _Duration>
	[[nodiscard]] friend constexpr bool
	operator==(const leap_second& __x,
		   const sys_time<_Duration>& __y) noexcept
	{ return __x.date() == __y; }

      template<typename _Duration>
	[[nodiscard]] friend constexpr bool
	operator<(const leap_second& __x,
		  const sys_time<_Duration>& __y) noexcept
	{ return __x.date() < __y; }

      template<typename _Duration>
	[[nodiscard]] friend constexpr bool
	operator<(const sys_time<_Duration>& __x,
		  const leap_second& __y) noexcept
	{ return __x < __y.date(); }

      template<typename _Duration>
	[[nodiscard]] friend constexpr bool
	operator>(const leap_second& __x,
		  const sys_time<_Duration>& __y) noexcept
	{ return __y < __x.date(); }

      template<typename _Duration>
	[[nodiscard]] friend constexpr bool
	operator>(const sys_time<_Duration>& __x,
		  const leap_second& __y) noexcept
	{ return __y.date() < __x; }

      template<typename _Duration>
	[[nodiscard]] friend constexpr bool
	operator<=(const leap_second& __x,
		   const sys_time<_Duration>& __y) noexcept
	{ return !(__y < __x.date()); }

      template<typename _Duration>
	[[nodiscard]] friend constexpr bool
	operator<=(const sys_time<_Duration>& __x,
		   const leap_second& __y) noexcept
	{ return !(__y.date() < __x); }

      template<typename _Duration>
	[[nodiscard]] friend constexpr bool
	operator>=(const leap_second& __x,
		   const sys_time<_Duration>& __y) noexcept
	{ return !(__x.date() < __y); }

      template<typename _Duration>
	[[nodiscard]] friend constexpr bool
	operator>=(const sys_time<_Duration>& __x,
		   const leap_second& __y) noexcept
	{ return !(__x < __y.date()); }

      // This is a simplified form of the constraint specified in the standard,
      // three_way_comparable_with<sys_seconds, sys_time<_Duration>>.
      template<three_way_comparable_with<seconds> _Duration>
	[[nodiscard]] friend constexpr auto
	operator<=>(const leap_second& __x,
		    const sys_time<_Duration>& __y) noexcept
	{ return __x.date() <=> __y; }

    private:
      explicit leap_second(seconds::rep __s) : _M_s(__s) { }

      friend struct tzdb_list::_Node;

      friend const tzdb& reload_tzdb();

      template<typename _Duration>
	friend leap_second_info
	get_leap_second_info(const utc_time<_Duration>&);

      seconds _M_s; // == date().time_since_epoch() * value().count()
    };

    template<class _Tp> struct zoned_traits { };

    template<>
      struct zoned_traits<const time_zone*>
      {
	static const time_zone*
	default_zone()
	{ return std::chrono::locate_zone("UTC"); }

	static const time_zone*
	locate_zone(string_view __name)
	{ return std::chrono::locate_zone(__name); }
      };

    struct tzdb
    {
      string version;
      _GLIBCXX_STD_C::vector<time_zone> zones;
      _GLIBCXX_STD_C::vector<time_zone_link> links;
      _GLIBCXX_STD_C::vector<leap_second> leap_seconds;

      const time_zone*
      locate_zone(string_view __tz_name) const;

      const time_zone*
      current_zone() const;

    private:
      friend const tzdb& reload_tzdb();
      friend class time_zone;
      friend struct tzdb_list::_Node;
    };

    tzdb_list& get_tzdb_list();
    const tzdb& get_tzdb();

    const tzdb& reload_tzdb();
    string remote_version();

    template<typename _Duration, typename _TimeZonePtr = const time_zone*>
      class zoned_time
      {
	static_assert(__is_duration_v<_Duration>);

	using _Traits = zoned_traits<_TimeZonePtr>;

	// Every constructor that accepts a string_view as its first parameter
	// does not participate in class template argument deduction.
	using string_view = type_identity_t<std::string_view>;

      public:
	using duration = common_type_t<_Duration, seconds>;

	zoned_time() requires requires { _Traits::default_zone(); }
	{ }

	zoned_time(const zoned_time&) = default;
	zoned_time& operator=(const zoned_time&) = default;

	zoned_time(const sys_time<_Duration>& __st)
	  requires requires { _Traits::default_zone(); }
	: _M_tp(__st)
	{ }

	explicit
	zoned_time(_TimeZonePtr __z) : _M_zone(std::move(__z)) { }

	explicit
	zoned_time(string_view __name)
	  requires requires {
	    _TimeZonePtr{_Traits::locate_zone(std::string_view{})};
	  }
	: _M_zone(_Traits::locate_zone(__name))
	{ }

	template<typename _Duration2>
	  zoned_time(const zoned_time<_Duration2, _TimeZonePtr>& __zt)
	  requires is_convertible_v<sys_time<_Duration2>, sys_time<_Duration>>
	  : _M_zone(__zt._M_zone), _M_tp(__zt._M_tp)
	  { }

	zoned_time(_TimeZonePtr __z, const sys_time<_Duration>& __st)
	: _M_zone(std::move(__z)), _M_tp(__st)
	{ }

	zoned_time(string_view __name, const sys_time<_Duration>& __st)
	: zoned_time(_Traits::locate_zone(__name), __st)
	{ }

	zoned_time(_TimeZonePtr __z, const local_time<_Duration>& __tp)
	requires requires {
	  { __z->to_sys(__tp) } -> convertible_to<sys_time<_Duration>>;
	}
	: _M_zone(std::move(__z)), _M_tp(_M_zone->to_sys(__tp))
	{ }

	zoned_time(string_view __name, const local_time<_Duration>& __tp)
	requires requires (_TimeZonePtr __z) {
	  { _Traits::locate_zone(__name) } -> convertible_to<_TimeZonePtr>;
	  { __z->to_sys(__tp) } -> convertible_to<sys_time<_Duration>>;
	}
	: zoned_time(_Traits::locate_zone(__name), __tp)
	{ }

	zoned_time(_TimeZonePtr __z, const local_time<_Duration>& __tp,
		   choose __c)
	requires requires {
	  { __z->to_sys(__tp, __c) } -> convertible_to<sys_time<_Duration>>;
	}
	: _M_zone(std::move(__z)), _M_tp(_M_zone->to_sys(__tp, __c))
	{ }

	zoned_time(string_view __name, const local_time<_Duration>& __tp,
		   choose __c)
	requires requires (_TimeZonePtr __z) {
	  { _Traits::locate_zone(__name) } -> convertible_to<_TimeZonePtr>;
	  { __z->to_sys(__tp, __c) } -> convertible_to<sys_time<_Duration>>;
	}
	: _M_zone(_Traits::locate_zone(__name)),
	  _M_tp(_M_zone->to_sys(__tp, __c))
	{ }

	template<typename _Duration2, typename _TimeZonePtr2>
	  zoned_time(_TimeZonePtr __z,
		     const zoned_time<_Duration2, _TimeZonePtr2>& __zt)
	  requires is_convertible_v<sys_time<_Duration2>, sys_time<_Duration>>
	  : _M_zone(__z), _M_tp(__zt._M_tp)
	  { }

	template<typename _Duration2, typename _TimeZonePtr2>
	  zoned_time(_TimeZonePtr __z,
		     const zoned_time<_Duration2, _TimeZonePtr2>& __zt,
		     choose)
	  requires is_convertible_v<sys_time<_Duration2>, sys_time<_Duration>>
	  : _M_zone(__z), _M_tp(__zt._M_tp)
	  { }

	template<typename _Duration2, typename _TimeZonePtr2>
	  zoned_time(string_view __name,
		     const zoned_time<_Duration2, _TimeZonePtr2>& __zt)
	  requires is_convertible_v<sys_time<_Duration2>, sys_time<_Duration>>
	  && requires {
	    { _Traits::locate_zone(__name) } -> convertible_to<_TimeZonePtr>;
	  }
	  : _M_zone(_Traits::locate_zone(__name)), _M_tp(__zt._M_tp)
	  { }

	template<typename _Duration2, typename _TimeZonePtr2>
	  zoned_time(string_view __name,
		     const zoned_time<_Duration2, _TimeZonePtr2>& __zt,
		     choose)
	  requires is_convertible_v<sys_time<_Duration2>, sys_time<_Duration>>
	  && requires {
	    { _Traits::locate_zone(__name) } -> convertible_to<_TimeZonePtr>;
	  }
	  : _M_zone(_Traits::locate_zone(__name)), _M_tp(__zt._M_tp)
	  { }

	zoned_time&
	operator=(const sys_time<_Duration>& __st)
	{
	  _M_tp = __st;
	  return *this;
	}

	zoned_time&
	operator=(const local_time<_Duration>& __lt)
	{
	  _M_tp = _M_zone->to_sys(__lt);
	  return *this;
	}

	[[nodiscard]]
	operator sys_time<duration>() const { return _M_tp; }

	[[nodiscard]]
	explicit operator local_time<duration>() const
	{ return get_local_time(); }

	[[nodiscard]]
	_TimeZonePtr
	get_time_zone() const
	{ return _M_zone; }

	[[nodiscard]]
	local_time<duration>
	get_local_time() const
	{ return _M_zone->to_local(_M_tp); }

	[[nodiscard]]
	sys_time<duration>
	get_sys_time() const
	{ return _M_tp; }

	[[nodiscard]]
	sys_info
	get_info() const
	{ return _M_zone->get_info(_M_tp); }

	[[nodiscard]] friend bool
	operator==(const zoned_time&, const zoned_time&) = default;

      private:
	_TimeZonePtr       _M_zone{ _Traits::default_zone() };
	sys_time<duration> _M_tp{};

	template<typename _Duration2, typename _TimeZonePtr2>
	  friend class zoned_time;
      };

    zoned_time() -> zoned_time<seconds>;

    template<typename _Duration>
    zoned_time(sys_time<_Duration>)
      -> zoned_time<common_type_t<_Duration, seconds>>;

  /// @cond undocumented
  template<typename _TimeZonePtrOrName>
    using __time_zone_representation
      = __conditional_t<is_convertible_v<_TimeZonePtrOrName, string_view>,
			const time_zone*,
			remove_cvref_t<_TimeZonePtrOrName>>;
  /// @endcond

  template<typename _TimeZonePtrOrName>
    zoned_time(_TimeZonePtrOrName&&)
      -> zoned_time<seconds, __time_zone_representation<_TimeZonePtrOrName>>;

  template<typename _TimeZonePtrOrName, typename _Duration>
    zoned_time(_TimeZonePtrOrName&&, sys_time<_Duration>)
      -> zoned_time<common_type_t<_Duration, seconds>,
                    __time_zone_representation<_TimeZonePtrOrName>>;

  template<typename _TimeZonePtrOrName, typename _Duration>
    zoned_time(_TimeZonePtrOrName&&, local_time<_Duration>,
               choose = choose::earliest)
      -> zoned_time<common_type_t<_Duration, seconds>,
                    __time_zone_representation<_TimeZonePtrOrName>>;

  template<typename _Duration, typename _TimeZonePtrOrName,
	   typename _TimeZonePtr2>
    zoned_time(_TimeZonePtrOrName&&, zoned_time<_Duration, _TimeZonePtr2>,
               choose = choose::earliest)
      -> zoned_time<common_type_t<_Duration, seconds>,
                    __time_zone_representation<_TimeZonePtrOrName>>;

  template<typename _Dur1, typename _TZPtr1, typename _Dur2, typename _TZPtr2>
    [[nodiscard]]
    inline bool
    operator==(const zoned_time<_Dur1, _TZPtr1>& __x,
	       const zoned_time<_Dur2, _TZPtr2>& __y)
    {
      return __x.get_time_zone() == __y.get_time_zone()
	       && __x.get_sys_time() == __y.get_sys_time();
    }

    using zoned_seconds = zoned_time<seconds>;
#endif // _GLIBCXX_USE_CXX11_ABI || ! _GLIBCXX_USE_DUAL_ABI

namespace __detail
{
    inline leap_second_info
    __get_leap_second_info(sys_seconds __ss, bool __is_utc)
    {
      if (__ss < sys_seconds{}) [[unlikely]]
	return {};

      const seconds::rep __leaps[] {
	  78796800, // 1 Jul 1972
	  94694400, // 1 Jan 1973
	 126230400, // 1 Jan 1974
	 157766400, // 1 Jan 1975
	 189302400, // 1 Jan 1976
	 220924800, // 1 Jan 1977
	 252460800, // 1 Jan 1978
	 283996800, // 1 Jan 1979
	 315532800, // 1 Jan 1980
	 362793600, // 1 Jul 1981
	 394329600, // 1 Jul 1982
	 425865600, // 1 Jul 1983
	 489024000, // 1 Jul 1985
	 567993600, // 1 Jan 1988
	 631152000, // 1 Jan 1990
	 662688000, // 1 Jan 1991
	 709948800, // 1 Jul 1992
	 741484800, // 1 Jul 1993
	 773020800, // 1 Jul 1994
	 820454400, // 1 Jan 1996
	 867715200, // 1 Jul 1997
	 915148800, // 1 Jan 1999
	1136073600, // 1 Jan 2006
	1230768000, // 1 Jan 2009
	1341100800, // 1 Jul 2012
	1435708800, // 1 Jul 2015
	1483228800, // 1 Jan 2017
      };
      // The list above is known to be valid until (at least) this date
      // and only contains positive leap seconds.
      constexpr sys_seconds __expires(1782604800s); // 2026-06-28 00:00:00 UTC

#if _GLIBCXX_USE_CXX11_ABI || ! _GLIBCXX_USE_DUAL_ABI
      if (__ss > __expires)
	{
	  // Use updated leap_seconds from tzdb.
	  size_t __n = std::size(__leaps);

	  auto __db = get_tzdb_list().begin();
	  auto __first = __db->leap_seconds.begin() + __n;
	  auto __last = __db->leap_seconds.end();
	  auto __pos = std::upper_bound(__first, __last, __ss);
	  seconds __elapsed(__n);
	  for (auto __i = __first; __i != __pos; ++__i)
	    __elapsed += __i->value();

	  if (__is_utc)
	    {
	      // Convert utc_time to sys_time:
	      __ss -= __elapsed;
	      // See if that sys_time is before (or during) previous leap sec:
	      if (__pos != __first && __ss < __pos[-1])
		{
		  if ((__ss + 1s) >= __pos[-1])
		    return {true, __elapsed};
		  __elapsed -= __pos[-1].value();
		}
	    }
	  return {false, __elapsed};
	}
      else
#endif
	{
	  seconds::rep __s = __ss.time_since_epoch().count();
	  const seconds::rep* __first = std::begin(__leaps);
	  const seconds::rep* __last = std::end(__leaps);

	  // Don't bother searching the list if we're after the last one.
	  if (__s > (__last[-1] + (__last - __first) + 1))
	    return { false, seconds(__last - __first) };

	  auto __pos = std::upper_bound(__first, __last, __s);
	  seconds __elapsed{__pos - __first};
	  if (__is_utc)
	    {
	      // Convert utc_time to sys_time:
	      __s -= __elapsed.count();
	      // See if that sys_time is before (or during) previous leap sec:
	      if (__pos != __first && __s < __pos[-1])
		{
		  if ((__s + 1) >= __pos[-1])
		    return {true, __elapsed};
		  --__elapsed;
		}
	    }
	  return {false, __elapsed};
	}
    }
} // namespace __detail

    template<typename _Duration>
      [[nodiscard]]
      inline leap_second_info
      get_leap_second_info(const utc_time<_Duration>& __ut)
      {
	auto __s = chrono::duration_cast<seconds>(__ut.time_since_epoch());
	return __detail::__get_leap_second_info(sys_seconds(__s), true);
      }

    template<typename _Duration>
      [[nodiscard]]
      inline utc_time<common_type_t<_Duration, seconds>>
      utc_clock::from_sys(const sys_time<_Duration>& __t)
      {
	using _CDur = common_type_t<_Duration, seconds>;
	auto __s = chrono::time_point_cast<seconds>(__t);
	const auto __li = __detail::__get_leap_second_info(__s, false);
	return utc_time<_CDur>{__t.time_since_epoch()} + __li.elapsed;
      }
#endif // _GLIBCXX_HOSTED

    /// @} group chrono
#endif // C++20
  } // namespace chrono

#if __glibcxx_chrono_cxx20 >= 202306 // C++26
  // Hash support [time.hash]

  template<typename _Tp>
    concept __is_nothrow_copy_hashable = requires(const _Tp& __t) {
      { hash<_Tp>{}(_Tp(__t)) } noexcept -> same_as<size_t>;
    };

 namespace chrono {

   template<typename _T1, typename... _Ts>
     [[__gnu__::__always_inline__]]
     constexpr auto
     __pack_ints(_T1 __v1, _Ts... __vs)
     {
       using _ResT = decltype([] {
         constexpr size_t __tsize = (sizeof(_T1) + ... + sizeof(_Ts));
	 if constexpr (__tsize <= 1)
	   return static_cast<unsigned char>(0);
	 else if constexpr (__tsize <= 2)
	   return static_cast<__UINT16_TYPE__>(0);
	 else if constexpr (__tsize <= 4)
	   return static_cast<__UINT32_TYPE__>(0);
	 else if constexpr (__tsize <= 8)
	   return static_cast<__UINT64_TYPE__>(0);
	 else
	   static_assert(__tsize <= 8);
       }());

       _ResT __res = __v1;
       ((__res = (__res << (sizeof(_Ts) * __CHAR_BIT__) | _ResT(__vs))), ...);
       return __res;
     }
    
   template<typename _Tp>
     [[__gnu__::__always_inline__]]
     constexpr auto
     __as_int(_Tp __val)
     {
       if constexpr (is_same_v<_Tp, year>)
	 return static_cast<unsigned short>(static_cast<int>(__val));
       else if constexpr (is_same_v<_Tp, month> || is_same_v<_Tp, day>)
	 return static_cast<unsigned char>(static_cast<unsigned>(__val));
       else if constexpr (is_same_v<_Tp, weekday>)
	 return static_cast<unsigned char>(__val.c_encoding());
       else if constexpr (is_same_v<_Tp, weekday_indexed>)
	 return __pack_ints(chrono::__as_int(__val.weekday()),
			    static_cast<unsigned char>(__val.index()));
       else if constexpr (is_same_v<_Tp, weekday_last>)
	 return chrono::__as_int(__val.weekday());
       else
	 static_assert(false);
     }

   template<typename _Arg, typename... _Args>
     size_t
     __int_hash(_Arg __arg, _Args... __args)
     {
       static_assert((is_integral_v<_Arg> && ... && is_integral_v<_Args>));

       // TODO consider using a better quality hasher
       using _Hasher = _Hash_impl;
       size_t __result = _Hasher::hash(__arg);
       ((__result = _Hasher::__hash_combine(__args, __result)), ...);
       return __result;
     }

   template<typename... _Tps>
     [[__gnu__::__always_inline__]]
     inline size_t
     __hash(_Tps... __vals)
     {
       if constexpr (sizeof...(_Tps) == 1)
	 return chrono::__int_hash(chrono::__as_int(__vals)...);
       else
	 {
	   auto __res = chrono::__pack_ints(chrono::__as_int(__vals)...);
	   return chrono::__int_hash(__res);
	 }
     }
 } // namespace chrono

  // duration
  template<typename _Rep, typename _Period>
    requires __is_hash_enabled_for<_Rep>
    struct hash<chrono::duration<_Rep, _Period>>
    {
      size_t
      operator()(const chrono::duration<_Rep, _Period>& __val) const
      noexcept(__is_nothrow_copy_hashable<_Rep>)
      {	
	if constexpr (is_integral_v<_Rep>)
	  return chrono::__int_hash(__val.count());
	else
	  return hash<_Rep>{}(__val.count());
      }
    };

  template<typename _Rep, typename _Period>
    struct __is_fast_hash<hash<chrono::duration<_Rep, _Period>>>
    : __is_fast_hash<hash<_Rep>>
    {};

  // time_point
  template<typename _Clock, typename _Dur>
    requires __is_hash_enabled_for<_Dur>
    struct hash<chrono::time_point<_Clock, _Dur>>
    {
      size_t
      operator()(const chrono::time_point<_Clock, _Dur>& __val) const
      noexcept(__is_nothrow_copy_hashable<_Dur>)
      { return hash<_Dur>{}(__val.time_since_epoch()); }
    };

  template<typename _Clock, typename _Dur>
    struct __is_fast_hash<hash<chrono::time_point<_Clock, _Dur>>>
    : __is_fast_hash<hash<_Dur>>
    {};

  // day
  template<>
    struct hash<chrono::day>
    {
      size_t
      operator()(chrono::day __val) const noexcept
      { return chrono::__hash(__val); }
    };

  // month
  template<>
    struct hash<chrono::month>
    {
      size_t
      operator()(chrono::month __val) const noexcept
      { return chrono::__hash(__val); }
    };

  // year
  template<>
    struct hash<chrono::year>
    {
      size_t
      operator()(chrono::year __val) const noexcept
      { return chrono::__hash(__val); }
    };

  // weekday
  template<>
    struct hash<chrono::weekday>
    {
      size_t
      operator()(chrono::weekday __val) const noexcept
      { return chrono::__hash(__val); }
    };

  // weekday_indexed
  template<>
    struct hash<chrono::weekday_indexed>
    {
      size_t
      operator()(chrono::weekday_indexed __val) const noexcept
      { return chrono::__hash(__val); }
    };

  // weekday_last
  template<>
    struct hash<chrono::weekday_last>
    {
      size_t
      operator()(chrono::weekday_last __val) const noexcept
      { return chrono::__hash(__val); }
    };

  // month_day
  template<>
    struct hash<chrono::month_day>
    {
      size_t
      operator()(chrono::month_day __val) const noexcept
      { return chrono::__hash(__val.month(), __val.day()); }
    };

  // month_day_last
  template<>
    struct hash<chrono::month_day_last>
    {
      size_t operator()(chrono::month_day_last __val) const noexcept
      { return chrono::__hash(__val.month()); }
    };

  // month_weekday
  template<>
    struct hash<chrono::month_weekday>
    {
      size_t
      operator()(chrono::month_weekday __val) const noexcept
      { return chrono::__hash(__val.month(), __val.weekday_indexed()); }
    };

  // month_weekday_last
  template<>
    struct hash<chrono::month_weekday_last>
    {
      size_t
      operator()(chrono::month_weekday_last __val) const noexcept
      { return chrono::__hash(__val.month(), __val.weekday_last()); }
    };

  // year_month
  template<>
    struct hash<chrono::year_month>
    {
      size_t
      operator()(chrono::year_month __val) const noexcept
      { return chrono::__hash(__val.year(), __val.month()); }
    };

  // year_month_day
  template<>
    struct hash<chrono::year_month_day>
    {
      size_t
      operator()(chrono::year_month_day __val) const noexcept
      { return chrono::__hash(__val.year(), __val.month(), __val.day()); }
    };

  // year_month_day_last
  template<>
    struct hash<chrono::year_month_day_last>
    {
      size_t
      operator()(chrono::year_month_day_last __val) const noexcept
      { return chrono::__hash(__val.year(), __val.month()); }
    };

  // year_month_weekday
  template<>
    struct hash<chrono::year_month_weekday>
    {
      size_t
      operator()(chrono::year_month_weekday __val) const noexcept
      { 
	return chrono::__hash(__val.year(), __val.month(),
			      __val.weekday_indexed());
      }
    };

  // year_month_weekday_last
  template<>
    struct hash<chrono::year_month_weekday_last>
    {
      size_t
      operator()(chrono::year_month_weekday_last __val) const noexcept
      { 
	return chrono::__hash(__val.year(), __val.month(),
			      __val.weekday_last());
      }
    };

#if _GLIBCXX_HOSTED
#if _GLIBCXX_USE_CXX11_ABI || ! _GLIBCXX_USE_DUAL_ABI
  // zoned_time
  template<typename _Duration, typename _TimeZonePtr>
    requires __is_hash_enabled_for<
	       typename chrono::zoned_time<_Duration, _TimeZonePtr>::duration>
	     && __is_hash_enabled_for<_TimeZonePtr>
    struct hash<chrono::zoned_time<_Duration, _TimeZonePtr>>
    {
    private:
      using _ActualDuration =
	typename chrono::zoned_time<_Duration, _TimeZonePtr>::duration;

    public:
      size_t
      operator()(const chrono::zoned_time<_Duration, _TimeZonePtr>& __val) const
      noexcept(__is_nothrow_copy_hashable<_ActualDuration>
	       && __is_nothrow_copy_hashable<_TimeZonePtr>)
      {
	const auto __iduration = [&] {
	  const _ActualDuration __sd = __val.get_sys_time().time_since_epoch();
	  if constexpr (is_integral_v<typename _ActualDuration::rep>)
	    return __sd.count();
	  else
	    return hash<_ActualDuration>{}(__sd);
	}();

	const auto __izone = [&] {
	  const _TimeZonePtr __tz = __val.get_time_zone();
	  if constexpr (is_same_v<_TimeZonePtr, const chrono::time_zone*>)
	    return reinterpret_cast<uintptr_t>(__tz);
	  else
	    return hash<_TimeZonePtr>{}(__tz);
	}();

	return chrono::__int_hash(__iduration, __izone);
      }
    };

  template<typename _Duration, typename _TimeZonePtr>
    struct __is_fast_hash<hash<chrono::zoned_time<_Duration, _TimeZonePtr>>>
    : __and_<__is_fast_hash<hash<
	       typename chrono::zoned_time<_Duration, _TimeZonePtr>::duration>>,
	     __is_fast_hash<hash<_TimeZonePtr>>>
    {};

  // leap_second
  template<>
    struct hash<chrono::leap_second>
    {
      size_t
      operator()(chrono::leap_second __val) const noexcept
      { 
	return chrono::__int_hash(
		 __val.date().time_since_epoch().count(),
		 __val.value().count());
      }
    };
#endif // _GLIBCXX_USE_CXX11_ABI || ! _GLIBCXX_USE_DUAL_ABI
#endif // _GLIBCXX_HOSTED
#endif // __glibcxx_chrono_cxx20 >= 202306

#ifdef __glibcxx_chrono_cxx20
  inline namespace literals
  {
  inline namespace chrono_literals
  {
    /// @addtogroup chrono
    /// @{
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wliteral-suffix"
    /// Literal suffix for creating chrono::day objects.
    /// @since C++20
    constexpr chrono::day
    operator""d(unsigned long long __d) noexcept
    { return chrono::day{static_cast<unsigned>(__d)}; }

    /// Literal suffix for creating chrono::year objects.
    /// @since C++20
    constexpr chrono::year
    operator""y(unsigned long long __y) noexcept
    { return chrono::year{static_cast<int>(__y)}; }
#pragma GCC diagnostic pop
    /// @}
  } // inline namespace chrono_literals
  } // inline namespace literals
#endif // C++20

_GLIBCXX_END_NAMESPACE_VERSION
} // namespace std

#if defined __glibcxx_chrono_cxx20 && _GLIBCXX_HOSTED
# include <bits/chrono_io.h>
#endif

#endif // C++11

#endif //_GLIBCXX_CHRONO
