LCOV - code coverage report
Current view: top level - url/detail/impl - any_params_iter.hpp (source / functions) Coverage Total Hit Missed
Test: coverage_remapped.info Lines: 99.4 % 168 167 1
Test Date: 2026-02-25 21:00:01 Functions: 96.0 % 25 24 1

           TLA  Line data    Source code
       1                 : //
       2                 : // Copyright (c) 2019 Vinnie Falco (vinnie.falco@gmail.com)
       3                 : // Copyright (c) 2023 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_DETAIL_IMPL_ANY_PARAMS_ITER_HPP
      12                 : #define BOOST_URL_DETAIL_IMPL_ANY_PARAMS_ITER_HPP
      13                 : 
      14                 : #include <boost/url/encode.hpp>
      15                 : #include <boost/url/rfc/detail/charsets.hpp>
      16                 : #include <boost/assert.hpp>
      17                 : 
      18                 : namespace boost {
      19                 : namespace urls {
      20                 : namespace detail {
      21                 : 
      22                 : /*
      23                 :     When a string is transformed into a range of
      24                 :     params, the empty string becomes ambiguous:
      25                 :     it can be an empty range, or a range with
      26                 :     one param. The value `not_empty` is used on
      27                 :     construction to inform the transformation
      28                 :     that the empty string should be treated as
      29                 :     a one-element range. This simplifies
      30                 :     edit_params().
      31                 : */
      32                 : 
      33                 : //------------------------------------------------
      34                 : //
      35                 : // any_params_iter
      36                 : //
      37                 : //------------------------------------------------
      38                 : 
      39                 : inline
      40 HIT         147 : any_params_iter::
      41                 : ~any_params_iter() noexcept = default;
      42                 : 
      43                 : //------------------------------------------------
      44                 : //
      45                 : // query_iter
      46                 : //
      47                 : //------------------------------------------------
      48                 : 
      49                 : inline
      50              33 : query_string_iter::
      51                 : query_string_iter(
      52                 :     core::string_view s,
      53              33 :     bool ne) noexcept
      54                 :     : any_params_iter(
      55              33 :         s.empty() && ! ne, s)
      56                 : {
      57              33 :     rewind();
      58              33 : }
      59                 : 
      60                 : inline
      61                 : void
      62              44 : query_string_iter::
      63                 : rewind() noexcept
      64                 : {
      65              44 :     if(empty)
      66                 :     {
      67              22 :         at_end_ = true;
      68              22 :         return;
      69                 :     }
      70              22 :     p_ = s0.begin();
      71              22 :     if(! s0.empty())
      72                 :     {
      73                 :         auto pos =
      74              16 :             s0.find_first_of('&');
      75              16 :         if(pos != core::string_view::npos)
      76               4 :             n_ = pos;
      77                 :         else
      78              12 :             n_ = s0.size();
      79                 :     }
      80                 :     else
      81                 :     {
      82               6 :         n_ = 0;
      83                 :     }
      84              22 :     at_end_ = false;
      85                 : }
      86                 : 
      87                 : inline
      88                 : bool
      89              46 : query_string_iter::
      90                 : measure(
      91                 :     std::size_t& n) noexcept
      92                 : {
      93              46 :     if(at_end_)
      94              33 :         return false;
      95                 :     // When interacting with the query as
      96                 :     // an intact string, we do not treat
      97                 :     // the plus sign as an encoded space.
      98              13 :     encoding_opts opt;
      99              13 :     opt.space_as_plus = false;
     100              13 :     n += encoded_size(
     101                 :         core::string_view(p_, n_),
     102                 :         query_chars,
     103                 :         opt);
     104              13 :     increment();
     105              13 :     return true;
     106                 : }
     107                 : 
     108                 : inline
     109                 : void
     110              13 : query_string_iter::
     111                 : copy(
     112                 :     char*& dest,
     113                 :     char const* end) noexcept
     114                 : {
     115              13 :     BOOST_ASSERT(! at_end_);
     116                 :     // When interacting with the query as
     117                 :     // an intact string, we do not treat
     118                 :     // the plus sign as an encoded space.
     119              13 :     encoding_opts opt;
     120              13 :     opt.space_as_plus = false;
     121              13 :     dest += encode_unsafe(
     122                 :         dest,
     123              13 :         end - dest,
     124                 :         core::string_view(p_, n_),
     125                 :         query_chars,
     126                 :         opt);
     127              13 :     increment();
     128              13 : }
     129                 : 
     130                 : inline
     131                 : void
     132              26 : query_string_iter::
     133                 : increment() noexcept
     134                 : {
     135              26 :     p_ += n_;
     136              26 :     if(p_ == s0.end())
     137                 :     {
     138              22 :         at_end_ = true;
     139              22 :         return;
     140                 :     }
     141               4 :     ++p_;
     142               4 :     core::string_view s(p_, s0.end() - p_);
     143               4 :     auto pos = s.find_first_of('&');
     144               4 :     if(pos != core::string_view::npos)
     145 MIS           0 :         n_ = pos;
     146                 :     else
     147 HIT           4 :         n_ = s.size();
     148                 : }
     149                 : 
     150                 : //------------------------------------------------
     151                 : //
     152                 : // param_iter
     153                 : //
     154                 : //------------------------------------------------
     155                 : 
     156                 : inline
     157              24 : single_param_iter::
     158                 : single_param_iter(
     159                 :     param_view const& p,
     160              24 :     bool space_as_plus) noexcept
     161                 :     : any_params_iter(
     162                 :         false,
     163                 :         p.key,
     164                 :         p.value)
     165              24 :     , has_value_(p.has_value)
     166              24 :     , space_as_plus_(space_as_plus)
     167                 : {
     168              24 : }
     169                 : 
     170                 : inline
     171                 : void
     172              24 : single_param_iter::
     173                 : rewind() noexcept
     174                 : {
     175              24 :     at_end_ = false;
     176              24 : }
     177                 : 
     178                 : inline
     179                 : bool
     180              48 : single_param_iter::
     181                 : measure(std::size_t& n) noexcept
     182                 : {
     183              48 :     if(at_end_)
     184              24 :         return false;
     185              24 :     encoding_opts opt;
     186              24 :     opt.space_as_plus = space_as_plus_;
     187              24 :     n += encoded_size(
     188                 :         s0,
     189                 :         detail::param_key_chars,
     190                 :         opt);
     191              24 :     if(has_value_)
     192                 :     {
     193              24 :         ++n; // '='
     194              24 :         n += encoded_size(
     195                 :             s1,
     196                 :             detail::param_value_chars,
     197                 :             opt);
     198                 :     }
     199              24 :     at_end_ = true;
     200              24 :     return true;
     201                 : }
     202                 : 
     203                 : inline
     204                 : void
     205              24 : single_param_iter::
     206                 : copy(
     207                 :     char*& dest,
     208                 :     char const* end) noexcept
     209                 : {
     210              24 :     BOOST_ASSERT(! at_end_);
     211              24 :     encoding_opts opt;
     212              24 :     opt.space_as_plus = space_as_plus_;
     213              48 :     dest += encode(
     214                 :         dest,
     215              24 :         end - dest,
     216                 :         s0,
     217                 :         detail::param_key_chars,
     218                 :         opt);
     219              24 :     if (has_value_)
     220                 :     {
     221              24 :         *dest++ = '=';
     222              24 :         dest += encode(
     223                 :             dest,
     224              24 :             end - dest,
     225                 :             s1,
     226                 :             detail::param_value_chars,
     227                 :             opt);
     228                 :     }
     229              24 : }
     230                 : 
     231                 : //------------------------------------------------
     232                 : //
     233                 : // params_iter_base
     234                 : //
     235                 : //------------------------------------------------
     236                 : 
     237                 : inline
     238                 : void
     239              70 : params_iter_base::
     240                 : measure_impl(
     241                 :     std::size_t& n,
     242                 :     param_view const& p) noexcept
     243                 : {
     244              70 :     encoding_opts opt;
     245              70 :     opt.space_as_plus = space_as_plus_;
     246              70 :     n += encoded_size(
     247                 :         p.key,
     248                 :         detail::param_key_chars,
     249                 :         opt);
     250              70 :     if(p.has_value)
     251                 :     {
     252              58 :         ++n; // '='
     253              58 :         n += encoded_size(
     254                 :             p.value,
     255                 :             detail::param_value_chars,
     256                 :             opt);
     257                 :     }
     258              70 : }
     259                 : 
     260                 : inline
     261                 : void
     262              70 : params_iter_base::
     263                 : copy_impl(
     264                 :     char*& dest,
     265                 :     char const* end,
     266                 :     param_view const& p) noexcept
     267                 : {
     268              70 :     encoding_opts opt;
     269              70 :     opt.space_as_plus = space_as_plus_;
     270             140 :     dest += encode(
     271                 :         dest,
     272              70 :         end - dest,
     273                 :         p.key,
     274                 :         detail::param_key_chars,
     275                 :         opt);
     276              70 :     if(p.has_value)
     277                 :     {
     278              58 :         *dest++ = '=';
     279              58 :         dest += encode(
     280                 :             dest,
     281              58 :             end - dest,
     282                 :             p.value,
     283                 :             detail::param_value_chars,
     284                 :             opt);
     285                 :     }
     286              70 : }
     287                 : 
     288                 : //------------------------------------------------
     289                 : //
     290                 : // param_encoded_iter
     291                 : //
     292                 : //------------------------------------------------
     293                 : 
     294                 : inline
     295              12 : param_encoded_iter::
     296                 : param_encoded_iter(
     297              12 :     param_pct_view const& p) noexcept
     298                 :     : any_params_iter(
     299                 :         false,
     300                 :         p.key,
     301                 :         p.value)
     302              12 :     , has_value_(p.has_value)
     303                 : {
     304              12 : }
     305                 : 
     306                 : inline
     307                 : void
     308              12 : param_encoded_iter::
     309                 : rewind() noexcept
     310                 : {
     311              12 :     at_end_ = false;
     312              12 : }
     313                 : 
     314                 : inline
     315                 : bool
     316              24 : param_encoded_iter::
     317                 : measure(std::size_t& n) noexcept
     318                 : {
     319              24 :     if(at_end_)
     320              12 :         return false;
     321              12 :     n += detail::re_encoded_size_unsafe(
     322                 :         s0,
     323                 :         detail::param_key_chars);
     324              12 :     if(has_value_)
     325              12 :         n += detail::re_encoded_size_unsafe(
     326                 :             s1,
     327              12 :             detail::param_value_chars) + 1; // for '='
     328              12 :     at_end_ = true;
     329              12 :     return true;
     330                 : }
     331                 : 
     332                 : inline
     333                 : void
     334              12 : param_encoded_iter::
     335                 : copy(
     336                 :     char*& dest,
     337                 :     char const* end) noexcept
     338                 : {
     339              12 :     detail::re_encode_unsafe(
     340                 :         dest,
     341                 :         end,
     342                 :         s0,
     343                 :         detail::param_key_chars);
     344              12 :     if(has_value_)
     345                 :     {
     346              12 :         *dest++ = '=';
     347              12 :         detail::re_encode_unsafe(
     348                 :             dest,
     349                 :             end,
     350                 :             s1,
     351                 :             detail::param_value_chars);
     352                 :     }
     353              12 : }
     354                 : 
     355                 : 
     356                 : //------------------------------------------------
     357                 : //
     358                 : // params_encoded_iter_base
     359                 : //
     360                 : //------------------------------------------------
     361                 : 
     362                 : inline
     363                 : void
     364              51 : params_encoded_iter_base::
     365                 : measure_impl(
     366                 :     std::size_t& n,
     367                 :     param_view const& p) noexcept
     368                 : {
     369              51 :     n += detail::re_encoded_size_unsafe(
     370                 :         p.key,
     371                 :         detail::param_key_chars);
     372              51 :     if(p.has_value)
     373              42 :         n += detail::re_encoded_size_unsafe(
     374                 :             p.value,
     375              42 :             detail::param_value_chars) + 1; // for '='
     376              51 : }
     377                 : 
     378                 : inline
     379                 : void
     380              51 : params_encoded_iter_base::
     381                 : copy_impl(
     382                 :     char*& dest,
     383                 :     char const* end,
     384                 :     param_view const& p) noexcept
     385                 : {
     386              51 :     detail::re_encode_unsafe(
     387                 :         dest,
     388                 :         end,
     389                 :         p.key,
     390                 :         detail::param_key_chars);
     391              51 :     if(p.has_value)
     392                 :     {
     393              42 :         *dest++ = '=';
     394              42 :         detail::re_encode_unsafe(
     395                 :             dest,
     396                 :             end,
     397                 :             p.value,
     398                 :             detail::param_value_chars);
     399                 :     }
     400              51 : }
     401                 : 
     402                 : //------------------------------------------------
     403                 : //
     404                 : // param_value_iter
     405                 : //
     406                 : //------------------------------------------------
     407                 : 
     408                 : inline
     409                 : void
     410               9 : param_value_iter::
     411                 : rewind() noexcept
     412                 : {
     413               9 :     at_end_ = false;
     414               9 : }
     415                 : 
     416                 : inline
     417                 : bool
     418              18 : param_value_iter::
     419                 : measure(
     420                 :     std::size_t& n) noexcept
     421                 : {
     422              18 :     if(at_end_)
     423               9 :         return false;
     424               9 :     n += nk_; // skip key
     425               9 :     if(has_value_)
     426                 :     {
     427               5 :         encoding_opts opt;
     428               5 :         opt.space_as_plus = false;
     429               5 :         n += encoded_size(
     430                 :             s0,
     431                 :             detail::param_value_chars,
     432               5 :             opt) + 1; // for '='
     433                 :     }
     434               9 :     at_end_ = true;
     435               9 :     return true;
     436                 : }
     437                 : 
     438                 : inline
     439                 : void
     440               9 : param_value_iter::
     441                 : copy(char*& it, char const* end) noexcept
     442                 : {
     443               9 :     it += nk_; // skip key
     444               9 :     if(! has_value_)
     445               4 :         return;
     446               5 :     *it++ = '=';
     447               5 :     encoding_opts opt;
     448               5 :     opt.space_as_plus = false;
     449               5 :     it += encode(
     450                 :         it,
     451               5 :         end - it,
     452                 :         s0,
     453                 :         detail::param_value_chars,
     454                 :         opt);
     455                 : }
     456                 : 
     457                 : //------------------------------------------------
     458                 : //
     459                 : // param_encoded_value_iter
     460                 : //
     461                 : //------------------------------------------------
     462                 : 
     463                 : inline
     464                 : void
     465               8 : param_encoded_value_iter::
     466                 : rewind() noexcept
     467                 : {
     468               8 :     at_end_ = false;
     469               8 : }
     470                 : 
     471                 : inline
     472                 : bool
     473              16 : param_encoded_value_iter::
     474                 : measure(
     475                 :     std::size_t& n) noexcept
     476                 : {
     477              16 :     if(at_end_)
     478               8 :         return false;
     479               8 :     n += nk_; // skip key
     480               8 :     if(has_value_)
     481                 :     {
     482               4 :         n += detail::re_encoded_size_unsafe(
     483                 :             s0,
     484               4 :             detail::param_value_chars) + 1; // for '='
     485                 :     }
     486               8 :     at_end_ = true;
     487               8 :     return true;
     488                 : }
     489                 : 
     490                 : inline
     491                 : void
     492               8 : param_encoded_value_iter::
     493                 : copy(
     494                 :     char*& dest,
     495                 :     char const* end) noexcept
     496                 : {
     497               8 :     dest += nk_; // skip key
     498               8 :     if(! has_value_)
     499               4 :         return;
     500               4 :     *dest++ = '=';
     501               4 :     detail::re_encode_unsafe(
     502                 :         dest,
     503                 :         end,
     504                 :         s0,
     505                 :         detail::param_value_chars);
     506                 : }
     507                 : 
     508                 : } // detail
     509                 : } // urls
     510                 : } // boost
     511                 : 
     512                 : #endif
        

Generated by: LCOV version 2.3