LCOV - code coverage report
Current view: top level - boost/url/grammar/detail - ci_string.hpp (source / functions) Hit Total Coverage
Test: coverage_filtered.info Lines: 24 25 96.0 %
Date: 2024-03-12 19:37:18 Functions: 6 7 85.7 %

          Line data    Source code
       1             : //
       2             : // Copyright (c) 2016-2019 Vinnie Falco (vinnie dot falco at gmail dot com)
       3             : // Copyright (c) 2022 Alan de Freitas (alandefreitas@gmail.com)
       4             : //
       5             : // Distributed under the Boost Software License, Version 1.0. (See accompanying
       6             : // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
       7             : //
       8             : // Official repository: https://github.com/boostorg/url
       9             : //
      10             : 
      11             : #ifndef BOOST_URL_GRAMMAR_DETAIL_CI_STRING_HPP
      12             : #define BOOST_URL_GRAMMAR_DETAIL_CI_STRING_HPP
      13             : 
      14             : #include <boost/core/detail/string_view.hpp>
      15             : #include <boost/assert.hpp>
      16             : #include <cstdint>
      17             : #include <iterator>
      18             : #include <type_traits>
      19             : 
      20             : namespace boost {
      21             : namespace urls {
      22             : namespace grammar {
      23             : namespace detail {
      24             : 
      25             : template<class T, class = void>
      26             : struct is_char_iter : std::false_type {};
      27             : 
      28             : template<class T>
      29             : struct is_char_iter<T, void_t<
      30             :     decltype(std::declval<char&>() =
      31             :         *std::declval<T const&>()),
      32             :     decltype(std::declval<T&>() =
      33             :         ++std::declval<T&>()),
      34             :     decltype(std::declval<bool&>() =
      35             :         std::declval<T const&>() ==
      36             :         std::declval<T const&>())
      37             :     > > : std::integral_constant<bool,
      38             :         std::is_copy_constructible<T>::value>
      39             : {
      40             : };
      41             : 
      42             : template<class T, class = void>
      43             : struct is_char_range : std::false_type {};
      44             : 
      45             : template<class T>
      46             : struct is_char_range<T, void_t<
      47             :     decltype(std::declval<T const&>().begin()),
      48             :     decltype(std::declval<T const&>().end())
      49             :     > > : std::integral_constant<bool,
      50             :         is_char_iter<decltype(
      51             :             std::declval<T const&>(
      52             :                 ).begin())>::value &&
      53             :         is_char_iter<decltype(
      54             :             std::declval<T const&>(
      55             :                 ).end())>::value>
      56             : {
      57             : };
      58             : 
      59             : template<class T>
      60             : struct type_id_impl
      61             : {
      62             :     static
      63             :     constexpr
      64             :     char cid = 0;
      65             : };
      66             : 
      67             : template<class T>
      68             : constexpr
      69             : char
      70             : type_id_impl<T>::cid;
      71             : 
      72             : template<class T>
      73             : constexpr
      74             : std::uintptr_t
      75         756 : type_id() noexcept
      76             : {
      77             :     return std::uintptr_t(
      78         756 :         &type_id_impl<T>::cid);
      79             : }
      80             : 
      81             : //------------------------------------------------
      82             : 
      83             : constexpr
      84             : char
      85       23451 : to_lower(char c) noexcept
      86             : {
      87             :     return
      88       22249 :       (c >= 'A' &&
      89             :        c <= 'Z')
      90         488 :         ? c + 'a' - 'A'
      91       45700 :         : c;
      92             : }
      93             : 
      94             : constexpr
      95             : char
      96         189 : to_upper(char c) noexcept
      97             : {
      98             :     return
      99          85 :       (c >= 'a' &&
     100             :        c <= 'z')
     101          85 :         ? c - ('a' - 'A')
     102         274 :         : c;
     103             : }
     104             : 
     105             : //------------------------------------------------
     106             : 
     107             : template<class S0, class S1>
     108             : auto
     109         252 : ci_is_equal(
     110             :     S0 const& s0,
     111             :     S1 const& s1) ->
     112             :         typename std::enable_if<
     113             :             ! std::is_convertible<
     114             :                 S0, core::string_view>::value ||
     115             :             ! std::is_convertible<
     116             :                 S1, core::string_view>::value,
     117             :         bool>::type
     118             : {
     119             : /*  If you get a compile error here, it
     120             :     means that a range you passed does
     121             :     not meet the requirements stated
     122             :     in the documentation.
     123             : */
     124             :     static_assert(
     125             :         is_char_range<S0>::value,
     126             :         "Type requirements not met");
     127             :     static_assert(
     128             :         is_char_range<S1>::value,
     129             :         "Type requirements not met");
     130             : 
     131             :     // Arguments are sorted by type to
     132             :     // reduce the number of function
     133             :     // template instantiations. This
     134             :     // works because:
     135             :     //
     136             :     // ci_is_equal(s0,s1) == ci_is_equal(s1,s0)
     137             :     //
     138         126 :     BOOST_ASSERT(
     139             :         detail::type_id<S0>() <=
     140             :         detail::type_id<S1>());
     141             : 
     142         252 :     auto it0 = s0.begin();
     143         252 :     auto it1 = s1.begin();
     144         252 :     auto const end0 = s0.end();
     145         252 :     auto const end1 = s1.end();
     146             :     for(;;)
     147             :     {
     148         352 :         if(it0 == end0)
     149          64 :             return it1 == end1;
     150         288 :         if(it1 == end1)
     151           0 :             return false;
     152         576 :         if( to_lower(*it0) !=
     153         288 :             to_lower(*it1))
     154         188 :             return false;
     155         100 :         ++it0;
     156         100 :         ++it1;
     157             :     }
     158             : }
     159             : 
     160             : //------------------------------------------------
     161             : 
     162             : BOOST_URL_DECL
     163             : bool
     164             : ci_is_equal(
     165             :     core::string_view s0,
     166             :     core::string_view s1) noexcept;
     167             : 
     168             : BOOST_URL_DECL
     169             : bool
     170             : ci_is_less(
     171             :     core::string_view s0,
     172             :     core::string_view s1) noexcept;
     173             : 
     174             : } // detail
     175             : } // grammar
     176             : } // urls
     177             : } // boost
     178             : 
     179             : #endif

Generated by: LCOV version 1.15