LCOV - code coverage report
Current view: top level - tests - catch_option_info_ref.cpp (source / functions) Hit Total Coverage
Test: coverage.info Lines: 850 860 98.8 %
Date: 2021-09-08 17:05:25 Functions: 5 5 100.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : // Copyright (c) 2006-2021  Made to Order Software Corp.  All Rights Reserved
       2             : //
       3             : // https://snapwebsites.org/project/advgetopt
       4             : // contact@m2osw.com
       5             : //
       6             : // This program is free software; you can redistribute it and/or modify
       7             : // it under the terms of the GNU General Public License as published by
       8             : // the Free Software Foundation; either version 2 of the License, or
       9             : // (at your option) any later version.
      10             : //
      11             : // This program 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             : // You should have received a copy of the GNU General Public License along
      17             : // with this program; if not, write to the Free Software Foundation, Inc.,
      18             : // 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
      19             : 
      20             : // self
      21             : //
      22             : #include    "catch_main.h"
      23             : 
      24             : 
      25             : // advgetopt lib
      26             : //
      27             : #include    <advgetopt/exception.h>
      28             : 
      29             : 
      30             : // libutf8 lib
      31             : //
      32             : #include    <libutf8/libutf8.h>
      33             : 
      34             : 
      35             : // C++ lib
      36             : //
      37             : #include    <fstream>
      38             : 
      39             : 
      40             : // last include
      41             : //
      42             : #include    <snapdev/poison.h>
      43             : 
      44             : 
      45             : 
      46             : 
      47             : 
      48          29 : CATCH_TEST_CASE("option_info_ref", "[option_info][valid][reference]")
      49             : {
      50          54 :     CATCH_START_SECTION("Option info reference")
      51             :     {
      52           1 :         advgetopt::option const options[] =
      53             :         {
      54             :             advgetopt::define_option(
      55             :                   advgetopt::Name("reference")
      56             :                 , advgetopt::ShortName('r')
      57             :                 , advgetopt::Flags(advgetopt::command_flags<
      58             :                               advgetopt::GETOPT_FLAG_REQUIRED
      59             :                             | advgetopt::GETOPT_FLAG_DYNAMIC_CONFIGURATION>())
      60             :                 , advgetopt::Help("test reference.")
      61             :             ),
      62             :             advgetopt::define_option(
      63             :                   advgetopt::Name("verbose")
      64             :                 , advgetopt::ShortName('v')
      65             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
      66             :                 , advgetopt::Help("make it all verbose.")
      67             :             ),
      68             :             advgetopt::end_options()
      69             :         };
      70             : 
      71           1 :         advgetopt::options_environment environment_options;
      72           1 :         environment_options.f_project_name = "unittest";
      73           1 :         environment_options.f_options = options;
      74           1 :         environment_options.f_help_header = "Usage: verify references";
      75             : 
      76           1 :         char const * cargv[] =
      77             :         {
      78             :             "/usr/bin/arguments",
      79             :             "--reference",
      80             :             "1001",
      81             :             "--verbose",
      82             :             "loud",
      83             :             nullptr
      84             :         };
      85           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
      86           1 :         char ** argv = const_cast<char **>(cargv);
      87             : 
      88           2 :         advgetopt::getopt opt(environment_options, argc, argv);
      89             : 
      90             :         // check that the result is valid
      91             : 
      92             :         // verify both parameters the "normal" way
      93           1 :         CATCH_REQUIRE(opt.get_option("reference") != nullptr);
      94           1 :         CATCH_REQUIRE(opt.size("reference") == 1);
      95           1 :         CATCH_REQUIRE(opt.get_string("reference") == "1001");
      96             : 
      97           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
      98           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
      99           1 :         CATCH_REQUIRE(opt.get_string("verbose") == "loud");
     100             : 
     101             :         // check the read-only verbose which does not create a reference
     102           1 :         CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["reference"] == "1001");
     103           1 :         CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["verbose"] == "loud");
     104             : 
     105           2 :         std::string const reference_value(const_cast<advgetopt::getopt const &>(opt)["reference"]);
     106           1 :         CATCH_REQUIRE(reference_value == "1001");
     107           2 :         std::string const verbose_value(const_cast<advgetopt::getopt const &>(opt)["verbose"]);
     108           1 :         CATCH_REQUIRE(verbose_value == "loud");
     109             : 
     110             :         // get a reference
     111           2 :         advgetopt::option_info_ref reference_ref(opt["reference"]);
     112           2 :         advgetopt::option_info_ref verbose_ref(opt["verbose"]);
     113             : 
     114           1 :         CATCH_REQUIRE_FALSE(reference_ref.empty());
     115           1 :         CATCH_REQUIRE_FALSE(verbose_ref.empty());
     116             : 
     117           1 :         CATCH_REQUIRE(reference_ref.length() == 4);
     118           1 :         CATCH_REQUIRE(reference_ref.size() == 4);
     119           1 :         CATCH_REQUIRE(verbose_ref.length() == 4);
     120           1 :         CATCH_REQUIRE(verbose_ref.size() == 4);
     121             : 
     122           1 :         CATCH_REQUIRE(reference_ref == reference_ref);
     123           1 :         CATCH_REQUIRE_FALSE(reference_ref != reference_ref);
     124           1 :         CATCH_REQUIRE_FALSE(reference_ref < reference_ref);
     125           1 :         CATCH_REQUIRE(reference_ref <= reference_ref);
     126           1 :         CATCH_REQUIRE_FALSE(reference_ref > reference_ref);
     127           1 :         CATCH_REQUIRE(reference_ref >= reference_ref);
     128             : 
     129           1 :         CATCH_REQUIRE_FALSE(reference_ref == verbose_ref);
     130           1 :         CATCH_REQUIRE(reference_ref != verbose_ref);
     131           1 :         CATCH_REQUIRE(reference_ref < verbose_ref);
     132           1 :         CATCH_REQUIRE(reference_ref <= verbose_ref);
     133           1 :         CATCH_REQUIRE_FALSE(reference_ref > verbose_ref);
     134           1 :         CATCH_REQUIRE_FALSE(reference_ref >= verbose_ref);
     135             : 
     136           1 :         reference_ref += "3";
     137           1 :         CATCH_REQUIRE(reference_ref == "10013");
     138           1 :         CATCH_REQUIRE("10013" == reference_ref);
     139           1 :         CATCH_REQUIRE(reference_ref != "17013");
     140           1 :         CATCH_REQUIRE("10413" != reference_ref);
     141           1 :         CATCH_REQUIRE(reference_ref < "20");
     142           1 :         CATCH_REQUIRE("1001" < reference_ref);
     143           1 :         CATCH_REQUIRE(reference_ref <= "10013");
     144           1 :         CATCH_REQUIRE("10013" <= reference_ref);
     145           1 :         CATCH_REQUIRE(reference_ref > "%");
     146           1 :         CATCH_REQUIRE("10014" > reference_ref);
     147           1 :         CATCH_REQUIRE(reference_ref >= "!");
     148           1 :         CATCH_REQUIRE("10013" >= reference_ref);
     149             : 
     150           2 :         std::string const new_value("zero");
     151           1 :         reference_ref = new_value;
     152           1 :         CATCH_REQUIRE(reference_ref == reference_ref);
     153           1 :         CATCH_REQUIRE(reference_ref == new_value);
     154           1 :         CATCH_REQUIRE(new_value == reference_ref);
     155           1 :         CATCH_REQUIRE_FALSE(reference_ref != new_value);
     156           1 :         CATCH_REQUIRE_FALSE(new_value != reference_ref);
     157           1 :         CATCH_REQUIRE_FALSE(reference_ref < new_value);
     158           1 :         CATCH_REQUIRE_FALSE(new_value < reference_ref);
     159           1 :         CATCH_REQUIRE(reference_ref <= new_value);
     160           1 :         CATCH_REQUIRE(new_value <= reference_ref);
     161           1 :         CATCH_REQUIRE_FALSE(reference_ref > new_value);
     162           1 :         CATCH_REQUIRE_FALSE(new_value > reference_ref);
     163           1 :         CATCH_REQUIRE(reference_ref >= new_value);
     164           1 :         CATCH_REQUIRE(new_value >= reference_ref);
     165             : 
     166           1 :         reference_ref += verbose_ref;
     167           1 :         CATCH_REQUIRE(reference_ref == reference_ref);
     168           1 :         CATCH_REQUIRE(reference_ref == "zeroloud");
     169           1 :         CATCH_REQUIRE("zeroloud" == reference_ref);
     170           1 :         CATCH_REQUIRE_FALSE(reference_ref != "zeroloud");
     171           1 :         CATCH_REQUIRE_FALSE("zeroloud" != reference_ref);
     172           1 :         CATCH_REQUIRE_FALSE(reference_ref < "zeroloud");
     173           1 :         CATCH_REQUIRE_FALSE("zeroloud" < reference_ref);
     174           1 :         CATCH_REQUIRE(reference_ref <= "zeroloud");
     175           1 :         CATCH_REQUIRE("zeroloud" <= reference_ref);
     176           1 :         CATCH_REQUIRE_FALSE(reference_ref > "zeroloud");
     177           1 :         CATCH_REQUIRE_FALSE("zeroloud" > reference_ref);
     178           1 :         CATCH_REQUIRE(reference_ref >= "zeroloud");
     179           1 :         CATCH_REQUIRE("zeroloud" >= reference_ref);
     180             : 
     181           1 :         reference_ref += '?';
     182           1 :         CATCH_REQUIRE(reference_ref == reference_ref);
     183           1 :         CATCH_REQUIRE(reference_ref == "zeroloud?");
     184           1 :         CATCH_REQUIRE("zeroloud?" == reference_ref);
     185           1 :         CATCH_REQUIRE_FALSE(reference_ref != "zeroloud?");
     186           1 :         CATCH_REQUIRE_FALSE("zeroloud?" != reference_ref);
     187           1 :         CATCH_REQUIRE_FALSE(reference_ref < "zeroloud?");
     188           1 :         CATCH_REQUIRE_FALSE("zeroloud?" < reference_ref);
     189           1 :         CATCH_REQUIRE(reference_ref <= "zeroloud?");
     190           1 :         CATCH_REQUIRE("zeroloud?" <= reference_ref);
     191           1 :         CATCH_REQUIRE_FALSE(reference_ref > "zeroloud?");
     192           1 :         CATCH_REQUIRE_FALSE("zeroloud?" > reference_ref);
     193           1 :         CATCH_REQUIRE(reference_ref >= "zeroloud?");
     194           1 :         CATCH_REQUIRE("zeroloud?" >= reference_ref);
     195             : 
     196           1 :         CATCH_REQUIRE_FALSE(reference_ref + "more" == reference_ref);
     197           1 :         CATCH_REQUIRE(reference_ref + "more" == "zeroloud?more");
     198           1 :         CATCH_REQUIRE("zeroloud?more" == reference_ref + "more");
     199           1 :         CATCH_REQUIRE(reference_ref + std::string("extra") == "zeroloud?extra");
     200           1 :         CATCH_REQUIRE("zeroloud?extra" == reference_ref + std::string("extra"));
     201           1 :         CATCH_REQUIRE(reference_ref + verbose_ref == "zeroloud?loud");
     202           1 :         CATCH_REQUIRE("zeroloud?loud" == reference_ref + verbose_ref);
     203             : 
     204           1 :         CATCH_REQUIRE_FALSE(reference_ref + '+' == reference_ref);
     205           1 :         CATCH_REQUIRE(reference_ref + '+' == "zeroloud?+");
     206           1 :         CATCH_REQUIRE("zeroloud?+" == reference_ref + '+');
     207           1 :         CATCH_REQUIRE('+' + reference_ref == "+zeroloud?");
     208           1 :         CATCH_REQUIRE("+zeroloud?" == '+' + reference_ref);
     209             : 
     210           1 :         CATCH_REQUIRE(reference_ref + '\0' == reference_ref);
     211           1 :         CATCH_REQUIRE(reference_ref + '\0' == "zeroloud?");
     212           1 :         CATCH_REQUIRE("zeroloud?" == reference_ref + '\0');
     213           1 :         CATCH_REQUIRE('\0' + reference_ref == "zeroloud?");
     214           1 :         CATCH_REQUIRE("zeroloud?" == '\0' + reference_ref);
     215             : 
     216           1 :         char32_t c(rand() % 0xFFFFF + ' ');
     217           1 :         if(c >= 0xD800 && c < 0xE000)
     218             :         {
     219           0 :             c += 0x800;
     220             :         }
     221             : 
     222           1 :         CATCH_REQUIRE_FALSE(reference_ref + c == reference_ref);
     223           1 :         CATCH_REQUIRE(reference_ref + c == "zeroloud?" + libutf8::to_u8string(c));
     224           1 :         CATCH_REQUIRE("zeroloud?" + libutf8::to_u8string(c) == reference_ref + c);
     225           1 :         CATCH_REQUIRE(c + reference_ref == libutf8::to_u8string(c) + "zeroloud?");
     226           1 :         CATCH_REQUIRE(libutf8::to_u8string(c) + "zeroloud?" == c + reference_ref);
     227             : 
     228           1 :         c = U'\0';
     229             : 
     230           1 :         CATCH_REQUIRE(reference_ref + c == reference_ref);
     231           1 :         CATCH_REQUIRE(reference_ref + c == "zeroloud?");
     232           1 :         CATCH_REQUIRE("zeroloud?" == reference_ref + c);
     233           1 :         CATCH_REQUIRE(c + reference_ref == "zeroloud?");
     234           1 :         CATCH_REQUIRE("zeroloud?" == c + reference_ref);
     235             : 
     236           1 :         reference_ref = "reset";
     237           1 :         CATCH_REQUIRE('"' + reference_ref + '"' == "\"reset\"");
     238           1 :         CATCH_REQUIRE('\0' + reference_ref + '\0' == std::string("reset") + '\0');  // we do not control the second + here...
     239           1 :         CATCH_REQUIRE(c + reference_ref + c == "reset");
     240             : 
     241           1 :         reference_ref = verbose_ref;
     242           1 :         CATCH_REQUIRE('(' + reference_ref + ')' == "(loud)");
     243           1 :         CATCH_REQUIRE('\0' + reference_ref + '\0' == std::string("loud") + '\0');  // we do not control the second + here...
     244           1 :         CATCH_REQUIRE(c + reference_ref + c == "loud");
     245             : 
     246           2 :         std::string const secret("secret");
     247           1 :         reference_ref += ' ';
     248           1 :         reference_ref += secret;
     249           1 :         CATCH_REQUIRE('>' + reference_ref + '<' == ">loud secret<");
     250           1 :         char32_t const left(0x1D233);
     251           1 :         char32_t const right(0x1D234);
     252           1 :         CATCH_REQUIRE((left + (reference_ref + right)) == "\xF0\x9D\x88\xB3loud secret\xF0\x9D\x88\xB4");
     253           1 :         CATCH_REQUIRE(((left + reference_ref) + right) == "\xF0\x9D\x88\xB3loud secret\xF0\x9D\x88\xB4");
     254           1 :         CATCH_REQUIRE(c == U'\0');
     255           1 :         CATCH_REQUIRE((c + (reference_ref + c)) == "loud secret");
     256           1 :         CATCH_REQUIRE(((c + reference_ref) + c) == "loud secret");
     257           1 :         CATCH_REQUIRE(reference_ref + new_value == "loud secretzero");
     258           1 :         CATCH_REQUIRE(new_value + reference_ref == "zeroloud secret");
     259           1 :         CATCH_REQUIRE(reference_ref + " more" == "loud secret more");
     260           1 :         CATCH_REQUIRE("less " + reference_ref == "less loud secret");
     261             : 
     262           1 :         reference_ref = '#';
     263           1 :         CATCH_REQUIRE(reference_ref == "#");
     264           1 :         reference_ref += '\0';
     265           1 :         CATCH_REQUIRE(reference_ref == "#");
     266           1 :         reference_ref += c;
     267           1 :         CATCH_REQUIRE(reference_ref == "#");
     268             : 
     269           1 :         reference_ref = '\0';
     270           1 :         CATCH_REQUIRE(reference_ref == "");
     271             : 
     272           1 :         reference_ref = '?';
     273           1 :         CATCH_REQUIRE(reference_ref == "?");
     274           1 :         reference_ref += '\0';
     275           1 :         CATCH_REQUIRE(reference_ref == "?");
     276           1 :         reference_ref += c;
     277           1 :         CATCH_REQUIRE(reference_ref == "?");
     278             : 
     279           1 :         reference_ref = c;
     280           1 :         CATCH_REQUIRE(reference_ref == "");
     281             :     }
     282             :     CATCH_END_SECTION()
     283             : 
     284          54 :     CATCH_START_SECTION("Non-existant reference")
     285             :     {
     286           1 :         advgetopt::option const options[] =
     287             :         {
     288             :             advgetopt::define_option(
     289             :                   advgetopt::Name("reference")
     290             :                 , advgetopt::ShortName('r')
     291             :                 , advgetopt::Flags(advgetopt::command_flags<
     292             :                               advgetopt::GETOPT_FLAG_REQUIRED
     293             :                             | advgetopt::GETOPT_FLAG_DYNAMIC_CONFIGURATION>())
     294             :                 , advgetopt::Help("test reference.")
     295             :             ),
     296             :             advgetopt::define_option(
     297             :                   advgetopt::Name("verbose")
     298             :                 , advgetopt::ShortName('v')
     299             :                 , advgetopt::Flags(advgetopt::command_flags<
     300             :                               advgetopt::GETOPT_FLAG_REQUIRED
     301             :                             | advgetopt::GETOPT_FLAG_DYNAMIC_CONFIGURATION>())
     302             :                 , advgetopt::Help("make it all verbose.")
     303             :             ),
     304             :             advgetopt::end_options()
     305             :         };
     306             : 
     307           1 :         advgetopt::options_environment environment_options;
     308           1 :         environment_options.f_project_name = "unittest";
     309           1 :         environment_options.f_options = options;
     310           1 :         environment_options.f_help_header = "Usage: verify references";
     311             : 
     312           1 :         char const * cargv[] =
     313             :         {
     314             :             "/usr/bin/arguments",
     315             :             "--reference",
     316             :             "1001",
     317             :             "--verbose",
     318             :             "loud",
     319             :             nullptr
     320             :         };
     321           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     322           1 :         char ** argv = const_cast<char **>(cargv);
     323             : 
     324           2 :         advgetopt::getopt opt(environment_options, argc, argv);
     325             : 
     326             :         // check that the result is valid
     327             : 
     328             :         // verify both parameters the "normal" way
     329           1 :         CATCH_REQUIRE(opt.get_option("reference") != nullptr);
     330           1 :         CATCH_REQUIRE(opt.size("reference") == 1);
     331           1 :         CATCH_REQUIRE(opt.get_string("reference") == "1001");
     332             : 
     333           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
     334           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
     335           1 :         CATCH_REQUIRE(opt.get_string("verbose") == "loud");
     336             : 
     337           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     338             : 
     339             :         // check the read-only verbose which does not create a reference
     340           1 :         CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["reference"] == "1001");
     341           1 :         CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["verbose"] == "loud");
     342             : 
     343           2 :         std::string const reference_value(const_cast<advgetopt::getopt const &>(opt)["reference"]);
     344           1 :         CATCH_REQUIRE(reference_value == "1001");
     345           2 :         std::string const verbose_value(const_cast<advgetopt::getopt const &>(opt)["verbose"]);
     346           1 :         CATCH_REQUIRE(verbose_value == "loud");
     347             : 
     348             :         // get references
     349           2 :         advgetopt::option_info_ref unknown_ref(opt["unknown"]);
     350           2 :         advgetopt::option_info_ref reference_ref(opt["reference"]);
     351           2 :         advgetopt::option_info_ref verbose_ref(opt["verbose"]);
     352             : 
     353           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     354             : 
     355           1 :         char const * null_string(nullptr);
     356             : 
     357           1 :         CATCH_REQUIRE(unknown_ref.empty());
     358           1 :         CATCH_REQUIRE(unknown_ref.length() == 0);
     359           1 :         CATCH_REQUIRE(unknown_ref.size() == 0);
     360           1 :         CATCH_REQUIRE(unknown_ref.get_long() == 0);
     361           1 :         CATCH_REQUIRE(static_cast<std::string>(unknown_ref) == "");
     362           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     363             : 
     364           1 :         CATCH_REQUIRE_FALSE(static_cast<bool>(unknown_ref));
     365           1 :         CATCH_REQUIRE(!unknown_ref);
     366           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     367             : 
     368           1 :         CATCH_REQUIRE(unknown_ref == nullptr);
     369           1 :         CATCH_REQUIRE(unknown_ref == "");
     370           1 :         CATCH_REQUIRE(unknown_ref == std::string());
     371           1 :         CATCH_REQUIRE_FALSE(unknown_ref == std::string("test"));
     372           1 :         CATCH_REQUIRE(nullptr == unknown_ref);
     373           1 :         CATCH_REQUIRE("" == unknown_ref);
     374           1 :         CATCH_REQUIRE(std::string() == unknown_ref);
     375           1 :         CATCH_REQUIRE_FALSE(std::string("test") == unknown_ref);
     376           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     377             : 
     378           1 :         CATCH_REQUIRE_FALSE(unknown_ref != nullptr);
     379           1 :         CATCH_REQUIRE_FALSE(unknown_ref != "");
     380           1 :         CATCH_REQUIRE_FALSE(unknown_ref != std::string());
     381           1 :         CATCH_REQUIRE(unknown_ref != std::string("test"));
     382           1 :         CATCH_REQUIRE_FALSE(nullptr != unknown_ref);
     383           1 :         CATCH_REQUIRE_FALSE("" != unknown_ref);
     384           1 :         CATCH_REQUIRE_FALSE(std::string() != unknown_ref);
     385           1 :         CATCH_REQUIRE(std::string("test") != unknown_ref);
     386           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     387             : 
     388           1 :         CATCH_REQUIRE_FALSE(unknown_ref < nullptr);
     389           1 :         CATCH_REQUIRE_FALSE(unknown_ref < "");
     390           1 :         CATCH_REQUIRE_FALSE(unknown_ref < std::string());
     391           1 :         CATCH_REQUIRE(unknown_ref < std::string("test"));
     392           1 :         CATCH_REQUIRE_FALSE(nullptr < unknown_ref);
     393           1 :         CATCH_REQUIRE_FALSE("" < unknown_ref);
     394           1 :         CATCH_REQUIRE_FALSE(std::string() < unknown_ref);
     395           1 :         CATCH_REQUIRE_FALSE(std::string("test") < unknown_ref);
     396           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     397             : 
     398           1 :         CATCH_REQUIRE(unknown_ref <= nullptr);
     399           1 :         CATCH_REQUIRE(unknown_ref <= "");
     400           1 :         CATCH_REQUIRE(unknown_ref <= std::string());
     401           1 :         CATCH_REQUIRE(unknown_ref <= std::string("test"));
     402           1 :         CATCH_REQUIRE(nullptr <= unknown_ref);
     403           1 :         CATCH_REQUIRE("" <= unknown_ref);
     404           1 :         CATCH_REQUIRE(std::string() <= unknown_ref);
     405           1 :         CATCH_REQUIRE_FALSE(std::string("test") <= unknown_ref);
     406           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     407             : 
     408           1 :         CATCH_REQUIRE_FALSE(unknown_ref > nullptr);
     409           1 :         CATCH_REQUIRE_FALSE(unknown_ref > "");
     410           1 :         CATCH_REQUIRE_FALSE(unknown_ref > std::string());
     411           1 :         CATCH_REQUIRE_FALSE(unknown_ref > std::string("test"));
     412           1 :         CATCH_REQUIRE_FALSE(nullptr > unknown_ref);
     413           1 :         CATCH_REQUIRE_FALSE("" > unknown_ref);
     414           1 :         CATCH_REQUIRE_FALSE(std::string() > unknown_ref);
     415           1 :         CATCH_REQUIRE(std::string("test") > unknown_ref);
     416           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     417             : 
     418           1 :         CATCH_REQUIRE(unknown_ref >= nullptr);
     419           1 :         CATCH_REQUIRE(unknown_ref >= "");
     420           1 :         CATCH_REQUIRE(unknown_ref >= std::string());
     421           1 :         CATCH_REQUIRE_FALSE(unknown_ref >= std::string("test"));
     422           1 :         CATCH_REQUIRE(nullptr >= unknown_ref);
     423           1 :         CATCH_REQUIRE("" >= unknown_ref);
     424           1 :         CATCH_REQUIRE(std::string() >= unknown_ref);
     425           1 :         CATCH_REQUIRE(std::string("test") >= unknown_ref);
     426           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     427             : 
     428           1 :         CATCH_REQUIRE(unknown_ref + '\0' == "");
     429           1 :         CATCH_REQUIRE(unknown_ref + '<' == "<");
     430           1 :         CATCH_REQUIRE(unknown_ref + static_cast<char32_t>(U'\0') == "");
     431           1 :         CATCH_REQUIRE(unknown_ref + static_cast<char32_t>(U'\x2020') == "\xE2\x80\xA0");
     432           1 :         CATCH_REQUIRE(unknown_ref + null_string == "");
     433           1 :         CATCH_REQUIRE(unknown_ref + "abc\xE4\x81\x81" == "abc\xE4\x81\x81");
     434           1 :         CATCH_REQUIRE(unknown_ref + std::string("xyz\xE4\x9E\x99") == "xyz\xE4\x9E\x99");
     435           1 :         CATCH_REQUIRE(unknown_ref + reference_ref == "1001");
     436           1 :         CATCH_REQUIRE(unknown_ref + verbose_ref == "loud");
     437           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     438             : 
     439           1 :         CATCH_REQUIRE('\0' + unknown_ref == "");
     440           1 :         CATCH_REQUIRE('<' + unknown_ref == "<");
     441           1 :         CATCH_REQUIRE(static_cast<char32_t>(U'\0') + unknown_ref == "");
     442           1 :         CATCH_REQUIRE(static_cast<char32_t>(U'\x2020') + unknown_ref == "\xE2\x80\xA0");
     443           1 :         CATCH_REQUIRE(null_string + unknown_ref == "");
     444           1 :         CATCH_REQUIRE("abc\xE4\x81\x81" + unknown_ref == "abc\xE4\x81\x81");
     445           1 :         CATCH_REQUIRE(std::string("xyz\xE4\x9E\x99") + unknown_ref == "xyz\xE4\x9E\x99");
     446           1 :         CATCH_REQUIRE(reference_ref + unknown_ref == "1001");
     447           1 :         CATCH_REQUIRE(verbose_ref + unknown_ref == "loud");
     448           1 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     449             : 
     450           1 :         unknown_ref = static_cast<char32_t>(U'\x4819'); // == '\xE4\xA0\x99'
     451           1 :         CATCH_REQUIRE(opt.is_defined("unknown"));
     452             : 
     453           1 :         CATCH_REQUIRE_FALSE(unknown_ref.empty());
     454           1 :         CATCH_REQUIRE(unknown_ref.length() == 3);       // 3 UTF-8 bytes
     455           1 :         CATCH_REQUIRE(unknown_ref.size() == 3);
     456             : 
     457           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: invalid number (\xE4\xA0\x99) in parameter --unknown at offset 0.");
     458           1 :         CATCH_REQUIRE(unknown_ref.get_long() == -1);
     459             : 
     460           1 :         CATCH_REQUIRE(static_cast<std::string>(unknown_ref) == "\xE4\xA0\x99");
     461           1 :         CATCH_REQUIRE(opt.is_defined("unknown"));
     462             : 
     463           1 :         CATCH_REQUIRE(static_cast<bool>(unknown_ref));
     464           1 :         CATCH_REQUIRE_FALSE(!unknown_ref);
     465           1 :         CATCH_REQUIRE(opt.is_defined("unknown"));
     466             : 
     467           1 :         CATCH_REQUIRE_FALSE(unknown_ref == nullptr);
     468           1 :         CATCH_REQUIRE_FALSE(unknown_ref == "");
     469           1 :         CATCH_REQUIRE(unknown_ref == "\xE4\xA0\x99");
     470           1 :         CATCH_REQUIRE_FALSE(unknown_ref == std::string());
     471           1 :         CATCH_REQUIRE_FALSE(unknown_ref == std::string("test"));
     472           1 :         CATCH_REQUIRE(unknown_ref == std::string("\xE4\xA0\x99"));
     473           1 :         CATCH_REQUIRE_FALSE(nullptr == unknown_ref);
     474           1 :         CATCH_REQUIRE_FALSE("" == unknown_ref);
     475           1 :         CATCH_REQUIRE("\xE4\xA0\x99" == unknown_ref);
     476           1 :         CATCH_REQUIRE_FALSE(std::string() == unknown_ref);
     477           1 :         CATCH_REQUIRE_FALSE(std::string("test") == unknown_ref);
     478           1 :         CATCH_REQUIRE(std::string("\xE4\xA0\x99") == unknown_ref);
     479           1 :         CATCH_REQUIRE(opt.is_defined("unknown"));
     480             : 
     481           1 :         CATCH_REQUIRE(unknown_ref != nullptr);
     482           1 :         CATCH_REQUIRE(unknown_ref != "");
     483           1 :         CATCH_REQUIRE_FALSE(unknown_ref != "\xE4\xA0\x99");
     484           1 :         CATCH_REQUIRE(unknown_ref != std::string());
     485           1 :         CATCH_REQUIRE(unknown_ref != std::string("test"));
     486           1 :         CATCH_REQUIRE_FALSE(unknown_ref != std::string("\xE4\xA0\x99"));
     487           1 :         CATCH_REQUIRE(nullptr != unknown_ref);
     488           1 :         CATCH_REQUIRE("" != unknown_ref);
     489           1 :         CATCH_REQUIRE_FALSE("\xE4\xA0\x99" != unknown_ref);
     490           1 :         CATCH_REQUIRE(std::string() != unknown_ref);
     491           1 :         CATCH_REQUIRE(std::string("test") != unknown_ref);
     492           1 :         CATCH_REQUIRE_FALSE(std::string("\xE4\xA0\x99") != unknown_ref);
     493           1 :         CATCH_REQUIRE(opt.is_defined("unknown"));
     494             : 
     495           1 :         CATCH_REQUIRE_FALSE(unknown_ref < nullptr);
     496           1 :         CATCH_REQUIRE_FALSE(unknown_ref < "");
     497           1 :         CATCH_REQUIRE_FALSE(unknown_ref < "\xE4\xA0\x99");
     498           1 :         CATCH_REQUIRE_FALSE(unknown_ref < std::string());
     499           1 :         CATCH_REQUIRE_FALSE(unknown_ref < std::string("test"));
     500           1 :         CATCH_REQUIRE_FALSE(unknown_ref < std::string("\xE4\xA0\x99"));
     501           1 :         CATCH_REQUIRE(nullptr < unknown_ref);
     502           1 :         CATCH_REQUIRE("" < unknown_ref);
     503           1 :         CATCH_REQUIRE_FALSE("\xE4\xA0\x99" < unknown_ref);
     504           1 :         CATCH_REQUIRE(std::string() < unknown_ref);
     505           1 :         CATCH_REQUIRE(std::string("test") < unknown_ref);
     506           1 :         CATCH_REQUIRE_FALSE(std::string("\xE4\xA0\x99") < unknown_ref);
     507           1 :         CATCH_REQUIRE(opt.is_defined("unknown"));
     508             : 
     509           1 :         CATCH_REQUIRE_FALSE(unknown_ref <= nullptr);
     510           1 :         CATCH_REQUIRE_FALSE(unknown_ref <= "");
     511           1 :         CATCH_REQUIRE(unknown_ref <= "\xE4\xA0\x99");
     512           1 :         CATCH_REQUIRE_FALSE(unknown_ref <= std::string());
     513           1 :         CATCH_REQUIRE_FALSE(unknown_ref <= std::string("test"));
     514           1 :         CATCH_REQUIRE(unknown_ref <= std::string("\xE4\xA0\x99"));
     515           1 :         CATCH_REQUIRE(nullptr <= unknown_ref);
     516           1 :         CATCH_REQUIRE("" <= unknown_ref);
     517           1 :         CATCH_REQUIRE("\xE4\xA0\x99" <= unknown_ref);
     518           1 :         CATCH_REQUIRE(std::string() <= unknown_ref);
     519           1 :         CATCH_REQUIRE(std::string("test") <= unknown_ref);
     520           1 :         CATCH_REQUIRE(std::string("\xE4\xA0\x99") <= unknown_ref);
     521           1 :         CATCH_REQUIRE(opt.is_defined("unknown"));
     522             : 
     523           1 :         CATCH_REQUIRE(unknown_ref > nullptr);
     524           1 :         CATCH_REQUIRE(unknown_ref > "");
     525           1 :         CATCH_REQUIRE_FALSE(unknown_ref > "\xE4\xA0\x99");
     526           1 :         CATCH_REQUIRE(unknown_ref > std::string());
     527           1 :         CATCH_REQUIRE(unknown_ref > std::string("test"));
     528           1 :         CATCH_REQUIRE_FALSE(unknown_ref > std::string("\xE4\xA0\x99"));
     529           1 :         CATCH_REQUIRE_FALSE(nullptr > unknown_ref);
     530           1 :         CATCH_REQUIRE_FALSE("" > unknown_ref);
     531           1 :         CATCH_REQUIRE_FALSE("\xE4\xA0\x99" > unknown_ref);
     532           1 :         CATCH_REQUIRE_FALSE(std::string() > unknown_ref);
     533           1 :         CATCH_REQUIRE_FALSE(std::string("test") > unknown_ref);
     534           1 :         CATCH_REQUIRE_FALSE(std::string("\xE4\xA0\x99") > unknown_ref);
     535           1 :         CATCH_REQUIRE(opt.is_defined("unknown"));
     536             : 
     537           1 :         CATCH_REQUIRE(unknown_ref >= nullptr);
     538           1 :         CATCH_REQUIRE(unknown_ref >= "");
     539           1 :         CATCH_REQUIRE(unknown_ref >= "\xE4\xA0\x99");
     540           1 :         CATCH_REQUIRE(unknown_ref >= std::string());
     541           1 :         CATCH_REQUIRE(unknown_ref >= std::string("test"));
     542           1 :         CATCH_REQUIRE(unknown_ref >= std::string("\xE4\xA0\x99"));
     543           1 :         CATCH_REQUIRE_FALSE(nullptr >= unknown_ref);
     544           1 :         CATCH_REQUIRE_FALSE("" >= unknown_ref);
     545           1 :         CATCH_REQUIRE_FALSE(std::string() >= unknown_ref);
     546           1 :         CATCH_REQUIRE_FALSE(std::string("test") >= unknown_ref);
     547           1 :         CATCH_REQUIRE(opt.is_defined("unknown"));
     548             : 
     549           1 :         CATCH_REQUIRE(unknown_ref + '\0' == "\xE4\xA0\x99");
     550           1 :         CATCH_REQUIRE(unknown_ref + '<' == "\xE4\xA0\x99<");
     551           1 :         CATCH_REQUIRE(unknown_ref + static_cast<char32_t>(U'\0') == "\xE4\xA0\x99");
     552           1 :         CATCH_REQUIRE(unknown_ref + static_cast<char32_t>(U'\x2020') == "\xE4\xA0\x99\xE2\x80\xA0");
     553           1 :         CATCH_REQUIRE(unknown_ref + null_string == "\xE4\xA0\x99");
     554           1 :         CATCH_REQUIRE(unknown_ref + "abc\xE4\x81\x81" == "\xE4\xA0\x99\x61\x62\x63\xE4\x81\x81");
     555           1 :         CATCH_REQUIRE(unknown_ref + std::string("xyz\xE4\x9E\x99") == "\xE4\xA0\x99xyz\xE4\x9E\x99");
     556           1 :         CATCH_REQUIRE(unknown_ref + reference_ref == "\xE4\xA0\x99\x31\x30\x30\x31");
     557           1 :         CATCH_REQUIRE(unknown_ref + verbose_ref == "\xE4\xA0\x99loud");
     558           1 :         CATCH_REQUIRE(opt.is_defined("unknown"));
     559             : 
     560           1 :         CATCH_REQUIRE('\0' + unknown_ref == "\xE4\xA0\x99");
     561           1 :         CATCH_REQUIRE('<' + unknown_ref == "<\xE4\xA0\x99");
     562           1 :         CATCH_REQUIRE(static_cast<char32_t>(U'\0') + unknown_ref == "\xE4\xA0\x99");
     563           1 :         CATCH_REQUIRE(static_cast<char32_t>(U'\x2020') + unknown_ref == "\xE2\x80\xA0\xE4\xA0\x99");
     564           1 :         CATCH_REQUIRE(null_string + unknown_ref == "\xE4\xA0\x99");
     565           1 :         CATCH_REQUIRE("abc\xE4\x81\x81" + unknown_ref == "abc\xE4\x81\x81\xE4\xA0\x99");
     566           1 :         CATCH_REQUIRE(std::string("xyz\xE4\x9E\x99") + unknown_ref == "xyz\xE4\x9E\x99\xE4\xA0\x99");
     567           1 :         CATCH_REQUIRE(reference_ref + unknown_ref == "1001\xE4\xA0\x99");
     568           1 :         CATCH_REQUIRE(verbose_ref + unknown_ref == "loud\xE4\xA0\x99");
     569           1 :         CATCH_REQUIRE(opt.is_defined("unknown"));
     570             :     }
     571             :     CATCH_END_SECTION()
     572             : 
     573          54 :     CATCH_START_SECTION("Set non-existant reference + many WHEN()")
     574             :     {
     575          25 :         advgetopt::option const options[] =
     576             :         {
     577             :             advgetopt::define_option(
     578             :                   advgetopt::Name("reference")
     579             :                 , advgetopt::ShortName('r')
     580             :                 , advgetopt::Flags(advgetopt::command_flags<
     581             :                               advgetopt::GETOPT_FLAG_REQUIRED
     582             :                             | advgetopt::GETOPT_FLAG_DYNAMIC_CONFIGURATION>())
     583             :                 , advgetopt::Help("test reference.")
     584             :                 , advgetopt::DefaultValue("978")
     585             :             ),
     586             :             advgetopt::define_option(
     587             :                   advgetopt::Name("verbose")
     588             :                 , advgetopt::ShortName('v')
     589             :                 , advgetopt::Flags(advgetopt::command_flags<
     590             :                               advgetopt::GETOPT_FLAG_REQUIRED
     591             :                             | advgetopt::GETOPT_FLAG_DYNAMIC_CONFIGURATION>())
     592             :                 , advgetopt::Help("make it all verbose.")
     593             :             ),
     594             :             advgetopt::end_options()
     595             :         };
     596             : 
     597          25 :         advgetopt::options_environment environment_options;
     598          25 :         environment_options.f_project_name = "unittest";
     599          25 :         environment_options.f_options = options;
     600          25 :         environment_options.f_help_header = "Usage: verify references";
     601             : 
     602          25 :         char const * cargv[] =
     603             :         {
     604             :             "/usr/bin/arguments",
     605             :             "--reference",
     606             :             "3100",
     607             :             "--verbose",
     608             :             "silence",
     609             :             nullptr
     610             :         };
     611          25 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
     612          25 :         char ** argv = const_cast<char **>(cargv);
     613             : 
     614          50 :         advgetopt::getopt opt(environment_options, argc, argv);
     615             : 
     616             :         // check that the result is valid
     617             : 
     618             :         // verify both parameters the "normal" way
     619          25 :         CATCH_REQUIRE(opt.get_option("reference") != nullptr);
     620          25 :         CATCH_REQUIRE(opt.size("reference") == 1);
     621          25 :         CATCH_REQUIRE(opt.get_string("reference") == "3100");
     622          25 :         CATCH_REQUIRE(opt.get_long("reference") == 3100);
     623             : 
     624          25 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
     625          25 :         CATCH_REQUIRE(opt.size("verbose") == 1);
     626          25 :         CATCH_REQUIRE(opt.get_string("verbose") == "silence");
     627             : 
     628          25 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     629             : 
     630             :         // check the read-only verbose which does not create a reference
     631          25 :         CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["reference"] == "3100");
     632          25 :         CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["verbose"] == "silence");
     633             : 
     634          50 :         std::string const reference_value(const_cast<advgetopt::getopt const &>(opt)["reference"]);
     635          25 :         CATCH_REQUIRE(reference_value == "3100");
     636          50 :         std::string const verbose_value(const_cast<advgetopt::getopt const &>(opt)["verbose"]);
     637          25 :         CATCH_REQUIRE(verbose_value == "silence");
     638             : 
     639             :         // get references
     640          50 :         advgetopt::option_info_ref unknown_ref(opt["unknown"]);
     641          50 :         advgetopt::option_info_ref undefined_ref(opt["undefined"]);     // never set, used as rhs to test setting/adding with an undefined ref.
     642          50 :         advgetopt::option_info_ref reference_ref(opt["reference"]);
     643          50 :         advgetopt::option_info_ref verbose_ref(opt["verbose"]);
     644             : 
     645          25 :         CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     646          25 :         CATCH_REQUIRE(opt.is_defined("reference"));
     647          25 :         CATCH_REQUIRE(opt.is_defined("verbose"));
     648          25 :         CATCH_REQUIRE(reference_ref.get_long() == 3100);
     649             : 
     650          50 :         WHEN("with = & zero char")
     651             :         {
     652           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     653             : 
     654           1 :             char const c('\0');
     655           1 :             unknown_ref = c;
     656             : 
     657           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     658             : 
     659           2 :             std::string s;
     660           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     661             : 
     662           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     663           1 :             CATCH_REQUIRE(unknown_value == s);
     664             : 
     665           1 :             CATCH_REQUIRE(unknown_ref == s);
     666             : 
     667           1 :             unknown_ref += c;
     668             : 
     669           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     670             : 
     671           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     672             : 
     673           2 :             std::string const unknown_value2(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     674           1 :             CATCH_REQUIRE(unknown_value2 == s);
     675             : 
     676           1 :             CATCH_REQUIRE(unknown_ref == s);
     677             :         }
     678             : 
     679          50 :         WHEN("with = & valid char")
     680             :         {
     681           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     682             : 
     683           1 :             char const c(rand() % 26 + 'a');
     684           1 :             unknown_ref = c;
     685             : 
     686           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     687             : 
     688           2 :             std::string s;
     689           1 :             s += c;
     690           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     691             : 
     692           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     693           1 :             CATCH_REQUIRE(unknown_value == s);
     694             : 
     695           1 :             CATCH_REQUIRE(unknown_ref == s);
     696             : 
     697           1 :             char const d(rand() % 26 + 'a');
     698           1 :             unknown_ref += d;
     699             : 
     700           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     701             : 
     702           1 :             s += d;
     703           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     704             : 
     705           2 :             std::string const unknown_value2(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     706           1 :             CATCH_REQUIRE(unknown_value2 == s);
     707             : 
     708           1 :             CATCH_REQUIRE(unknown_ref == s);
     709             :         }
     710             : 
     711          50 :         WHEN("with = & zero char32_t")
     712             :         {
     713           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     714             : 
     715           1 :             char32_t const c(U'\0');
     716           1 :             unknown_ref = c;
     717             : 
     718           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     719             : 
     720           2 :             std::string s;
     721           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     722             : 
     723           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     724           1 :             CATCH_REQUIRE(unknown_value == s);
     725             : 
     726           1 :             CATCH_REQUIRE(unknown_ref == s);
     727             : 
     728           1 :             unknown_ref += c;
     729             : 
     730           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     731             : 
     732           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     733             : 
     734           2 :             std::string const unknown_value2(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     735           1 :             CATCH_REQUIRE(unknown_value2 == s);
     736             : 
     737           1 :             CATCH_REQUIRE(unknown_ref == s);
     738             :         }
     739             : 
     740          50 :         WHEN("with = & valid char32_t")
     741             :         {
     742           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     743             : 
     744           1 :             char32_t c((rand() & 0xFFFFF) + ' ');
     745           1 :             if(c >= 0xD800 && c < 0xE000)
     746             :             {
     747           0 :                 c += 0x0800;
     748             :             }
     749           1 :             unknown_ref = c;
     750             : 
     751           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     752             : 
     753           2 :             std::string s;
     754           1 :             s += libutf8::to_u8string(c);
     755           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     756             : 
     757           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     758           1 :             CATCH_REQUIRE(unknown_value == s);
     759             : 
     760           1 :             CATCH_REQUIRE(unknown_ref == s);
     761             : 
     762           1 :             char32_t d((rand() & 0xFFFFF) + ' ');
     763           1 :             if(d >= 0xD800 && d < 0xE000)
     764             :             {
     765           0 :                 d += 0x0800;
     766             :             }
     767           1 :             unknown_ref += d;
     768             : 
     769           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     770             : 
     771           1 :             s += libutf8::to_u8string(d);
     772           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     773             : 
     774           2 :             std::string const unknown_value2(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     775           1 :             CATCH_REQUIRE(unknown_value2 == s);
     776             : 
     777           1 :             CATCH_REQUIRE(unknown_ref == s);
     778             :         }
     779             : 
     780          50 :         WHEN("with = & nullptr of 'char const *'")
     781             :         {
     782           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     783             : 
     784           1 :             char const * str(nullptr);
     785           1 :             unknown_ref = str;
     786             : 
     787           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     788             : 
     789           2 :             std::string s;
     790           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     791             : 
     792           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     793           1 :             CATCH_REQUIRE(unknown_value == s);
     794             : 
     795           1 :             CATCH_REQUIRE(unknown_ref == s);
     796             : 
     797           1 :             unknown_ref += str;
     798             : 
     799           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     800             : 
     801           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     802             : 
     803           2 :             std::string const unknown_value2(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     804           1 :             CATCH_REQUIRE(unknown_value2 == s);
     805             : 
     806           1 :             CATCH_REQUIRE(unknown_ref == s);
     807             :         }
     808             : 
     809          50 :         WHEN("with = & empty 'char const *' string")
     810             :         {
     811           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     812             : 
     813           1 :             char const * str("");
     814           1 :             unknown_ref = str;
     815             : 
     816           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     817             : 
     818           2 :             std::string s;
     819           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     820             : 
     821           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     822           1 :             CATCH_REQUIRE(unknown_value == s);
     823             : 
     824           1 :             CATCH_REQUIRE(unknown_ref == s);
     825             : 
     826           1 :             unknown_ref += str;
     827             : 
     828           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     829             : 
     830           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     831             : 
     832           2 :             std::string const unknown_value2(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     833           1 :             CATCH_REQUIRE(unknown_value2 == s);
     834             : 
     835           1 :             CATCH_REQUIRE(unknown_ref == s);
     836             :         }
     837             : 
     838          50 :         WHEN("with = & valid `char const *`")
     839             :         {
     840           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     841             : 
     842           2 :             std::string str;
     843           1 :             size_t max(rand() % 10 + 1);
     844          10 :             for(size_t idx(0); idx < max; ++idx)
     845             :             {
     846           9 :                 char32_t c((rand() & 0xFFFFF) + ' ');
     847           9 :                 if(c >= 0xD800 && c < 0xE000)
     848             :                 {
     849           0 :                     c += 0x0800;
     850             :                 }
     851           9 :                 str += libutf8::to_u8string(c);
     852             :             }
     853           1 :             unknown_ref = str.c_str();
     854             : 
     855           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     856             : 
     857           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == str);
     858             : 
     859           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     860           1 :             CATCH_REQUIRE(unknown_value == str);
     861             : 
     862           1 :             CATCH_REQUIRE(unknown_ref == str);
     863             : 
     864           2 :             std::string add;
     865           1 :             max = rand() % 10 + 1;
     866           9 :             for(size_t idx(0); idx < max; ++idx)
     867             :             {
     868           8 :                 char32_t c((rand() & 0xFFFFF) + ' ');
     869           8 :                 if(c >= 0xD800 && c < 0xE000)
     870             :                 {
     871           0 :                     c += 0x0800;
     872             :                 }
     873           8 :                 add += libutf8::to_u8string(c);
     874             :             }
     875           1 :             unknown_ref += add.c_str();
     876             : 
     877           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     878             : 
     879           1 :             str += add;
     880           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == str);
     881             : 
     882           2 :             std::string const unknown_value2(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     883           1 :             CATCH_REQUIRE(unknown_value2 == str);
     884             : 
     885           1 :             CATCH_REQUIRE(unknown_ref == str);
     886             :         }
     887             : 
     888          50 :         WHEN("with = & empty std::string")
     889             :         {
     890           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     891             : 
     892           2 :             std::string str;
     893           1 :             unknown_ref = str;
     894             : 
     895           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     896             : 
     897           2 :             std::string s;
     898           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     899             : 
     900           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     901           1 :             CATCH_REQUIRE(unknown_value == s);
     902             : 
     903           1 :             CATCH_REQUIRE(unknown_ref == s);
     904             : 
     905           1 :             unknown_ref += str;
     906             : 
     907           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     908             : 
     909           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
     910             : 
     911           2 :             std::string const unknown_value2(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     912           1 :             CATCH_REQUIRE(unknown_value2 == s);
     913             : 
     914           1 :             CATCH_REQUIRE(unknown_ref == s);
     915             :         }
     916             : 
     917          50 :         WHEN("with = & valid std::string")
     918             :         {
     919           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     920             : 
     921           2 :             std::string str;
     922           1 :             size_t max(rand() % 10 + 1);
     923           2 :             for(size_t idx(0); idx < max; ++idx)
     924             :             {
     925           1 :                 char32_t c((rand() & 0xFFFFF) + ' ');
     926           1 :                 if(c >= 0xD800 && c < 0xE000)
     927             :                 {
     928           0 :                     c += 0x0800;
     929             :                 }
     930           1 :                 str += libutf8::to_u8string(c);
     931             :             }
     932           1 :             unknown_ref = str;
     933             : 
     934           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     935             : 
     936           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == str);
     937             : 
     938           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     939           1 :             CATCH_REQUIRE(unknown_value == str);
     940             : 
     941           1 :             CATCH_REQUIRE(unknown_ref == str);
     942             : 
     943           2 :             std::string add;
     944           1 :             max = rand() % 10 + 1;
     945           9 :             for(size_t idx(0); idx < max; ++idx)
     946             :             {
     947           8 :                 char32_t c((rand() & 0xFFFFF) + ' ');
     948           8 :                 if(c >= 0xD800 && c < 0xE000)
     949             :                 {
     950           0 :                     c += 0x0800;
     951             :                 }
     952           8 :                 add += libutf8::to_u8string(c);
     953             :             }
     954           1 :             unknown_ref += add;
     955             : 
     956           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     957             : 
     958           1 :             str += add;
     959           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == str);
     960             : 
     961           2 :             std::string const unknown_value2(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     962           1 :             CATCH_REQUIRE(unknown_value2 == str);
     963             : 
     964           1 :             CATCH_REQUIRE(unknown_ref == str);
     965             :         }
     966             : 
     967          50 :         WHEN("with = & unknown reference")
     968             :         {
     969           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     970             : 
     971           1 :             unknown_ref = undefined_ref;
     972             : 
     973           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     974             : 
     975           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == "");
     976             : 
     977           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     978           1 :             CATCH_REQUIRE(unknown_value == std::string());
     979             : 
     980           1 :             CATCH_REQUIRE(unknown_ref == std::string());
     981             :         }
     982             : 
     983          50 :         WHEN("with = & self reference")
     984             :         {
     985           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
     986             : 
     987           1 :             unknown_ref = unknown_ref;
     988             : 
     989           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
     990             : 
     991           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == "");
     992             : 
     993           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
     994           1 :             CATCH_REQUIRE(unknown_value == std::string());
     995             : 
     996           1 :             CATCH_REQUIRE(unknown_ref == std::string());
     997             : 
     998           1 :             CATCH_REQUIRE(unknown_ref == unknown_ref);
     999             :         }
    1000             : 
    1001          50 :         WHEN("with = & known reference")
    1002             :         {
    1003           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1004             : 
    1005           1 :             unknown_ref = verbose_ref;
    1006             : 
    1007           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1008             : 
    1009           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == verbose_value);
    1010             : 
    1011           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1012           1 :             CATCH_REQUIRE(unknown_value == verbose_value);
    1013             : 
    1014           1 :             CATCH_REQUIRE(unknown_ref == verbose_value);
    1015             : 
    1016           1 :             unknown_ref += reference_ref;
    1017             : 
    1018           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1019             : 
    1020           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == verbose_value + reference_value);
    1021             : 
    1022           2 :             std::string const unknown_value2(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1023           1 :             CATCH_REQUIRE(unknown_value2 == verbose_value + reference_value);
    1024             : 
    1025           1 :             CATCH_REQUIRE(unknown_ref == verbose_value + reference_value);
    1026             :         }
    1027             : 
    1028          50 :         WHEN("with += & zero char")
    1029             :         {
    1030           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1031             : 
    1032           1 :             char const c('\0');
    1033           1 :             unknown_ref += c;
    1034             : 
    1035           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1036             : 
    1037           2 :             std::string s;
    1038           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
    1039             : 
    1040           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1041           1 :             CATCH_REQUIRE(unknown_value == s);
    1042             : 
    1043           1 :             CATCH_REQUIRE(unknown_ref == s);
    1044             :         }
    1045             : 
    1046          50 :         WHEN("with += & valid char")
    1047             :         {
    1048           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1049             : 
    1050           1 :             char const c(rand() % 26 + 'a');
    1051           1 :             unknown_ref += c;
    1052             : 
    1053           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1054             : 
    1055           2 :             std::string s;
    1056           1 :             s += c;
    1057           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
    1058             : 
    1059           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1060           1 :             CATCH_REQUIRE(unknown_value == s);
    1061             : 
    1062           1 :             CATCH_REQUIRE(unknown_ref == s);
    1063             :         }
    1064             : 
    1065          50 :         WHEN("with += & zero char32_t")
    1066             :         {
    1067           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1068             : 
    1069           1 :             char32_t const c(U'\0');
    1070           1 :             unknown_ref += c;
    1071             : 
    1072           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1073             : 
    1074           2 :             std::string s;
    1075           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
    1076             : 
    1077           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1078           1 :             CATCH_REQUIRE(unknown_value == s);
    1079             : 
    1080           1 :             CATCH_REQUIRE(unknown_ref == s);
    1081             :         }
    1082             : 
    1083          50 :         WHEN("with += & valid char32_t")
    1084             :         {
    1085           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1086             : 
    1087           1 :             char32_t c((rand() & 0xFFFFF) + ' ');
    1088           1 :             if(c >= 0xD800 && c < 0xE000)
    1089             :             {
    1090           0 :                 c += 0x0800;
    1091             :             }
    1092             : 
    1093           1 :             unknown_ref += c;
    1094             : 
    1095           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1096             : 
    1097           2 :             std::string s;
    1098           1 :             s += libutf8::to_u8string(c);
    1099           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
    1100             : 
    1101           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1102           1 :             CATCH_REQUIRE(unknown_value == s);
    1103             : 
    1104           1 :             CATCH_REQUIRE(unknown_ref == s);
    1105             :         }
    1106             : 
    1107          50 :         WHEN("with += & nullptr of 'char const *'")
    1108             :         {
    1109           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1110             : 
    1111           1 :             char const * str(nullptr);
    1112             : 
    1113           1 :             unknown_ref += str;
    1114             : 
    1115           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1116             : 
    1117           2 :             std::string s;
    1118           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
    1119             : 
    1120           2 :             std::string const unknown_value2(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1121           1 :             CATCH_REQUIRE(unknown_value2 == s);
    1122             : 
    1123           1 :             CATCH_REQUIRE(unknown_ref == s);
    1124             :         }
    1125             : 
    1126          50 :         WHEN("with += & empty 'char const *' string")
    1127             :         {
    1128           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1129             : 
    1130           1 :             char const * str("");
    1131             : 
    1132           1 :             unknown_ref += str;
    1133             : 
    1134           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1135             : 
    1136           2 :             std::string s;
    1137           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
    1138             : 
    1139           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1140           1 :             CATCH_REQUIRE(unknown_value == s);
    1141             : 
    1142           1 :             CATCH_REQUIRE(unknown_ref == s);
    1143             :         }
    1144             : 
    1145          50 :         WHEN("with += & valid `char const *`")
    1146             :         {
    1147           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1148             : 
    1149           2 :             std::string str;
    1150           1 :             size_t max(rand() % 10 + 1);
    1151           3 :             for(size_t idx(0); idx < max; ++idx)
    1152             :             {
    1153           2 :                 char32_t c((rand() & 0xFFFFF) + ' ');
    1154           2 :                 if(c >= 0xD800 && c < 0xE000)
    1155             :                 {
    1156           0 :                     c += 0x0800;
    1157             :                 }
    1158           2 :                 str += libutf8::to_u8string(c);
    1159             :             }
    1160             : 
    1161           1 :             unknown_ref += str.c_str();
    1162             : 
    1163           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1164             : 
    1165           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == str);
    1166             : 
    1167           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1168           1 :             CATCH_REQUIRE(unknown_value == str);
    1169             : 
    1170           1 :             CATCH_REQUIRE(unknown_ref == str);
    1171             :         }
    1172             : 
    1173          50 :         WHEN("with += & empty std::string")
    1174             :         {
    1175           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1176             : 
    1177           2 :             std::string str;
    1178           1 :             unknown_ref += str;
    1179             : 
    1180           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1181             : 
    1182           2 :             std::string s;
    1183           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == s);
    1184             : 
    1185           2 :             std::string const unknown_value2(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1186           1 :             CATCH_REQUIRE(unknown_value2 == s);
    1187             : 
    1188           1 :             CATCH_REQUIRE(unknown_ref == s);
    1189             :         }
    1190             : 
    1191          50 :         WHEN("with += & valid std::string")
    1192             :         {
    1193           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1194             : 
    1195           2 :             std::string str;
    1196           1 :             size_t max(rand() % 10 + 1);
    1197          11 :             for(size_t idx(0); idx < max; ++idx)
    1198             :             {
    1199          10 :                 char32_t c((rand() & 0xFFFFF) + ' ');
    1200          10 :                 if(c >= 0xD800 && c < 0xE000)
    1201             :                 {
    1202           0 :                     c += 0x0800;
    1203             :                 }
    1204          10 :                 str += libutf8::to_u8string(c);
    1205             :             }
    1206           1 :             unknown_ref += str;
    1207             : 
    1208           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1209             : 
    1210           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == str);
    1211             : 
    1212           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1213           1 :             CATCH_REQUIRE(unknown_value == str);
    1214             : 
    1215           1 :             CATCH_REQUIRE(unknown_ref == str);
    1216             :         }
    1217             : 
    1218          50 :         WHEN("with += & unknown reference")
    1219             :         {
    1220           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1221             : 
    1222           1 :             unknown_ref += undefined_ref;
    1223             : 
    1224           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1225             : 
    1226           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == "");
    1227             : 
    1228           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1229           1 :             CATCH_REQUIRE(unknown_value == std::string());
    1230             : 
    1231           1 :             CATCH_REQUIRE(unknown_ref == std::string());
    1232             :         }
    1233             : 
    1234          50 :         WHEN("with += & self reference")
    1235             :         {
    1236           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1237             : 
    1238           1 :             unknown_ref += unknown_ref;
    1239             : 
    1240           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1241             : 
    1242           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == "");
    1243             : 
    1244           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1245           1 :             CATCH_REQUIRE(unknown_value == std::string());
    1246             : 
    1247           1 :             CATCH_REQUIRE(unknown_ref == std::string());
    1248             : 
    1249           1 :             CATCH_REQUIRE(unknown_ref == unknown_ref);
    1250             :         }
    1251             : 
    1252          50 :         WHEN("with += & known reference")
    1253             :         {
    1254           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1255             : 
    1256           1 :             unknown_ref += reference_ref;
    1257             : 
    1258           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1259             : 
    1260           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == reference_value);
    1261             : 
    1262           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1263           1 :             CATCH_REQUIRE(unknown_value == reference_value);
    1264             : 
    1265           1 :             CATCH_REQUIRE(unknown_ref == reference_value);
    1266             :         }
    1267             : 
    1268          50 :         WHEN("with += & self reference")
    1269             :         {
    1270           1 :             CATCH_REQUIRE_FALSE(opt.is_defined("unknown"));
    1271             : 
    1272           1 :             unknown_ref += unknown_ref;
    1273             : 
    1274           1 :             CATCH_REQUIRE(opt.is_defined("unknown"));
    1275             : 
    1276           1 :             CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["unknown"] == "");
    1277             : 
    1278           2 :             std::string const unknown_value(const_cast<advgetopt::getopt const &>(opt)["unknown"]);
    1279           1 :             CATCH_REQUIRE(unknown_value == "");
    1280             : 
    1281           1 :             CATCH_REQUIRE(unknown_ref == "");
    1282             :         }
    1283             :     }
    1284             :     CATCH_END_SECTION()
    1285          27 : }
    1286             : 
    1287             : 
    1288             : 
    1289           3 : CATCH_TEST_CASE("option_info_ref_with_valid_default", "[option_info][valid][reference][long][default]")
    1290             : {
    1291           2 :     CATCH_START_SECTION("No reference on command line, valid default for get_long()")
    1292             :     {
    1293           1 :         advgetopt::option const options[] =
    1294             :         {
    1295             :             advgetopt::define_option(
    1296             :                   advgetopt::Name("reference")
    1297             :                 , advgetopt::ShortName('r')
    1298             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    1299             :                 , advgetopt::Help("test reference.")
    1300             :                 , advgetopt::DefaultValue("459")
    1301             :             ),
    1302             :             advgetopt::define_option(
    1303             :                   advgetopt::Name("verbose")
    1304             :                 , advgetopt::ShortName('v')
    1305             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    1306             :                 , advgetopt::Help("make it all verbose.")
    1307             :             ),
    1308             :             advgetopt::end_options()
    1309             :         };
    1310             : 
    1311           1 :         advgetopt::options_environment environment_options;
    1312           1 :         environment_options.f_project_name = "unittest";
    1313           1 :         environment_options.f_options = options;
    1314           1 :         environment_options.f_help_header = "Usage: verify references";
    1315             : 
    1316           1 :         char const * cargv[] =
    1317             :         {
    1318             :             "/usr/bin/arguments",
    1319             :             "--verbose",
    1320             :             "loud",
    1321             :             nullptr
    1322             :         };
    1323           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1324           1 :         char ** argv = const_cast<char **>(cargv);
    1325             : 
    1326           2 :         advgetopt::getopt opt(environment_options, argc, argv);
    1327             : 
    1328             :         // check that the result is valid
    1329             : 
    1330             :         // verify both parameters the "normal" way
    1331           1 :         CATCH_REQUIRE(opt.get_option("reference") != nullptr);
    1332           1 :         CATCH_REQUIRE(opt.size("reference") == 0);
    1333           1 :         CATCH_REQUIRE(opt.get_string("reference") == "459");
    1334             : 
    1335           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    1336           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    1337           1 :         CATCH_REQUIRE(opt.get_string("verbose") == "loud");
    1338             : 
    1339             :         // check the read-only verbose which does not create a reference
    1340           1 :         CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["reference"] == "459");
    1341           1 :         CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["verbose"] == "loud");
    1342             : 
    1343           2 :         std::string const reference_value(const_cast<advgetopt::getopt const &>(opt)["reference"]);
    1344           1 :         CATCH_REQUIRE(reference_value == "459");
    1345           2 :         std::string const verbose_value(const_cast<advgetopt::getopt const &>(opt)["verbose"]);
    1346           1 :         CATCH_REQUIRE(verbose_value == "loud");
    1347             : 
    1348             :         // get a reference
    1349           2 :         advgetopt::option_info_ref reference_ref(opt["reference"]);
    1350           2 :         advgetopt::option_info_ref verbose_ref(opt["verbose"]);
    1351             : 
    1352           1 :         CATCH_REQUIRE(reference_ref.empty());
    1353           1 :         CATCH_REQUIRE_FALSE(verbose_ref.empty());
    1354             : 
    1355           1 :         CATCH_REQUIRE(reference_ref.length() == 3);
    1356           1 :         CATCH_REQUIRE(reference_ref.size() == 3);
    1357           1 :         CATCH_REQUIRE(verbose_ref.length() == 4);
    1358           1 :         CATCH_REQUIRE(verbose_ref.size() == 4);
    1359             : 
    1360           1 :         CATCH_REQUIRE(reference_ref.get_long() == 459);
    1361             : 
    1362           1 :         CATCH_REQUIRE(reference_ref == reference_ref);
    1363           1 :         CATCH_REQUIRE_FALSE(reference_ref != reference_ref);
    1364           1 :         CATCH_REQUIRE_FALSE(reference_ref < reference_ref);
    1365           1 :         CATCH_REQUIRE(reference_ref <= reference_ref);
    1366           1 :         CATCH_REQUIRE_FALSE(reference_ref > reference_ref);
    1367           1 :         CATCH_REQUIRE(reference_ref >= reference_ref);
    1368             : 
    1369           1 :         CATCH_REQUIRE_FALSE(reference_ref == verbose_ref);
    1370           1 :         CATCH_REQUIRE(reference_ref != verbose_ref);
    1371           1 :         CATCH_REQUIRE(reference_ref < verbose_ref);
    1372           1 :         CATCH_REQUIRE(reference_ref <= verbose_ref);
    1373           1 :         CATCH_REQUIRE_FALSE(reference_ref > verbose_ref);
    1374           1 :         CATCH_REQUIRE_FALSE(reference_ref >= verbose_ref);
    1375             :     }
    1376             :     CATCH_END_SECTION()
    1377           1 : }
    1378             : 
    1379             : 
    1380             : 
    1381           3 : CATCH_TEST_CASE("option_info_ref_with_invalid_default", "[option_info][invalid][reference][long][default]")
    1382             : {
    1383           2 :     CATCH_START_SECTION("No reference on command line, not valid for get_long()")
    1384             :     {
    1385           1 :         advgetopt::option const options[] =
    1386             :         {
    1387             :             advgetopt::define_option(
    1388             :                   advgetopt::Name("reference")
    1389             :                 , advgetopt::ShortName('r')
    1390             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    1391             :                 , advgetopt::Help("test reference.")
    1392             :                 , advgetopt::DefaultValue("undefined")
    1393             :             ),
    1394             :             advgetopt::define_option(
    1395             :                   advgetopt::Name("verbose")
    1396             :                 , advgetopt::ShortName('v')
    1397             :                 , advgetopt::Flags(advgetopt::command_flags<advgetopt::GETOPT_FLAG_REQUIRED>())
    1398             :                 , advgetopt::Help("make it all verbose.")
    1399             :             ),
    1400             :             advgetopt::end_options()
    1401             :         };
    1402             : 
    1403           1 :         advgetopt::options_environment environment_options;
    1404           1 :         environment_options.f_project_name = "unittest";
    1405           1 :         environment_options.f_options = options;
    1406           1 :         environment_options.f_help_header = "Usage: verify references";
    1407             : 
    1408           1 :         char const * cargv[] =
    1409             :         {
    1410             :             "/usr/bin/arguments",
    1411             :             "--verbose",
    1412             :             "loud",
    1413             :             nullptr
    1414             :         };
    1415           1 :         int const argc(sizeof(cargv) / sizeof(cargv[0]) - 1);
    1416           1 :         char ** argv = const_cast<char **>(cargv);
    1417             : 
    1418           2 :         advgetopt::getopt opt(environment_options, argc, argv);
    1419             : 
    1420             :         // check that the result is valid
    1421             : 
    1422             :         // verify both parameters the "normal" way
    1423           1 :         CATCH_REQUIRE(opt.get_option("reference") != nullptr);
    1424           1 :         CATCH_REQUIRE(opt.size("reference") == 0);
    1425           1 :         CATCH_REQUIRE(opt.get_string("reference") == "undefined");
    1426             : 
    1427           1 :         CATCH_REQUIRE(opt.get_option("verbose") != nullptr);
    1428           1 :         CATCH_REQUIRE(opt.size("verbose") == 1);
    1429           1 :         CATCH_REQUIRE(opt.get_string("verbose") == "loud");
    1430             : 
    1431             :         // check the read-only verbose which does not create a reference
    1432           1 :         CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["reference"] == "undefined");
    1433           1 :         CATCH_REQUIRE(const_cast<advgetopt::getopt const &>(opt)["verbose"] == "loud");
    1434             : 
    1435           2 :         std::string const reference_value(const_cast<advgetopt::getopt const &>(opt)["reference"]);
    1436           1 :         CATCH_REQUIRE(reference_value == "undefined");
    1437           2 :         std::string const verbose_value(const_cast<advgetopt::getopt const &>(opt)["verbose"]);
    1438           1 :         CATCH_REQUIRE(verbose_value == "loud");
    1439             : 
    1440             :         // get a reference
    1441           2 :         advgetopt::option_info_ref reference_ref(opt["reference"]);
    1442           2 :         advgetopt::option_info_ref verbose_ref(opt["verbose"]);
    1443             : 
    1444           1 :         CATCH_REQUIRE(reference_ref.empty());
    1445           1 :         CATCH_REQUIRE_FALSE(verbose_ref.empty());
    1446             : 
    1447           1 :         CATCH_REQUIRE(reference_ref.length() == 9);
    1448           1 :         CATCH_REQUIRE(reference_ref.size() == 9);
    1449           1 :         CATCH_REQUIRE(verbose_ref.length() == 4);
    1450           1 :         CATCH_REQUIRE(verbose_ref.size() == 4);
    1451             : 
    1452           1 :         SNAP_CATCH2_NAMESPACE::push_expected_log("error: invalid default value for a number (undefined) in parameter --reference at offset 0.");
    1453           1 :         CATCH_REQUIRE(reference_ref.get_long() == -1);
    1454             : 
    1455           1 :         CATCH_REQUIRE(reference_ref == reference_ref);
    1456           1 :         CATCH_REQUIRE_FALSE(reference_ref != reference_ref);
    1457           1 :         CATCH_REQUIRE_FALSE(reference_ref < reference_ref);
    1458           1 :         CATCH_REQUIRE(reference_ref <= reference_ref);
    1459           1 :         CATCH_REQUIRE_FALSE(reference_ref > reference_ref);
    1460           1 :         CATCH_REQUIRE(reference_ref >= reference_ref);
    1461             : 
    1462           1 :         CATCH_REQUIRE_FALSE(reference_ref == verbose_ref);
    1463           1 :         CATCH_REQUIRE(reference_ref != verbose_ref);
    1464           1 :         CATCH_REQUIRE_FALSE(reference_ref < verbose_ref);
    1465           1 :         CATCH_REQUIRE_FALSE(reference_ref <= verbose_ref);
    1466           1 :         CATCH_REQUIRE(reference_ref > verbose_ref);
    1467           1 :         CATCH_REQUIRE(reference_ref >= verbose_ref);
    1468             :     }
    1469             :     CATCH_END_SECTION()
    1470           7 : }
    1471             : 
    1472             : 
    1473             : 
    1474             : 
    1475             : 
    1476             : 
    1477             : 
    1478             : // vim: ts=4 sw=4 et

Generated by: LCOV version 1.13