public inbox for gcc-patches@gcc.gnu.org
 help / color / mirror / Atom feed
* C++/c-common PATCH to conversion from scoped enum to bool (part of 48450)
@ 2011-04-07 21:42 Jason Merrill
  2011-04-11 21:54 ` Jason Merrill
  0 siblings, 1 reply; 2+ messages in thread
From: Jason Merrill @ 2011-04-07 21:42 UTC (permalink / raw)
  To: gcc-patches List

[-- Attachment #1: Type: text/plain, Size: 441 bytes --]

PR 48450 has to do with SFINAE bugs, but one of them turns out to be a 
different sort of bug: we were failing to convert from a non-constant 
value of scoped enum type to bool, because that conversion was doing a 
!= 0, which requires an implicit conversion to int.  So now we 
explicitly convert to the underlying integral type first, and prevent 
c-common from helpfully removing it again.

Tested x86_64-pc-linux-gnu, applying to trunk.

[-- Attachment #2: scoped-48450.patch --]
[-- Type: text/plain, Size: 2879 bytes --]

commit 87823d7d9dab304517871340e7b3aba6b73afe16
Author: Jason Merrill <jason@redhat.com>
Date:   Tue Apr 5 15:02:14 2011 -0400

    	PR c++/48450
    	* c-family/c-common.c (c_common_truthvalue_conversion): Don't ignore
    	conversion from C++0x scoped enum.
    	* cp/cvt.c (ocp_convert): Handle converting scoped enum to bool.

diff --git a/gcc/c-family/c-common.c b/gcc/c-family/c-common.c
index 1252b18..e0acfea 100644
--- a/gcc/c-family/c-common.c
+++ b/gcc/c-family/c-common.c
@@ -3939,16 +3939,25 @@ c_common_truthvalue_conversion (location_t location, tree expr)
 	}
 
     CASE_CONVERT:
-      /* Don't cancel the effect of a CONVERT_EXPR from a REFERENCE_TYPE,
-	 since that affects how `default_conversion' will behave.  */
-      if (TREE_CODE (TREE_TYPE (expr)) == REFERENCE_TYPE
-	  || TREE_CODE (TREE_TYPE (TREE_OPERAND (expr, 0))) == REFERENCE_TYPE)
-	break;
-      /* If this is widening the argument, we can ignore it.  */
-      if (TYPE_PRECISION (TREE_TYPE (expr))
-	  >= TYPE_PRECISION (TREE_TYPE (TREE_OPERAND (expr, 0))))
-	return c_common_truthvalue_conversion (location,
-					       TREE_OPERAND (expr, 0));
+      {
+	tree totype = TREE_TYPE (expr);
+	tree fromtype = TREE_TYPE (TREE_OPERAND (expr, 0));
+
+	/* Don't cancel the effect of a CONVERT_EXPR from a REFERENCE_TYPE,
+	   since that affects how `default_conversion' will behave.  */
+	if (TREE_CODE (totype) == REFERENCE_TYPE
+	    || TREE_CODE (fromtype) == REFERENCE_TYPE)
+	  break;
+	/* Don't strip a conversion from C++0x scoped enum, since they
+	   don't implicitly convert to other types.  */
+	if (TREE_CODE (fromtype) == ENUMERAL_TYPE
+	    && ENUM_IS_SCOPED (fromtype))
+	  break;
+	/* If this isn't narrowing the argument, we can ignore it.  */
+	if (TYPE_PRECISION (totype) >= TYPE_PRECISION (fromtype))
+	  return c_common_truthvalue_conversion (location,
+						 TREE_OPERAND (expr, 0));
+      }
       break;
 
     case MODIFY_EXPR:
diff --git a/gcc/cp/cvt.c b/gcc/cp/cvt.c
index 8ab0001..290b926 100644
--- a/gcc/cp/cvt.c
+++ b/gcc/cp/cvt.c
@@ -727,7 +727,13 @@ ocp_convert (tree type, tree expr, int convtype, int flags)
 	  return error_mark_node;
 	}
       if (code == BOOLEAN_TYPE)
-	return cp_truthvalue_conversion (e);
+	{
+	  /* We can't implicitly convert a scoped enum to bool, so convert
+	     to the underlying type first.  */
+	  if (SCOPED_ENUM_P (intype) && (convtype & CONV_STATIC))
+	    e = convert (ENUM_UNDERLYING_TYPE (intype), e);
+	  return cp_truthvalue_conversion (e);
+	}
 
       converted = fold_if_not_in_template (convert_to_integer (type, e));
 
diff --git a/gcc/testsuite/g++.dg/cpp0x/enum9.C b/gcc/testsuite/g++.dg/cpp0x/enum9.C
new file mode 100644
index 0000000..10e510b
--- /dev/null
+++ b/gcc/testsuite/g++.dg/cpp0x/enum9.C
@@ -0,0 +1,5 @@
+// { dg-options -std=c++0x }
+
+enum class E { };
+E f();
+bool b2 = static_cast<bool>(f());

^ permalink raw reply	[flat|nested] 2+ messages in thread

* Re: C++/c-common PATCH to conversion from scoped enum to bool (part of 48450)
  2011-04-07 21:42 C++/c-common PATCH to conversion from scoped enum to bool (part of 48450) Jason Merrill
@ 2011-04-11 21:54 ` Jason Merrill
  0 siblings, 0 replies; 2+ messages in thread
From: Jason Merrill @ 2011-04-11 21:54 UTC (permalink / raw)
  To: gcc-patches List

[-- Attachment #1: Type: text/plain, Size: 621 bytes --]

On 04/07/2011 05:41 PM, Jason Merrill wrote:
> PR 48450 has to do with SFINAE bugs, but one of them turns out to be a
> different sort of bug: we were failing to convert from a non-constant
> value of scoped enum type to bool, because that conversion was doing a
> != 0, which requires an implicit conversion to int. So now we explicitly
> convert to the underlying integral type first, and prevent c-common from
> helpfully removing it again.

...except that if the underlying type is bool, this leads to infinite 
recursion.  So use build_nop instead of convert.

Tested x86_64-pc-linux-gnu, applying to trunk and 4.6.

[-- Attachment #2: 48534.patch --]
[-- Type: text/plain, Size: 1091 bytes --]

commit a2873eda4e9932624a2cd1ec77fb7554206b3574
Author: Jason Merrill <jason@redhat.com>
Date:   Sun Apr 10 08:33:43 2011 -0400

    	PR c++/48534
    	* cvt.c (ocp_convert): Use build_nop to convert to underlying type
    	of scoped enum.

diff --git a/gcc/cp/cvt.c b/gcc/cp/cvt.c
index 6551de6..de981bc 100644
--- a/gcc/cp/cvt.c
+++ b/gcc/cp/cvt.c
@@ -731,7 +731,7 @@ ocp_convert (tree type, tree expr, int convtype, int flags)
 	  /* We can't implicitly convert a scoped enum to bool, so convert
 	     to the underlying type first.  */
 	  if (SCOPED_ENUM_P (intype) && (convtype & CONV_STATIC))
-	    e = convert (ENUM_UNDERLYING_TYPE (intype), e);
+	    e = build_nop (ENUM_UNDERLYING_TYPE (intype), e);
 	  return cp_truthvalue_conversion (e);
 	}
 
diff --git a/gcc/testsuite/g++.dg/cpp0x/enum10.C b/gcc/testsuite/g++.dg/cpp0x/enum10.C
new file mode 100644
index 0000000..55a1ab4
--- /dev/null
+++ b/gcc/testsuite/g++.dg/cpp0x/enum10.C
@@ -0,0 +1,9 @@
+// PR c++/48534
+// { dg-options -std=c++0x }
+
+enum class OpSE : bool;
+
+int main()
+{
+  return static_cast<bool>(OpSE());
+}

^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2011-04-11 21:54 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-04-07 21:42 C++/c-common PATCH to conversion from scoped enum to bool (part of 48450) Jason Merrill
2011-04-11 21:54 ` Jason Merrill

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).