Task: ParmParse: Add parser support for bool (AMReX-Codes/amrex#4552)

org: AMReX-Codes
repo: amrex
pr_number: 4552
issue_title: ParmParse: Add parser support for bool
issue_body: Close #4535 
resolved_issues: number: 4535
title: `bool` support in `queryAddWithParser`
body: Currently, `ParmParse::queryAddWithParser` does not support `bool` types. It would be very useful and consistent if added / completed for this.

Reference solution:
fix_patch: diff --git a/Src/Base/AMReX_ParmParse.H b/Src/Base/AMReX_ParmParse.H
index 0e2aa7d37f3..c7ec4728b6d 100644
--- a/Src/Base/AMReX_ParmParse.H
+++ b/Src/Base/AMReX_ParmParse.H
@@ -1108,6 +1108,7 @@ public:
      * scalar. The return value indicates whether it's found. Note that
      * queryWithParser will be used recursively for unresolved symbols.
      */
+    int queryWithParser (const char* name, bool& ref) const;
     int queryWithParser (const char* name, int& ref) const;
     int queryWithParser (const char* name, long& ref) const;
     int queryWithParser (const char* name, long long& ref) const;
@@ -1120,12 +1121,14 @@ public:
      * symbols. If the number of elements in the input does not equal to
      * `nvals`, it's a runtime error.
      */
+    int queryarrWithParser (const char* name, int nvals, bool* ref) const;
     int queryarrWithParser (const char* name, int nvals, int* ref) const;
     int queryarrWithParser (const char* name, int nvals, long* ref) const;
     int queryarrWithParser (const char* name, int nvals, long long* ref) const;
     int queryarrWithParser (const char* name, int nvals, float* ref) const;
     int queryarrWithParser (const char* name, int nvals, double* ref) const;
-    template <typename T, std::enable_if_t<std::is_same_v<T,int> ||
+    template <typename T, std::enable_if_t<std::is_same_v<T,bool> ||
+                                           std::is_same_v<T,int> ||
                                            std::is_same_v<T,long> ||
                                            std::is_same_v<T,long long> ||
                                            std::is_same_v<T,float> ||
@@ -1146,7 +1149,8 @@ public:
      * scalar. If not, the value in `ref` will be added to the ParmParse
      * database. The return value indicates whether it's found.
      */
-    template <typename T, std::enable_if_t<std::is_same_v<T,int> ||
+    template <typename T, std::enable_if_t<std::is_same_v<T,bool> ||
+                                           std::is_same_v<T,int> ||
                                            std::is_same_v<T,long> ||
                                            std::is_same_v<T,long long> ||
                                            std::is_same_v<T,float> ||
@@ -1165,7 +1169,8 @@ public:
      * to parse the entire list of empty space separated values as a single
      * scalar. If not, it's a runtime error.
      */
-    template <typename T, std::enable_if_t<std::is_same_v<T,int> ||
+    template <typename T, std::enable_if_t<std::is_same_v<T,bool> ||
+                                           std::is_same_v<T,int> ||
                                            std::is_same_v<T,long> ||
                                            std::is_same_v<T,long long> ||
                                            std::is_same_v<T,float> ||
@@ -1183,7 +1188,8 @@ public:
      * error. If the number of elements does not equal to `nvals`, it's also
      * a runtime error.
      */
-    template <typename T, std::enable_if_t<std::is_same_v<T,int> ||
+    template <typename T, std::enable_if_t<std::is_same_v<T,bool> ||
+                                           std::is_same_v<T,int> ||
                                            std::is_same_v<T,long> ||
                                            std::is_same_v<T,long long> ||
                                            std::is_same_v<T,float> ||
@@ -1201,7 +1207,8 @@ public:
      * error. If the number of elements does not equal to `nvals`, it's also
      * a runtime error.
      */
-    template <typename T, std::enable_if_t<std::is_same_v<T,int> ||
+    template <typename T, std::enable_if_t<std::is_same_v<T,bool> ||
+                                           std::is_same_v<T,int> ||
                                            std::is_same_v<T,long> ||
                                            std::is_same_v<T,long long> ||
                                            std::is_same_v<T,float> ||
@@ -1219,7 +1226,8 @@ public:
      *
      * For unknown symbols, ParmParse database will be queried.
      */
-    template <typename T, std::enable_if_t<std::is_same_v<T,int> ||
+    template <typename T, std::enable_if_t<std::is_same_v<T,bool> ||
+                                           std::is_same_v<T,int> ||
                                            std::is_same_v<T,long> ||
                                            std::is_same_v<T,long long> ||
                                            std::is_same_v<T,float> ||
diff --git a/Src/Base/AMReX_ParmParse.cpp b/Src/Base/AMReX_ParmParse.cpp
index 7a41f187bc2..098ad89c9a7 100644
--- a/Src/Base/AMReX_ParmParse.cpp
+++ b/Src/Base/AMReX_ParmParse.cpp
@@ -718,7 +718,8 @@ squeryval (const ParmParse::Table& table,
     bool ok = is(valname, ref);
     if ( !ok )
     {
-        if constexpr (std::is_same_v<T,int> ||
+        if constexpr (std::is_same_v<T,bool> ||
+                      std::is_same_v<T,int> ||
                       std::is_same_v<T,long> ||
                       std::is_same_v<T,long long> ||
                       std::is_same_v<T,float> ||
@@ -1011,14 +1012,16 @@ bool squeryWithParser (const ParmParse::Table& table,
                        const std::string&      name,
                        T&                      ref);
 
-template <typename T, typename PARSER_t = std::conditional_t<std::is_integral_v<T>,
+template <typename T, typename PARSER_t = std::conditional_t<std::is_integral_v<T>
+                                                             && !std::is_same_v<bool,T>,
                                                              IParser, Parser>>
 PARSER_t
 pp_make_parser (std::string const& func, Vector<std::string> const& vars,
                 ParmParse::Table const& table, std::string const& parser_prefix,
                 bool use_querywithparser)
 {
-    using value_t =  std::conditional_t<std::is_integral_v<T>, long long, double>;
+    using value_t =  std::conditional_t<std::is_integral_v<T> && !std::is_same_v<bool,T>,
+                                        long long, double>;
 
     std::vector<std::string> prefixes;
     prefixes.reserve(3);
@@ -2048,6 +2051,12 @@ bool squeryarrWithParser (const ParmParse::Table& table,
 }
 }
 
+int
+ParmParse::queryWithParser (const char* name, bool& ref) const
+{
+    return squeryWithParser(*m_table,m_parser_prefix,prefixedName(name),ref);
+}
+
 int
 ParmParse::queryWithParser (const char* name, int& ref) const
 {
@@ -2078,6 +2087,12 @@ ParmParse::queryWithParser (const char* name, double& ref) const
     return squeryWithParser(*m_table,m_parser_prefix,prefixedName(name),ref);
 }
 
+int
+ParmParse::queryarrWithParser (const char* name, int nvals, bool* ref) const
+{
+    return squeryarrWithParser(*m_table,m_parser_prefix,prefixedName(name),nvals,ref);
+}
+
 int
 ParmParse::queryarrWithParser (const char* name, int nvals, int* ref) const
 {