On Thu, May 7, 2026 at 9:58 AM Jonathan Wakely <[email protected]>
wrote:

> I think we might as well just move the whole function into the library,
> and only have one place that keeps the list of leap seconds and the expiry.
>
The separation requires us to pass one parameter: the number of leap
seconds.
so I don't think it adds that much complexity.

>
> That way we don't need to care about what's in the header.
>
We also avoid the risk that someone will slap constexpr of this function in
header
file, do one test and propose to make it so.

>
>

>
> On Thu, 7 May 2026, 07:15 Tomasz Kaminski, <[email protected]> wrote:
>
>>
>>
>> On Thu, May 7, 2026 at 7:58 AM Tomasz Kaminski <[email protected]>
>> wrote:
>>
>>>
>>>
>>> On Wed, May 6, 2026 at 7:28 PM Jonathan Wakely <[email protected]>
>>> wrote:
>>>
>>>> On Wed, 6 May 2026 at 15:47, Tomasz Kaminski <[email protected]>
>>>> wrote:
>>>> >
>>>> >
>>>> >
>>>> > On Wed, May 6, 2026 at 4:18 PM Jonathan Wakely <[email protected]>
>>>> wrote:
>>>> >>
>>>> >> This change allows the hardcoded list of leap seconds in <chrono> to
>>>> be
>>>> >> used even when the program is executing after the hardcoded expiry
>>>> date
>>>> >> in that header. If the OS-provided leapseconds file has a later
>>>> expiry
>>>> >> date (or contains new leap seconds added after the one in 2017) then
>>>> the
>>>> >> new __detail::__leap_seconds_expiry() function will return that new
>>>> >> dynamically-obtained expiry date. The
>>>> __detail::__get_leap_second_info
>>>> >> function in the header can check that new expiry date instead of
>>>> relying
>>>> >> only on the hardcoded one.
>>>> >>
>>>> >> This change means that in the worst case we now make two calls into
>>>> the
>>>> >> library (one to get the dynamic expiry date and then possibly another
>>>> >> one to get the actual list of new leap seconds). Previously we just
>>>> make
>>>> >> one, to get the list. The change seems worthwhile, because it means
>>>> that
>>>> >> in more cases we don't need to increment+decrement the reference
>>>> count
>>>> >> on a tzdb object and use its leapseconds vector, we can just use the
>>>> >> hardcoded array.
>>>> >>
>>>> >> The new expiry date is stored in a global variable, rather than being
>>>> >> per-tzdb object, but that seems fine because we only ever expect that
>>>> >> expiry date to move forwards in time, not to move forwards and
>>>> backwards
>>>> >> as new tzdb objects are loaded by chrono::reload_tzdb(). Even if a
>>>> new
>>>> >> list of leap seconds is loaded, we still expect an expiry date that
>>>> was
>>>> >> loaded previously to be valid.
>>>> >
>>>> > I was wondering about it in connection to the test that overrides the
>>>> zone directory,
>>>> > and may move the date around. But for those already impacted by the
>>>> fact that
>>>> > any date with an expiry date before one that we hardcode is ignored.
>>>> However,
>>>> > for that reason, I would ensure we do not move the date backward;
>>>> suggestion below.
>>>> > (In also could move backward if reading #experies fails).
>>>>
>>> I think I would like to propose a bit of different model. As different
>>> GCC versions will
>>> hardcode different number of leap seconds in the header, we should
>>> provide function looking like
>>> that:
>>>    // Returns expiry time for nth leap second.
>>>    __expiry_of_leap_second(size_t nth);
>>> This function should return 1s prior the expiry of nth leap second, if
>>> that is know to the
>>> tzdb (as you do), but if current time zone database didn't load leap
>>> second data with it,
>>> we could return infinity (expiry_type max). This is totally fine, as
>>> reload_tzdb call that
>>> will load nth leap second will cause a new value to be returned (this is
>>> checked on each all).
>>> Then in the header, we do something like: f (__ss > __expires && __ss
>>> > __expiry_of_leap_second(std::size(leaps)))
>>>
>>> Now in the source file, we will have:
>>> const sys_seconds static_leaps[] = ....; // leaps second know when
>>> compiled
>>> const atomic<expiry_time> next_leap(expiry_max); // There is no next
>>> leap second data at this point
>>>
>>> Implementation of __expiry_of_leap_second will be something like:
>>>    if (nth < sizeof(static_leaps))
>>>      return __leaps[_nth]; // this leap second data was compiled into
>>> binary
>>>   else if (nth == sizeof(static_leaps))
>>>      return __next_leap.load(relaxed); // time of next leap second not
>>> know by binary
>>>   else
>>>
>>      // This is caused by linking code compiled with new headers against
>>>      // older version of leapstdc++, we know that nth leap will be after
>>> __next_leap,
>>>      // so return currently know value of __next_leap.
>>>      return __next_leap.load(relaxed);
>>>
>> The above could be simply 0, as we know the expiry time in that header is
>> later
>> date that __next_heap (because it included that leap second). Returning
>> __next_leap
>> however guaratees tht if we didn't load the new data from disk (and it is
>> infinite),
>> we will use header information that have more data that library file.
>>
>>
>>>
>>> The loading leaps seconds file does not need to check expiry, just do
>>> something like:
>>>     if (leaps.size() > static_leaps.size()) // we loaded the next leap
>>> second
>>>       expiry_time =
>>> leaps[static_leaps.size()].time_since_epoch().count() - 1;
>>>    else
>>>       expiry_time = expiry_max; // There is no new leap second data.
>>>
>>> And simply update expiry_time to this value.
>>>
>>>
>>>
>>>> There are three problem cases I was worried about.
>>>>
>>>> The happy path is where we read a good expiry time from the
>>>> leapseconds file, so we want to store it in the global variable.
>>>> That's the easy case.
>>>>
>>>> If the file doesn't contain any #expires line so we should not update
>>>> the global.
>>>>
>>> Counterintuitively, I do not think the #experies line is important when
>>> loading dynamically updates the time, so my suggestion solves that.
>>>
>>>
>>>>
>>>> The second problem case is where it contains an #expires line, but we
>>>> fail to parse the value (maybe the format changed in a future version
>>>> of the file?). This should not happen, but is possible for a custom
>>>> leapseconds file provided by the user or their sysadmin, and we should
>>>> not update the global in this case.
>>>>
>>> We do not look at #expires so this is also solved.
>>>
>>>>
>>>> The third problem is where a bad leapseconds file is installed and it
>>>> has a bad #expires line, with a date too far in the future (maybe
>>>> somebody makes a typo in a custom file and it has too many digits). In
>>>> this case, the user/sysadmin might install a fixed leapseconds file,
>>>> then trigger the application to call reload_tzdb() to read the fixed
>>>> file. In this case, we would want to update the global even if it
>>>> means moving backwards in time.
>>>>
>>> This would be equivalent to someone accidentally putting a wrong file
>>> with 28th leap second put very close to the date (between header expiry
>>> and now), that would cause wrong converison, as next_leap will be udpate.
>>> But with my suggestion for reload, putting a correct version will always
>>> fix that,
>>> as we override next_leap:
>>>   * if 28th leap was removed, we will update timout to maximium, until
>>> it will show up
>>>   * if value was changed, we will also update it to it
>>>
>>> And in my approach the expiry time always corresponds to tzdb latest.
>>>
>>>>
>>>> In all cases, if a 28th leap second has been defined, that becomes the
>>>> new expiry.
>>>>
>>>> >
>>>> >>
>>>> >>
>>>> >> libstdc++-v3/ChangeLog:
>>>> >>
>>>> >>         PR libstdc++/123165
>>>> >>         * acinclude.m4 (libtool_VERSION): Bump version.
>>>> >>         * config/abi/pre/gnu.ver (GLIBCXX_3.4.36): Add new symbol
>>>> >>         version and export new symbol.
>>>> >>         * configure: Regenerate.
>>>> >>         * include/std/chrono (__detail::__leap_seconds_expiry):
>>>> >>         Declare new function.
>>>> >>         (__detail::__get_leap_second_info): Use new function.
>>>> >>         * src/c++20/tzdb.cc (__detail::__leap_seconds_expiry):
>>>> Define.
>>>> >>         (tzdb_list::_Node::_S_read_leap_seconds): Read 'expires' line
>>>> >>         from leapseconds file and optionally update global cache.
>>>> >>         * testsuite/std/time/tzdb/leap_seconds.cc: Add expires line
>>>> to
>>>> >>         replacement leapseconds file.
>>>> >>         * testsuite/util/testsuite_abi.cc: Update known_versions and
>>>> >>         latestp.
>>>> >> ---
>>>> >>
>>>> >> Tested x86_64-linux.
>>>> >>
>>>> >>
>>>> >>  libstdc++-v3/acinclude.m4                     |  2 +-
>>>> >>  libstdc++-v3/config/abi/pre/gnu.ver           |  7 ++
>>>> >>  libstdc++-v3/configure                        |  2 +-
>>>> >>  libstdc++-v3/include/std/chrono               |  9 +-
>>>> >>  libstdc++-v3/src/c++20/tzdb.cc                | 88
>>>> ++++++++++++++++---
>>>> >>  .../testsuite/std/time/tzdb/leap_seconds.cc   |  1 +
>>>> >>  libstdc++-v3/testsuite/util/testsuite_abi.cc  |  3 +-
>>>> >>  7 files changed, 96 insertions(+), 16 deletions(-)
>>>> >>
>>>> >> diff --git a/libstdc++-v3/acinclude.m4 b/libstdc++-v3/acinclude.m4
>>>> >> index 8dc9e17b214c..3a4b11a98a28 100644
>>>> >> --- a/libstdc++-v3/acinclude.m4
>>>> >> +++ b/libstdc++-v3/acinclude.m4
>>>> >> @@ -4085,7 +4085,7 @@ changequote([,])dnl
>>>> >>  fi
>>>> >>
>>>> >>  # For libtool versioning info, format is CURRENT:REVISION:AGE
>>>> >> -libtool_VERSION=6:35:0
>>>> >> +libtool_VERSION=6:36:0
>>>> >>
>>>> >>  # Everything parsed; figure out what files and settings to use.
>>>> >>  case $enable_symvers in
>>>> >> diff --git a/libstdc++-v3/config/abi/pre/gnu.ver
>>>> b/libstdc++-v3/config/abi/pre/gnu.ver
>>>> >> index bd4da6418295..35aaf89984d1 100644
>>>> >> --- a/libstdc++-v3/config/abi/pre/gnu.ver
>>>> >> +++ b/libstdc++-v3/config/abi/pre/gnu.ver
>>>> >> @@ -2623,6 +2623,13 @@ GLIBCXX_3.4.35 {
>>>> >>
>>>> >>  } GLIBCXX_3.4.34;
>>>> >>
>>>> >> +# GCC 17.1.0
>>>> >> +GLIBCXX_3.4.36 {
>>>> >> +
>>>> >> +    _ZNSt6chrono8__detail21__leap_seconds_expiryEv;
>>>> >> +
>>>> >> +} GLIBCXX_3.4.35;
>>>> >> +
>>>> >>  # Symbols in the support library (libsupc++) have their own tag.
>>>> >>  CXXABI_1.3 {
>>>> >>
>>>> >> diff --git a/libstdc++-v3/configure b/libstdc++-v3/configure
>>>> >> index 6713e4504b1c..013c388b9c2f 100755
>>>> >> --- a/libstdc++-v3/configure
>>>> >> +++ b/libstdc++-v3/configure
>>>> >> @@ -51418,7 +51418,7 @@ $as_echo "$as_me: WARNING: === Symbol
>>>> versioning will be disabled." >&2;}
>>>> >>  fi
>>>> >>
>>>> >>  # For libtool versioning info, format is CURRENT:REVISION:AGE
>>>> >> -libtool_VERSION=6:35:0
>>>> >> +libtool_VERSION=6:36:0
>>>> >>
>>>> >>  # Everything parsed; figure out what files and settings to use.
>>>> >>  case $enable_symvers in
>>>> >> diff --git a/libstdc++-v3/include/std/chrono
>>>> b/libstdc++-v3/include/std/chrono
>>>> >> index 674f867dcdc7..228293f12bef 100644
>>>> >> --- a/libstdc++-v3/include/std/chrono
>>>> >> +++ b/libstdc++-v3/include/std/chrono
>>>> >> @@ -3217,6 +3217,11 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>>>> >>
>>>> >>  namespace __detail
>>>> >>  {
>>>> >> +    // The list below is known to be valid until (at least) this
>>>> date.
>>>> >> +    // This value is defined in the library (possibly to a newer
>>>> value than
>>>> >> +    // the hardcoded value below) and can change at runtime.
>>>> >> +    sys_seconds __leap_seconds_expiry();
>>>> >> +
>>>> >>      inline leap_second_info
>>>> >>      __get_leap_second_info(sys_seconds __ss, bool __is_utc)
>>>> >>      {
>>>> >> @@ -3252,12 +3257,12 @@ namespace __detail
>>>> >>         1435708800, // 1 Jul 2015
>>>> >>         1483228800, // 1 Jan 2017
>>>> >>        };
>>>> >> +#if _GLIBCXX_USE_CXX11_ABI || ! _GLIBCXX_USE_DUAL_ABI // use
>>>> chrono::tzdb
>>>> >>        // The list above is known to be valid until (at least) this
>>>> date
>>>> >>        // and only contains positive leap seconds.
>>>> >>        constexpr sys_seconds __expires(1798416000s); // 2026-12-28
>>>> 00:00:00 U
>>>> >
>>>> >
>>>> >>
>>>> >> -#if _GLIBCXX_USE_CXX11_ABI || ! _GLIBCXX_USE_DUAL_ABI
>>>> >> -      if (__ss > __expires)
>>>> >> +      if (__ss > __expires && __ss > __leap_seconds_expiry())
>>>> >>         {
>>>> >>           // Use updated leap_seconds from tzdb.
>>>> >>           size_t __n = std::size(__leaps);
>>>> >> diff --git a/libstdc++-v3/src/c++20/tzdb.cc
>>>> b/libstdc++-v3/src/c++20/tzdb.cc
>>>> >> index b0fbfc46a6d3..ba0020814ba8 100644
>>>> >> --- a/libstdc++-v3/src/c++20/tzdb.cc
>>>> >> +++ b/libstdc++-v3/src/c++20/tzdb.cc
>>>> >> @@ -1251,6 +1251,40 @@ namespace std::chrono
>>>> >>    }
>>>> >>  #endif // TZDB_DISABLED
>>>> >>
>>>> >> +namespace
>>>> >> +{
>>>> >> +#if ATOMIC_LONG_LOCK_FREE == 2
>>>> >> +  using expiry_type = unsigned long;
>>>> >> +#else
>>>> >> +  using expiry_type = unsigned;
>>>> >> +#endif
>>>> >> +  // When GCC 16.1 was released with stable C++20 chrono support
>>>> (in 2026),
>>>> >> +  // the last leap second in the list was the one in 2017. If
>>>> another leap
>>>> >> +  // second is introduced in future, objects compiled by GCC 16.1
>>>> will not
>>>> >> +  // contain that leap second in the hardcoded list in <chrono>.
>>>> >> +  // This expiry time must be less than that first post-2017 leap
>>>> second,
>>>> >> +  // so that old copies of __get_leap_second_info will use
>>>> tzdb::leap_seconds
>>>> >> +  // which will contain the post-2017 leap seconds.
>>>> >> +  // If no new leap second is introduced, then this expiry time can
>>>> just be
>>>> >> +  // updated to the 'expires' value read from the leapseconds file.
>>>> >> +  // tzdata 2026a leapseconds list expires at 2026-12-28 00:00:00
>>>> UTC
>>>> >> +  constinit std::atomic<expiry_type>
>>>> leap_seconds_expiry{1798416000u};
>>>> >
>>>> > Could you extract the __expires  from
>>>> tzdb_list::_Node::_S_read_leap_seconds()
>>>> > (in this file)  as the global (but TU-local) variables, and use the
>>>> __expires as initializer here,
>>>> > so we do not need to update two prices. This will not add any symbols
>>>> to the library, as we are in source file.
>>>> > (This is why I am not suggesting doing that in header, as we will
>>>> need to make the data inline).
>>>> >
>>>> >
>>>> >>
>>>> >> +}
>>>> >> +
>>>> >> +  namespace __detail
>>>> >> +  {
>>>> >> +    // Called by chrono::__detail::__get_leap_second_info in
>>>> <chrono>.
>>>> >> +    // The value returned by this function determines whether the
>>>> hardcoded
>>>> >> +    // list in __get_leap_second_info is used, or if the
>>>> tzdb::leap_seconds
>>>> >> +    // vector is used, which might require parsing and constructing
>>>> a tzdb.
>>>> >> +    sys_seconds
>>>> >> +    __leap_seconds_expiry()
>>>> >> +    {
>>>> >> +      auto val = leap_seconds_expiry.load(memory_order::relaxed);
>>>> >> +      return sys_seconds(seconds(val));
>>>> >> +    }
>>>> >> +  }
>>>> >> +
>>>> >>    // Return leap_second values, and a bool indicating whether the
>>>> values are
>>>> >>    // current (true), or potentially out of date (false).
>>>> >>    pair<vector<leap_second>, bool>
>>>> >> @@ -1289,13 +1323,8 @@ namespace std::chrono
>>>> >>        (leap_second)1483228800, // 1 Jan 2017
>>>> >>      };
>>>> >>
>>>> >> -#if 0
>>>> >> -    // This optimization isn't valid if the file has additional
>>>> leap seconds
>>>> >> -    // defined since the library was compiled, but the system clock
>>>> has been
>>>> >> -    // set to a time before the hardcoded expiration date.
>>>> >> -    if (system_clock::now() < expires)
>>>> >> -      return {std::move(leaps), true};
>>>> >> -#endif
>>>> >> +    sys_seconds new_expires = expires;
>>>> >> +    bool read_new_leaps = true;
>>>> >>
>>>> >>  #ifndef TZDB_DISABLED
>>>> >>      if (ifstream ls{zoneinfo_file(leaps_file)})
>>>> >> @@ -1308,7 +1337,16 @@ namespace std::chrono
>>>> >>             // Leap  YEAR  MONTH  DAY  HH:MM:SS  CORR  R/S
>>>> >>
>>>> >>             if (!s.starts_with("Leap"))
>>>> >> -             continue;
>>>> >> +             {
>>>> >> +               if (s.starts_with("#expires "))
>>>> >> +                 __try {
>>>> >> +                   auto e =
>>>> sys_seconds(seconds(std::stoll(s.substr(9))));
>>>> >> +                   if (e > new_expires)
>>>> >> +                     new_expires = e;
>>>> >> +                 } __catch (const std::exception&) { /* ignore */ }
>>>> >
>>>> > Note that if reading the expires line fails, new_expires will be moved
>>>> > to build default (__expires), i.e. backward from already been
>>>> successfully loaded
>>>> > tzdb.
>>>>
>>>> Yes, that's wrong, thanks.
>>>>
>>>> >>
>>>> >> +               continue;
>>>> >> +             }
>>>> >> +
>>>> >>             istringstream li(std::move(s));
>>>> >>             li.exceptions(ios::failbit);
>>>> >>             li.ignore(4);
>>>> >> @@ -1339,12 +1377,40 @@ namespace std::chrono
>>>> >>                       leaps.push_back(ls);
>>>> >>                   }
>>>> >>               }
>>>> >> -           s = std::move(li).str(); // return storage to s
>>>> >> +           s = std::move(li).str(); // give allocated storage back
>>>> to s
>>>> >>           }
>>>> >> -       return {std::move(leaps), true};
>>>> >> +
>>>> >> +       read_new_leaps = true;
>>>> >>        }
>>>> >>  #endif
>>>> >> -    return {std::move(leaps), false};
>>>> >> +
>>>> >> +    if (leaps.size() > 27)
>>>> >
>>>> > And replaces this wit std::size(__leaps), they are defined in this
>>>> function.
>>>> > No need for magic number.
>>>> >>
>>>> >> +      {
>>>> >> +       // One or more new leap seconds have been introduced since
>>>> 2026.
>>>> >> +       // See comment on __detail::__leap_seconds_expiry() above.
>>>> >> +       // Object files compiled by older versions of GCC may not
>>>> have
>>>> >> +       // any leap seconds after 2017 in the hardcoded list in
>>>> <chrono>,
>>>> >> +       // so the expiry time that the header code uses must be
>>>> before the
>>>> >> +       // new leap seconds.
>>>> >> +       new_expires = leaps[27].date() - 1s;
>>>> >> +      }
>>>> >> +
>>>> >> +    // Should we update the global expiry time?
>>>> >> +    const sys_seconds old_expires =
>>>> __detail::__leap_seconds_expiry();
>>>> >> +
>>>> >> +    if (new_expires != old_expires)
>>>> >
>>>> > This should check if new_expires > old_expires to avoid moving
>>>> backward.
>>>> > case of tests or failures to load.
>>>> >>
>>>> >> +      {
>>>> >> +       expiry_type old_exp = old_expires.time_since_epoch().count();
>>>> >> +       expiry_type new_exp = new_expires.time_since_epoch().count();
>>>> >> +
>>>> >> +       // We don't care about this compare-exchange failing. If
>>>> another
>>>> >> +       // thread updated the expiry time, just use that value
>>>> instead.
>>>> >> +       leap_seconds_expiry.compare_exchange_strong(old_exp, new_exp,
>>>> >> +
>>>>  memory_order::release,
>>>> >
>>>> >  Why do you use release here? There is no memory writes (except
>>>> atomic)
>>>> > that we want to see in other threads.  After loading the value we may
>>>> continue
>>>> > to use static data.
>>>>
>>>> We might also *not* use the static data, and use
>>>> get_tzdb_list()->begin()->leapseconds. But that already imposes a
>>>> memory barrier, and there are no loads of the std::atomic that use
>>>> acquire ordering, to synchronize with this release. So I agree it can
>>>> be relaxed here.
>>>>
>>>>
>>>>
>>>> >>
>>>> >> +
>>>>  memory_order::relaxed);
>>>> >> +      }
>>>> >> +
>>>> >> +    return {std::move(leaps), read_new_leaps};
>>>> >>    }
>>>> >>
>>>> >>  #ifndef TZDB_DISABLED
>>>> >> diff --git a/libstdc++-v3/testsuite/std/time/tzdb/leap_seconds.cc
>>>> b/libstdc++-v3/testsuite/std/time/tzdb/leap_seconds.cc
>>>> >> index 5999635a89f0..24ef7d44858d 100644
>>>> >> --- a/libstdc++-v3/testsuite/std/time/tzdb/leap_seconds.cc
>>>> >> +++ b/libstdc++-v3/testsuite/std/time/tzdb/leap_seconds.cc
>>>> >> @@ -52,6 +52,7 @@ Leap  2016    Dec     31      23:59:60        +
>>>>    S
>>>> >>  # These are fake leap seconds for testing purposes:
>>>> >>  Leap   2093    Jun     30      23:59:59        -       S
>>>> >>  Leap   2093    Dec     31      23:59:60        +       S
>>>> >> +#expires 3991680000 (2096-06-28 00:00:00 UTC)
>>>> >>  )";
>>>> >>
>>>> >>    const auto& db = std::chrono::get_tzdb();
>>>> >> diff --git a/libstdc++-v3/testsuite/util/testsuite_abi.cc
>>>> b/libstdc++-v3/testsuite/util/testsuite_abi.cc
>>>> >> index 8fb38355cadd..4e80c5f184a6 100644
>>>> >> --- a/libstdc++-v3/testsuite/util/testsuite_abi.cc
>>>> >> +++ b/libstdc++-v3/testsuite/util/testsuite_abi.cc
>>>> >> @@ -217,6 +217,7 @@ check_version(symbol& test, bool added)
>>>> >>        known_versions.push_back("GLIBCXX_3.4.33");
>>>> >>        known_versions.push_back("GLIBCXX_3.4.34");
>>>> >>        known_versions.push_back("GLIBCXX_3.4.35");
>>>> >> +      known_versions.push_back("GLIBCXX_3.4.36");
>>>> >>        known_versions.push_back("GLIBCXX_LDBL_3.4.31");
>>>> >>        known_versions.push_back("GLIBCXX_IEEE128_3.4.29");
>>>> >>        known_versions.push_back("GLIBCXX_IEEE128_3.4.30");
>>>> >> @@ -260,7 +261,7 @@ check_version(symbol& test, bool added)
>>>> >>         test.version_status = symbol::incompatible;
>>>> >>
>>>> >>        // Check that added symbols are added in the latest
>>>> pre-release version.
>>>> >> -      bool latestp = (test.version_name == "GLIBCXX_3.4.35"
>>>> >> +      bool latestp = (test.version_name == "GLIBCXX_3.4.36"
>>>> >>                      || test.version_name == "CXXABI_1.3.17"
>>>> >>                      || test.version_name == "CXXABI_FLOAT128"
>>>> >>                      || test.version_name == "CXXABI_TM_1");
>>>> >> --
>>>> >> 2.54.0
>>>> >>
>>>>
>>>>

Reply via email to