LCOV - code coverage report
Current view: top level - 11/bits - functional_hash.h (source / functions) Hit Total Coverage
Test: jami-coverage-filtered.info Lines: 2 2 100.0 %
Date: 2025-08-24 09:11:10 Functions: 1 1 100.0 %

          Line data    Source code
       1             : // functional_hash.h header -*- C++ -*-
       2             : 
       3             : // Copyright (C) 2007-2021 Free Software Foundation, Inc.
       4             : //
       5             : // This file is part of the GNU ISO C++ Library.  This library is free
       6             : // software; you can redistribute it and/or modify it under the
       7             : // terms of the GNU General Public License as published by the
       8             : // Free Software Foundation; either version 3, or (at your option)
       9             : // any later version.
      10             : 
      11             : // This library is distributed in the hope that it will be useful,
      12             : // but WITHOUT ANY WARRANTY; without even the implied warranty of
      13             : // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      14             : // GNU General Public License for more details.
      15             : 
      16             : // Under Section 7 of GPL version 3, you are granted additional
      17             : // permissions described in the GCC Runtime Library Exception, version
      18             : // 3.1, as published by the Free Software Foundation.
      19             : 
      20             : // You should have received a copy of the GNU General Public License and
      21             : // a copy of the GCC Runtime Library Exception along with this program;
      22             : // see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
      23             : // <http://www.gnu.org/licenses/>.
      24             : 
      25             : /** @file bits/functional_hash.h
      26             :  *  This is an internal header file, included by other library headers.
      27             :  *  Do not attempt to use it directly. @headername{functional}
      28             :  */
      29             : 
      30             : #ifndef _FUNCTIONAL_HASH_H
      31             : #define _FUNCTIONAL_HASH_H 1
      32             : 
      33             : #pragma GCC system_header
      34             : 
      35             : #include <type_traits>
      36             : #include <bits/hash_bytes.h>
      37             : 
      38             : namespace std _GLIBCXX_VISIBILITY(default)
      39             : {
      40             : _GLIBCXX_BEGIN_NAMESPACE_VERSION
      41             : 
      42             :   /** @defgroup hashes Hashes
      43             :    *  @ingroup functors
      44             :    *
      45             :    *   Hashing functors taking a variable type and returning a @c std::size_t.
      46             :    *
      47             :    *  @{
      48             :    */
      49             : 
      50             :   template<typename _Result, typename _Arg>
      51             :     struct __hash_base
      52             :     {
      53             :       typedef _Result     result_type _GLIBCXX17_DEPRECATED;
      54             :       typedef _Arg      argument_type _GLIBCXX17_DEPRECATED;
      55             :     };
      56             : 
      57             :   /// Primary class template hash.
      58             :   template<typename _Tp>
      59             :     struct hash;
      60             : 
      61             :   template<typename _Tp, typename = void>
      62             :     struct __poison_hash
      63             :     {
      64             :       static constexpr bool __enable_hash_call = false;
      65             :     private:
      66             :       // Private rather than deleted to be non-trivially-copyable.
      67             :       __poison_hash(__poison_hash&&);
      68             :       ~__poison_hash();
      69             :     };
      70             : 
      71             :   template<typename _Tp>
      72             :     struct __poison_hash<_Tp, __void_t<decltype(hash<_Tp>()(declval<_Tp>()))>>
      73             :     {
      74             :       static constexpr bool __enable_hash_call = true;
      75             :     };
      76             : 
      77             :   // Helper struct for SFINAE-poisoning non-enum types.
      78             :   template<typename _Tp, bool = is_enum<_Tp>::value>
      79             :     struct __hash_enum
      80             :     {
      81             :     private:
      82             :       // Private rather than deleted to be non-trivially-copyable.
      83             :       __hash_enum(__hash_enum&&);
      84             :       ~__hash_enum();
      85             :     };
      86             : 
      87             :   // Helper struct for hash with enum types.
      88             :   template<typename _Tp>
      89             :     struct __hash_enum<_Tp, true> : public __hash_base<size_t, _Tp>
      90             :     {
      91             :       size_t
      92             :       operator()(_Tp __val) const noexcept
      93             :       {
      94             :        using __type = typename underlying_type<_Tp>::type;
      95             :        return hash<__type>{}(static_cast<__type>(__val));
      96             :       }
      97             :     };
      98             : 
      99             :   /// Primary class template hash, usable for enum types only.
     100             :   // Use with non-enum types still SFINAES.
     101             :   template<typename _Tp>
     102             :     struct hash : __hash_enum<_Tp>
     103             :     { };
     104             : 
     105             :   /// Partial specializations for pointer types.
     106             :   template<typename _Tp>
     107             :     struct hash<_Tp*> : public __hash_base<size_t, _Tp*>
     108             :     {
     109             :       size_t
     110             :       operator()(_Tp* __p) const noexcept
     111             :       { return reinterpret_cast<size_t>(__p); }
     112             :     };
     113             : 
     114             :   // Explicit specializations for integer types.
     115             : #define _Cxx_hashtable_define_trivial_hash(_Tp)         \
     116             :   template<>                                              \
     117             :     struct hash<_Tp> : public __hash_base<size_t, _Tp>  \
     118             :     {                                                   \
     119             :       size_t                                            \
     120             :       operator()(_Tp __val) const noexcept              \
     121             :       { return static_cast<size_t>(__val); }            \
     122             :     };
     123             : 
     124             :   /// Explicit specialization for bool.
     125             :   _Cxx_hashtable_define_trivial_hash(bool)
     126             : 
     127             :   /// Explicit specialization for char.
     128             :   _Cxx_hashtable_define_trivial_hash(char)
     129             : 
     130             :   /// Explicit specialization for signed char.
     131             :   _Cxx_hashtable_define_trivial_hash(signed char)
     132             : 
     133             :   /// Explicit specialization for unsigned char.
     134             :   _Cxx_hashtable_define_trivial_hash(unsigned char)
     135             : 
     136             :   /// Explicit specialization for wchar_t.
     137             :   _Cxx_hashtable_define_trivial_hash(wchar_t)
     138             : 
     139             : #ifdef _GLIBCXX_USE_CHAR8_T
     140             :   /// Explicit specialization for char8_t.
     141             :   _Cxx_hashtable_define_trivial_hash(char8_t)
     142             : #endif
     143             : 
     144             :   /// Explicit specialization for char16_t.
     145             :   _Cxx_hashtable_define_trivial_hash(char16_t)
     146             : 
     147             :   /// Explicit specialization for char32_t.
     148             :   _Cxx_hashtable_define_trivial_hash(char32_t)
     149             : 
     150             :   /// Explicit specialization for short.
     151             :   _Cxx_hashtable_define_trivial_hash(short)
     152             : 
     153             :   /// Explicit specialization for int.
     154             :   _Cxx_hashtable_define_trivial_hash(int)
     155             : 
     156             :   /// Explicit specialization for long.
     157             :   _Cxx_hashtable_define_trivial_hash(long)
     158             : 
     159             :   /// Explicit specialization for long long.
     160             :   _Cxx_hashtable_define_trivial_hash(long long)
     161             : 
     162             :   /// Explicit specialization for unsigned short.
     163             :   _Cxx_hashtable_define_trivial_hash(unsigned short)
     164             : 
     165             :   /// Explicit specialization for unsigned int.
     166             :   _Cxx_hashtable_define_trivial_hash(unsigned int)
     167             : 
     168             :   /// Explicit specialization for unsigned long.
     169             :   _Cxx_hashtable_define_trivial_hash(unsigned long)
     170             : 
     171             :   /// Explicit specialization for unsigned long long.
     172             :   _Cxx_hashtable_define_trivial_hash(unsigned long long)
     173             : 
     174             : #ifdef __GLIBCXX_TYPE_INT_N_0
     175             :   _Cxx_hashtable_define_trivial_hash(__GLIBCXX_TYPE_INT_N_0)
     176             :   _Cxx_hashtable_define_trivial_hash(__GLIBCXX_TYPE_INT_N_0 unsigned)
     177             : #endif
     178             : #ifdef __GLIBCXX_TYPE_INT_N_1
     179             :   _Cxx_hashtable_define_trivial_hash(__GLIBCXX_TYPE_INT_N_1)
     180             :   _Cxx_hashtable_define_trivial_hash(__GLIBCXX_TYPE_INT_N_1 unsigned)
     181             : #endif
     182             : #ifdef __GLIBCXX_TYPE_INT_N_2
     183             :   _Cxx_hashtable_define_trivial_hash(__GLIBCXX_TYPE_INT_N_2)
     184             :   _Cxx_hashtable_define_trivial_hash(__GLIBCXX_TYPE_INT_N_2 unsigned)
     185             : #endif
     186             : #ifdef __GLIBCXX_TYPE_INT_N_3
     187             :   _Cxx_hashtable_define_trivial_hash(__GLIBCXX_TYPE_INT_N_3)
     188             :   _Cxx_hashtable_define_trivial_hash(__GLIBCXX_TYPE_INT_N_3 unsigned)
     189             : #endif
     190             : 
     191             : #undef _Cxx_hashtable_define_trivial_hash
     192             : 
     193             :   struct _Hash_impl
     194             :   {
     195             :     static size_t
     196         745 :     hash(const void* __ptr, size_t __clength,
     197             :          size_t __seed = static_cast<size_t>(0xc70f6907UL))
     198         745 :     { return _Hash_bytes(__ptr, __clength, __seed); }
     199             : 
     200             :     template<typename _Tp>
     201             :       static size_t
     202             :       hash(const _Tp& __val)
     203             :       { return hash(&__val, sizeof(__val)); }
     204             : 
     205             :     template<typename _Tp>
     206             :       static size_t
     207             :       __hash_combine(const _Tp& __val, size_t __hash)
     208             :       { return hash(&__val, sizeof(__val), __hash); }
     209             :   };
     210             : 
     211             :   // A hash function similar to FNV-1a (see PR59406 for how it differs).
     212             :   struct _Fnv_hash_impl
     213             :   {
     214             :     static size_t
     215             :     hash(const void* __ptr, size_t __clength,
     216             :          size_t __seed = static_cast<size_t>(2166136261UL))
     217             :     { return _Fnv_hash_bytes(__ptr, __clength, __seed); }
     218             : 
     219             :     template<typename _Tp>
     220             :       static size_t
     221             :       hash(const _Tp& __val)
     222             :       { return hash(&__val, sizeof(__val)); }
     223             : 
     224             :     template<typename _Tp>
     225             :       static size_t
     226             :       __hash_combine(const _Tp& __val, size_t __hash)
     227             :       { return hash(&__val, sizeof(__val), __hash); }
     228             :   };
     229             : 
     230             :   /// Specialization for float.
     231             :   template<>
     232             :     struct hash<float> : public __hash_base<size_t, float>
     233             :     {
     234             :       size_t
     235             :       operator()(float __val) const noexcept
     236             :       {
     237             :         // 0 and -0 both hash to zero.
     238             :         return __val != 0.0f ? std::_Hash_impl::hash(__val) : 0;
     239             :       }
     240             :     };
     241             : 
     242             :   /// Specialization for double.
     243             :   template<>
     244             :     struct hash<double> : public __hash_base<size_t, double>
     245             :     {
     246             :       size_t
     247             :       operator()(double __val) const noexcept
     248             :       {
     249             :         // 0 and -0 both hash to zero.
     250             :         return __val != 0.0 ? std::_Hash_impl::hash(__val) : 0;
     251             :       }
     252             :     };
     253             : 
     254             :   /// Specialization for long double.
     255             :   template<>
     256             :     struct hash<long double>
     257             :     : public __hash_base<size_t, long double>
     258             :     {
     259             :       _GLIBCXX_PURE size_t
     260             :       operator()(long double __val) const noexcept;
     261             :     };
     262             : 
     263             : #if __cplusplus >= 201703L
     264             :   template<>
     265             :     struct hash<nullptr_t> : public __hash_base<size_t, nullptr_t>
     266             :     {
     267             :       size_t
     268             :       operator()(nullptr_t) const noexcept
     269             :       { return 0; }
     270             :     };
     271             : #endif
     272             : 
     273             :   /// @} group hashes
     274             : 
     275             :   // Hint about performance of hash functor. If not fast the hash-based
     276             :   // containers will cache the hash code.
     277             :   // Default behavior is to consider that hashers are fast unless specified
     278             :   // otherwise.
     279             :   template<typename _Hash>
     280             :     struct __is_fast_hash : public std::true_type
     281             :     { };
     282             : 
     283             :   template<>
     284             :     struct __is_fast_hash<hash<long double>> : public std::false_type
     285             :     { };
     286             : 
     287             : _GLIBCXX_END_NAMESPACE_VERSION
     288             : } // namespace
     289             : 
     290             : #endif // _FUNCTIONAL_HASH_H

Generated by: LCOV version 1.14