* [PING^3] Wconversion: fixes for C++ front-end
@ 2007-02-06 9:14 Manuel López-Ibáñez
2007-02-06 18:24 ` Paolo Carlini
0 siblings, 1 reply; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-02-06 9:14 UTC (permalink / raw)
To: gcc-patches
[-- Attachment #1: Type: text/plain, Size: 186 bytes --]
http://gcc.gnu.org/ml/gcc-patches/2006-12/msg00799.html
Rediff, rebootstrapped and re-regression-tested against revision
121356 on i686-pc-linux-gnu.
Context and unified diffs follow.
[-- Attachment #2: wcoercion-4-gplusplus-try5-powerpc.diff --]
[-- Type: text/plain, Size: 11350 bytes --]
Index: gcc/doc/invoke.texi
===================================================================
--- gcc/doc/invoke.texi (revision 121356)
+++ gcc/doc/invoke.texi (working copy)
@@ -3210,10 +3210,16 @@ conversions between real and integer, li
like @code{unsigned ui = -1}; and conversions to smaller types, like
@code{sqrtf (M_PI)}. Do not warn for explicit casts like @code{abs
((int) x)} and @code{ui = (unsigned) -1}, or if the value is not
changed by the conversion like in @code{abs (2.0)}.
+For C++, also warn for conversions between @code{NULL} and non-pointer
+types; confusing overload resolution for user-defined conversions; and
+conversions that will never use a type conversion operator:
+conversions to @code{void}, the same type, a base class or a reference
+to them.
+
@item -Wempty-body
@opindex Wempty-body
An empty body occurs in an @samp{if} or @samp{else} statement.
This warning is also enabled by @option{-Wextra}.
Index: gcc/testsuite/g++.dg/warn/Wconversion-real-integer.C
===================================================================
--- gcc/testsuite/g++.dg/warn/Wconversion-real-integer.C (revision 0)
+++ gcc/testsuite/g++.dg/warn/Wconversion-real-integer.C (revision 0)
@@ -0,0 +1,73 @@
+/* Test for diagnostics for Wconversion between floating-point and
+ integers. C++ equivalent of
+ gcc/testsuite/gcc.dg/Wconversion-real-integer.c */
+
+/* { dg-do compile }
+/* { dg-options "-Wconversion" } */
+
+#include <limits.h>
+
+void fsi (signed int x);
+void fui (unsigned int x);
+void ffloat (float x);
+void fdouble (double x);
+
+float vfloat;
+double vdouble;
+
+void h (void)
+{
+ unsigned int ui = 3;
+ int si = 3;
+ unsigned char uc = 3;
+ signed char sc = 3;
+ float f = 3;
+ double d = 3;
+
+ fsi (3.1f); /* { dg-warning "conversion" } */
+ si = 3.1f; /* { dg-warning "conversion" } */
+ fsi (3.1); /* { dg-warning "conversion" } */
+ si = 3.1; /* { dg-warning "conversion" } */
+ fsi (d); /* { dg-warning "conversion" } */
+ si = d; /* { dg-warning "conversion" } */
+ fui (-1.0); /* { dg-warning "overflow" } */
+ ui = -1.0; /* { dg-warning "overflow" } */
+ ffloat (INT_MAX); /* { dg-warning "conversion" } */
+ vfloat = INT_MAX; /* { dg-warning "conversion" } */
+ ffloat (16777217); /* { dg-warning "conversion" } */
+ vfloat = 16777217; /* { dg-warning "conversion" } */
+ ffloat (si); /* { dg-warning "conversion" } */
+ vfloat = si; /* { dg-warning "conversion" } */
+ ffloat (ui); /* { dg-warning "conversion" } */
+ vfloat = ui; /* { dg-warning "conversion" } */
+
+ fsi (3);
+ si = 3;
+ fsi (3.0f);
+ si = 3.0f;
+ fsi (3.0);
+ si = 3.0;
+ fsi (16777217.0f);
+ si = 16777217.0f;
+ fsi ((int) 3.1);
+ si = (int) 3.1;
+ ffloat (3U);
+ vfloat = 3U;
+ ffloat (3);
+ vfloat = 3;
+ ffloat (INT_MIN);
+ vfloat = INT_MIN;
+ ffloat (uc);
+ vfloat = uc;
+ ffloat (sc);
+ vfloat = sc;
+
+ fdouble (UINT_MAX);
+ vdouble = UINT_MAX;
+ fdouble (ui);
+ vdouble = ui;
+ fdouble (si);
+ vdouble = si;
+}
+
+
Index: gcc/testsuite/g++.dg/warn/Wconversion-real.C
===================================================================
--- gcc/testsuite/g++.dg/warn/Wconversion-real.C (revision 0)
+++ gcc/testsuite/g++.dg/warn/Wconversion-real.C (revision 0)
@@ -0,0 +1,85 @@
+/* Test for diagnostics for Wconversion for floating-point.
+ C++ equivalent of gcc/testsuite/gcc.dg/Wconversion-real.c */
+
+/* { dg-do compile }
+/* { dg-options "-Wconversion" } */
+
+float vfloat;
+double vdouble;
+long double vlongdouble;
+
+void ffloat (float f);
+void fdouble (double d);
+void flongdouble (long double ld);
+
+void h (void)
+{
+ float f = 0;
+ double d = 0;
+ long double ld = 0;
+
+ ffloat (3.1); /* { dg-warning "conversion" } */
+ vfloat = 3.1; /* { dg-warning "conversion" } */
+ ffloat (3.1L); /* { dg-warning "conversion" } */
+ vfloat = 3.1L; /* { dg-warning "conversion" } */
+ fdouble (3.1L); /* { dg-warning "conversion" "" { target large_long_double } } */
+ vdouble = 3.1L; /* { dg-warning "conversion" "" { target large_long_double } } */
+ ffloat (vdouble); /* { dg-warning "conversion" } */
+ vfloat = vdouble; /* { dg-warning "conversion" } */
+ ffloat (vlongdouble); /* { dg-warning "conversion" } */
+ vfloat = vlongdouble; /* { dg-warning "conversion" } */
+ fdouble (vlongdouble); /* { dg-warning "conversion" "" { target large_long_double } } */
+ vdouble = vlongdouble; /* { dg-warning "conversion" "" { target large_long_double } } */
+
+
+ ffloat ((float) 3.1);
+ vfloat = (float) 3.1;
+ ffloat ((float) 3.1L);
+ vfloat = (float) 3.1L;
+ fdouble ((double) 3.1L);
+ vdouble = (double) 3.1L;
+ ffloat ((float) vdouble);
+ vfloat = (float) vdouble;
+ ffloat ((float) vlongdouble);
+ vfloat = (float) vlongdouble;
+ fdouble ((double) vlongdouble);
+ vdouble = (double) vlongdouble;
+
+
+ ffloat (3.0);
+ vfloat = 3.0;
+ ffloat (3.1f);
+ vfloat = 3.1f;
+ ffloat (0.25L);
+ vfloat = 0.25L;
+
+
+ fdouble (3.0);
+ vdouble = 3.0;
+ fdouble (3.1f);
+ vdouble = 3.1f;
+ fdouble (0.25L);
+ vdouble = 0.25L;
+
+ flongdouble (3.0);
+ vlongdouble = 3.0;
+ flongdouble (3.1f);
+ vlongdouble = 3.1f;
+ flongdouble (0.25L);
+ vlongdouble = 0.25L;
+
+ ffloat (f);
+ vfloat = f;
+ fdouble (f);
+ vdouble = f;
+ fdouble (d);
+ vdouble = d;
+ flongdouble (f);
+ vlongdouble = f;
+ flongdouble (d);
+ vlongdouble = d;
+ flongdouble (ld);
+ vlongdouble = ld;
+}
+
+
Index: gcc/testsuite/g++.dg/warn/Wconversion-integer.C
===================================================================
--- gcc/testsuite/g++.dg/warn/Wconversion-integer.C (revision 0)
+++ gcc/testsuite/g++.dg/warn/Wconversion-integer.C (revision 0)
@@ -0,0 +1,95 @@
+/* Test for diagnostics for implicit conversions between integer types
+ C++ equivalent of gcc/testsuite/gcc.dg/Wconversion-integer.c */
+
+// { dg-do compile }
+// { dg-options "-fsigned-char -Wconversion" }
+
+#include <limits.h>
+
+void fsc (signed char sc);
+void fuc (unsigned char uc);
+unsigned fui (unsigned int ui);
+void fsi (signed int ui);
+
+void h (int x)
+{
+ unsigned int ui = 3;
+ int si = 3;
+ unsigned char uc = 3;
+ signed char sc = 3;
+
+ fuc (-1); /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ uc = -1; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ fuc ('\xa0'); /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ uc = '\xa0'; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ uc = x ? 1U : -1; /* { dg-warning "conversion" } */
+ /* { dg-warning "negative integer implicitly converted to unsigned type" "" { target *-*-* } 25 } */
+ uc = x ? SCHAR_MIN : 1U; /* { dg-warning "conversion" } */
+ /* { dg-warning "negative integer implicitly converted to unsigned type" "" { target *-*-* } 27 } */
+
+ uc = x ? 1 : -1; /* { dg-warning "conversion" } */
+
+ uc = x ? SCHAR_MIN : 1; /* { dg-warning "conversion" } */
+
+ fuc ('A');
+ uc = 'A';
+ uc = (unsigned char) -1;
+
+ fui (-1); /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = -1; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = x ? 1U : -1; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = x ? INT_MIN : 1U; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = ui ? SCHAR_MIN : 1U; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = 1U * -1; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = ui + INT_MIN; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = x ? 1 : -1; /* { dg-warning "conversion" } */
+ ui = ui ? SCHAR_MIN : 1; /* { dg-warning "conversion" } */
+
+ ui = -1 * (1 * -1);
+ ui = (unsigned) -1;
+
+ fsc (uc); /* { dg-warning "conversion" } */
+ sc = uc; /* { dg-warning "conversion" } */
+ fuc (sc); /* { dg-warning "conversion" } */
+ uc = sc; /* { dg-warning "conversion" } */
+ fsi (ui); /* { dg-warning "conversion" } */
+ si = ui; /* { dg-warning "conversion" } */
+ fui (si); /* { dg-warning "conversion" } */
+ ui = si; /* { dg-warning "conversion" } */
+ fui (sc); /* { dg-warning "conversion" } */
+ ui = sc; /* { dg-warning "conversion" } */
+
+ fui ('\xa0');/* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = '\xa0'; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+
+ fsi (si);
+ fui (ui);
+ fsi (uc);
+ si = uc;
+ fui (uc);
+ ui = uc;
+ fui ('A');
+ ui = 'A';
+ fsi ('A');
+ si = 'A';
+
+
+ fsi (UINT_MAX - 1); /* { dg-warning "conversion" } */
+ si = UINT_MAX - 1; /* { dg-warning "conversion" } */
+ fsi (UINT_MAX - 1U); /* { dg-warning "conversion" } */
+ si = UINT_MAX - 1U; /* { dg-warning "conversion" } */
+ fsi (UINT_MAX/3U);
+ si = UINT_MAX/3U;
+ fsi (UINT_MAX/3);
+ si = UINT_MAX/3;
+ fui (UINT_MAX - 1);
+ ui = UINT_MAX - 1;
+
+ fsi (0x80000000); /* { dg-warning "conversion" } */
+ si = 0x80000000; /* { dg-warning "conversion" } */
+}
+
+
+unsigned fui (unsigned a) { return a + -1; } /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+
+
Index: gcc/testsuite/g++.dg/warn/conv2.C
===================================================================
--- gcc/testsuite/g++.dg/warn/conv2.C (revision 121356)
+++ gcc/testsuite/g++.dg/warn/conv2.C (working copy)
@@ -1,4 +1,5 @@
// PR c++/13932
// { dg-options "-Wconversion" }
-int i = 1.; // { dg-warning "converting" }
+int i = 1.;
+int j = 1.1; // { dg-warning "conversion" }
Index: gcc/cp/typeck.c
===================================================================
--- gcc/cp/typeck.c (revision 121356)
+++ gcc/cp/typeck.c (working copy)
@@ -3853,13 +3853,19 @@ build_binary_op (enum tree_code code, tr
warning (0, "NULL used in arithmetic");
if (! converted)
{
if (TREE_TYPE (op0) != result_type)
- op0 = cp_convert (result_type, op0);
- if (TREE_TYPE (op1) != result_type)
- op1 = cp_convert (result_type, op1);
+ {
+ convert_and_check (result_type, op0);
+ op0 = cp_convert (result_type, op0);
+ }
+ if (TREE_TYPE (op1) != result_type)
+ {
+ convert_and_check (result_type, op1);
+ op1 = cp_convert (result_type, op1);
+ }
if (op0 == error_mark_node || op1 == error_mark_node)
return error_mark_node;
}
Index: gcc/cp/call.c
===================================================================
--- gcc/cp/call.c (revision 121356)
+++ gcc/cp/call.c (working copy)
@@ -4261,15 +4261,14 @@ convert_like_real (conversion *convs, tr
/* Warn about assigning a floating-point type to an integer type. */
if (TREE_CODE (TREE_TYPE (expr)) == REAL_TYPE
&& TREE_CODE (t) == INTEGER_TYPE)
{
- if (fn)
- warning (OPT_Wconversion, "passing %qT for argument %P to %qD",
- TREE_TYPE (expr), argnum, fn);
- else
- warning (OPT_Wconversion, "converting to %qT from %qT", t, TREE_TYPE (expr));
+ convert_and_check (t, expr);
+ /* There is another call to convert_and_check below, we just
+ warn once. */
+ issue_conversion_warnings = false;
}
}
switch (convs->kind)
{
[-- Attachment #3: wcoercion-4-gplusplus-try5-powerpc-context.diff --]
[-- Type: text/plain, Size: 12138 bytes --]
Index: gcc/doc/invoke.texi
===================================================================
*** gcc/doc/invoke.texi (revision 121356)
--- gcc/doc/invoke.texi (working copy)
***************
*** 3210,3219 **** conversions between real and integer, li
--- 3210,3225 ----
like @code{unsigned ui = -1}; and conversions to smaller types, like
@code{sqrtf (M_PI)}. Do not warn for explicit casts like @code{abs
((int) x)} and @code{ui = (unsigned) -1}, or if the value is not
changed by the conversion like in @code{abs (2.0)}.
+ For C++, also warn for conversions between @code{NULL} and non-pointer
+ types; confusing overload resolution for user-defined conversions; and
+ conversions that will never use a type conversion operator:
+ conversions to @code{void}, the same type, a base class or a reference
+ to them.
+
@item -Wempty-body
@opindex Wempty-body
An empty body occurs in an @samp{if} or @samp{else} statement.
This warning is also enabled by @option{-Wextra}.
Index: gcc/testsuite/g++.dg/warn/Wconve===================================================================
*** gcc/testsuite/g++.dg/warn/Wconversion-real-integer.C (revision 0)
--- gcc/testsuite/g++.dg/warn/Wconversion-real-integer.C (revision 0)
***************
*** 0 ****
--- 1,73 ----
+ /* Test for diagnostics for Wconversion between floating-point and
+ integers. C++ equivalent of
+ gcc/testsuite/gcc.dg/Wconversion-real-integer.c */
+
+ /* { dg-do compile }
+ /* { dg-options "-Wconversion" } */
+
+ #include <limits.h>
+
+ void fsi (signed int x);
+ void fui (unsigned int x);
+ void ffloat (float x);
+ void fdouble (double x);
+
+ float vfloat;
+ double vdouble;
+
+ void h (void)
+ {
+ unsigned int ui = 3;
+ int si = 3;
+ unsigned char uc = 3;
+ signed char sc = 3;
+ float f = 3;
+ double d = 3;
+
+ fsi (3.1f); /* { dg-warning "conversion" } */
+ si = 3.1f; /* { dg-warning "conversion" } */
+ fsi (3.1); /* { dg-warning "conversion" } */
+ si = 3.1; /* { dg-warning "conversion" } */
+ fsi (d); /* { dg-warning "conversion" } */
+ si = d; /* { dg-warning "conversion" } */
+ fui (-1.0); /* { dg-warning "overflow" } */
+ ui = -1.0; /* { dg-warning "overflow" } */
+ ffloat (INT_MAX); /* { dg-warning "conversion" } */
+ vfloat = INT_MAX; /* { dg-warning "conversion" } */
+ ffloat (16777217); /* { dg-warning "conversion" } */
+ vfloat = 16777217; /* { dg-warning "conversion" } */
+ ffloat (si); /* { dg-warning "conversion" } */
+ vfloat = si; /* { dg-warning "conversion" } */
+ ffloat (ui); /* { dg-warning "conversion" } */
+ vfloat = ui; /* { dg-warning "conversion" } */
+
+ fsi (3);
+ si = 3;
+ fsi (3.0f);
+ si = 3.0f;
+ fsi (3.0);
+ si = 3.0;
+ fsi (16777217.0f);
+ si = 16777217.0f;
+ fsi ((int) 3.1);
+ si = (int) 3.1;
+ ffloat (3U);
+ vfloat = 3U;
+ ffloat (3);
+ vfloat = 3;
+ ffloat (INT_MIN);
+ vfloat = INT_MIN;
+ ffloat (uc);
+ vfloat = uc;
+ ffloat (sc);
+ vfloat = sc;
+
+ fdouble (UINT_MAX);
+ vdouble = UINT_MAX;
+ fdouble (ui);
+ vdouble = ui;
+ fdouble (si);
+ vdouble = si;
+ }
+
+
Index: gcc/testsuite/g++.dg/warn/Wconversion-real.C
===================================================================
*** gcc/testsuite/g++.dg/warn/Wconversion-real.C (revision 0)
--- gcc/testsuite/g++.dg/warn/Wconversion-real.C (revision 0)
***************
*** 0 ****
--- 1,85 ----
+ /* Test for diagnostics for Wconversion for floating-point.
+ C++ equivalent of gcc/testsuite/gcc.dg/Wconversion-real.c */
+
+ /* { dg-do compile }
+ /* { dg-options "-Wconversion" } */
+
+ float vfloat;
+ double vdouble;
+ long double vlongdouble;
+
+ void ffloat (float f);
+ void fdouble (double d);
+ void flongdouble (long double ld);
+
+ void h (void)
+ {
+ float f = 0;
+ double d = 0;
+ long double ld = 0;
+
+ ffloat (3.1); /* { dg-warning "conversion" } */
+ vfloat = 3.1; /* { dg-warning "conversion" } */
+ ffloat (3.1L); /* { dg-warning "conversion" } */
+ vfloat = 3.1L; /* { dg-warning "conversion" } */
+ fdouble (3.1L); /* { dg-warning "conversion" "" { target large_long_double } } */
+ vdouble = 3.1L; /* { dg-warning "conversion" "" { target large_long_double } } */
+ ffloat (vdouble); /* { dg-warning "conversion" } */
+ vfloat = vdouble; /* { dg-warning "conversion" } */
+ ffloat (vlongdouble); /* { dg-warning "conversion" } */
+ vfloat = vlongdouble; /* { dg-warning "conversion" } */
+ fdouble (vlongdouble); /* { dg-warning "conversion" "" { target large_long_double } } */
+ vdouble = vlongdouble; /* { dg-warning "conversion" "" { target large_long_double } } */
+
+
+ ffloat ((float) 3.1);
+ vfloat = (float) 3.1;
+ ffloat ((float) 3.1L);
+ vfloat = (float) 3.1L;
+ fdouble ((double) 3.1L);
+ vdouble = (double) 3.1L;
+ ffloat ((float) vdouble);
+ vfloat = (float) vdouble;
+ ffloat ((float) vlongdouble);
+ vfloat = (float) vlongdouble;
+ fdouble ((double) vlongdouble);
+ vdouble = (double) vlongdouble;
+
+
+ ffloat (3.0);
+ vfloat = 3.0;
+ ffloat (3.1f);
+ vfloat = 3.1f;
+ ffloat (0.25L);
+ vfloat = 0.25L;
+
+
+ fdouble (3.0);
+ vdouble = 3.0;
+ fdouble (3.1f);
+ vdouble = 3.1f;
+ fdouble (0.25L);
+ vdouble = 0.25L;
+
+ flongdouble (3.0);
+ vlongdouble = 3.0;
+ flongdouble (3.1f);
+ vlongdouble = 3.1f;
+ flongdouble (0.25L);
+ vlongdouble = 0.25L;
+
+ ffloat (f);
+ vfloat = f;
+ fdouble (f);
+ vdouble = f;
+ fdouble (d);
+ vdouble = d;
+ flongdouble (f);
+ vlongdouble = f;
+ flongdouble (d);
+ vlongdouble = d;
+ flongdouble (ld);
+ vlongdouble = ld;
+ }
+
+
Index: gcc/testsuite/g++.dg/warn/Wconversion-integer.C
*** gcc/testsuite/g++.dg/warn/Wconversion-integer.C (revision 0)
--- gcc/testsuite/g++.dg/warn/Wconversion-integer.C (revision 0)
***************
*** 0 ****
--- 1,95 ----
+ /* Test for diagnostics for implicit conversions between integer types
+ C++ equivalent of gcc/testsuite/gcc.dg/Wconversion-integer.c */
+
+ // { dg-do compile }
+ // { dg-options "-fsigned-char -Wconversion" }
+
+ #include <limits.h>
+
+ void fsc (signed char sc);
+ void fuc (unsigned char uc);
+ unsigned fui (unsigned int ui);
+ void fsi (signed int ui);
+
+ void h (int x)
+ {
+ unsigned int ui = 3;
+ int si = 3;
+ unsigned char uc = 3;
+ signed char sc = 3;
+
+ fuc (-1); /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ uc = -1; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ fuc ('\xa0'); /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ uc = '\xa0'; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ uc = x ? 1U : -1; /* { dg-warning "conversion" } */
+ /* { dg-warning "negative integer implicitly converted to unsigned type" "" { target *-*-* } 25 } */
+ uc = x ? SCHAR_MIN : 1U; /* { dg-warning "conversion" } */
+ /* { dg-warning "negative integer implicitly converted to unsigned type" "" { target *-*-* } 27 } */
+
+ uc = x ? 1 : -1; /* { dg-warning "conversion" } */
+
+ uc = x ? SCHAR_MIN : 1; /* { dg-warning "conversion" } */
+
+ fuc ('A');
+ uc = 'A';
+ uc = (unsigned char) -1;
+
+ fui (-1); /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = -1; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = x ? 1U : -1; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = x ? INT_MIN : 1U; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = ui ? SCHAR_MIN : 1U; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = 1U * -1; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = ui + INT_MIN; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = x ? 1 : -1; /* { dg-warning "conversion" } */
+ ui = ui ? SCHAR_MIN : 1; /* { dg-warning "conversion" } */
+
+ ui = -1 * (1 * -1);
+ ui = (unsigned) -1;
+
+ fsc (uc); /* { dg-warning "conversion" } */
+ sc = uc; /* { dg-warning "conversion" } */
+ fuc (sc); /* { dg-warning "conversion" } */
+ uc = sc; /* { dg-warning "conversion" } */
+ fsi (ui); /* { dg-warning "conversion" } */
+ si = ui; /* { dg-warning "conversion" } */
+ fui (si); /* { dg-warning "conversion" } */
+ ui = si; /* { dg-warning "conversion" } */
+ fui (sc); /* { dg-warning "conversion" } */
+ ui = sc; /* { dg-warning "conversion" } */
+
+ fui ('\xa0');/* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = '\xa0'; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+
+ fsi (si);
+ fui (ui);
+ fsi (uc);
+ si = uc;
+ fui (uc);
+ ui = uc;
+ fui ('A');
+ ui = 'A';
+ fsi ('A');
+ si = 'A';
+
+
+ fsi (UINT_MAX - 1); /* { dg-warning "conversion" } */
+ si = UINT_MAX - 1; /* { dg-warning "conversion" } */
+ fsi (UINT_MAX - 1U); /* { dg-warning "conversion" } */
+ si = UINT_MAX - 1U; /* { dg-warning "conversion" } */
+ fsi (UINT_MAX/3U);
+ si = UINT_MAX/3U;
+ fsi (UINT_MAX/3);
+ si = UINT_MAX/3;
+ fui (UINT_MAX - 1);
+ ui = UINT_MAX - 1;
+
+ fsi (0x80000000); /* { dg-warning "conversion" } */
+ si = 0x80000000; /* { dg-warning "conversion" } */
+ }
+
+
+ unsigned fui (unsigned a) { return a + -1; } /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+
+
Index: gcc/testsuite/g++.dg/warn/conv2.C
*** gcc/testsuite/g++.dg/warn/conv2.C (revision 121356)
--- gcc/testsuite/g++.dg/warn/conv2.C (working copy)
***************
*** 1,4 ****
// PR c++/13932
// { dg-options "-Wconversion" }
! int i = 1.; // { dg-warning "converting" }
--- 1,5 ----
// PR c++/13932
// { dg-options "-Wconversion" }
! int i = 1.;
! int j = 1.1; // { dg-warning "conversion" }
Index: gcc/cp/typeck.c
===================================================================
*** gcc/cp/typeck.c (revision 121356)
--- gcc/cp/typeck.c (working copy)
***************
*** 3853,3865 **** build_binary_op (enum tree_code code, tr
warning (0, "NULL used in arithmetic");
if (! converted)
{
if (TREE_TYPE (op0) != result_type)
! op0 = cp_convert (result_type, op0);
! if (TREE_TYPE (op1) != result_type)
! op1 = cp_convert (result_type, op1);
if (op0 == error_mark_node || op1 == error_mark_node)
return error_mark_node;
}
--- 3853,3871 ----
warning (0, "NULL used in arithmetic");
if (! converted)
{
if (TREE_TYPE (op0) != result_type)
! {
! convert_and_check (result_type, op0);
! op0 = cp_convert (result_type, op0);
! }
! if (TREE_TYPE (op1) != result_type)
! {
! convert_and_check (result_type, op1);
! op1 = cp_convert (result_type, op1);
! }
if (op0 == error_mark_node || op1 == error_mark_node)
return error_mark_node;
}
Index: gcc/cp/call.c
*** gcc/cp/call.c (revision 121356)
--- gcc/cp/call.c (working copy)
***************
*** 4261,4275 **** convert_like_real (conversion *convs, tr
/* Warn about assigning a floating-point type to an integer type. */
if (TREE_CODE (TREE_TYPE (expr)) == REAL_TYPE
&& TREE_CODE (t) == INTEGER_TYPE)
{
! if (fn)
! warning (OPT_Wconversion, "passing %qT for argument %P to %qD",
! TREE_TYPE (expr), argnum, fn);
! else
! warning (OPT_Wconversion, "converting to %qT from %qT", t, TREE_TYPE (expr));
}
}
switch (convs->kind)
{
--- 4261,4274 ----
/* Warn about assigning a floating-point type to an integer type. */
if (TREE_CODE (TREE_TYPE (expr)) == REAL_TYPE
&& TREE_CODE (t) == INTEGER_TYPE)
{
! convert_and_check (t, expr);
! /* There is another call to convert_and_check below, we just
! warn once. */
! issue_conversion_warnings = false;
}
}
switch (convs->kind)
{
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-06 9:14 [PING^3] Wconversion: fixes for C++ front-end Manuel López-Ibáñez
@ 2007-02-06 18:24 ` Paolo Carlini
2007-02-06 19:21 ` Gabriel Dos Reis
2007-02-06 19:50 ` Manuel López-Ibáñez
0 siblings, 2 replies; 26+ messages in thread
From: Paolo Carlini @ 2007-02-06 18:24 UTC (permalink / raw)
To: Manuel López-Ibáñez; +Cc: gcc-patches, Gabriel Dos Reis
Manuel López-Ibáñez wrote:
> http://gcc.gnu.org/ml/gcc-patches/2006-12/msg00799.html
>
> Rediff, rebootstrapped and re-regression-tested against revision
> 121356 on i686-pc-linux-gnu.
>
> Context and unified diffs follow.
Is there something I'm missing or the new testcase Wconversion-integer.C
doesn't reflect the consensus resulting from the discussions in the
audit trail of libstdc++/30464?!? Shall we wait a bit and add the final
version of it???
Paolo.
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-06 18:24 ` Paolo Carlini
@ 2007-02-06 19:21 ` Gabriel Dos Reis
2007-02-06 19:57 ` Manuel López-Ibáñez
2007-02-06 19:50 ` Manuel López-Ibáñez
1 sibling, 1 reply; 26+ messages in thread
From: Gabriel Dos Reis @ 2007-02-06 19:21 UTC (permalink / raw)
To: Paolo Carlini; +Cc: Manuel López-Ibáñez, gcc-patches
Paolo Carlini <pcarlini@suse.de> writes:
| Manuel López-Ibáñez wrote:
|
| > http://gcc.gnu.org/ml/gcc-patches/2006-12/msg00799.html
| >
| > Rediff, rebootstrapped and re-regression-tested against revision
| > 121356 on i686-pc-linux-gnu.
| >
| > Context and unified diffs follow.
|
| Is there something I'm missing or the new testcase
| Wconversion-integer.C doesn't reflect the consensus resulting from the
| discussions in the audit trail of libstdc++/30464?!? Shall we wait a
| bit and add the final version of it???
Waiting will not magically turn the consensus, without new data.
I was hoping the patch will be upgraded to reflect the consensus.
As an aside, I just finised a build of CVS src/gdb with SVN GCC, and I
got lot of those noise too.
-- Gaby
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-06 18:24 ` Paolo Carlini
2007-02-06 19:21 ` Gabriel Dos Reis
@ 2007-02-06 19:50 ` Manuel López-Ibáñez
1 sibling, 0 replies; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-02-06 19:50 UTC (permalink / raw)
To: Paolo Carlini; +Cc: gcc-patches, Gabriel Dos Reis
On 06/02/07, Paolo Carlini <pcarlini@suse.de> wrote:
> Manuel López-Ibáñez wrote:
>
> > http://gcc.gnu.org/ml/gcc-patches/2006-12/msg00799.html
> >
> > Rediff, rebootstrapped and re-regression-tested against revision
> > 121356 on i686-pc-linux-gnu.
> >
> > Context and unified diffs follow.
>
> Is there something I'm missing or the new testcase Wconversion-integer.C
> doesn't reflect the consensus resulting from the discussions in the
> audit trail of libstdc++/30464?!? Shall we wait a bit and add the final
> version of it???
This patch is months old (it's been in the patch queue since
november). As you can see, it doesn't touch the warning logic (which
is in c-common.c), it just updates places in the C++ front-end where
convert_and_check should be called, but it wasn't. It also adds
testcases for C++, some of them will work without this patch.
As for PR30464, I already have a patch (and I have already said this
more than once) that addresses the concerns raised in PR30464. Since
the patches are logically independent (apart from the testcases, that
will need minor modifications), it makes sense to me to have
Wconversion completed and then fine-tune it as requested in PR30464 as
an incremental improvement (so each step makes sense on its own). I
just didn't see the point on submitting the patch for PR30464 until
the pending one was reviewed.
Cheers,
Manuel.
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-06 19:21 ` Gabriel Dos Reis
@ 2007-02-06 19:57 ` Manuel López-Ibáñez
2007-02-06 22:22 ` Gabriel Dos Reis
0 siblings, 1 reply; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-02-06 19:57 UTC (permalink / raw)
To: Gabriel Dos Reis; +Cc: Paolo Carlini, gcc-patches
On 06 Feb 2007 13:20:54 -0600, Gabriel Dos Reis <gdr@cs.tamu.edu> wrote:
> Paolo Carlini <pcarlini@suse.de> writes:
>
> | Manuel López-Ibáñez wrote:
> |
> | > http://gcc.gnu.org/ml/gcc-patches/2006-12/msg00799.html
> | >
> | > Rediff, rebootstrapped and re-regression-tested against revision
> | > 121356 on i686-pc-linux-gnu.
> | >
> | > Context and unified diffs follow.
> |
> | Is there something I'm missing or the new testcase
> | Wconversion-integer.C doesn't reflect the consensus resulting from the
> | discussions in the audit trail of libstdc++/30464?!? Shall we wait a
> | bit and add the final version of it???
>
> Waiting will not magically turn the consensus, without new data.
> I was hoping the patch will be upgraded to reflect the consensus.
I am waiting for patches to get reviewed. I hope that at least this is
not my fault. If I can do something to get the patches reviewed
faster, please, let me know.
As I said before, this patch has nothing to do with the warning logic
for Wconversion, it just updates places in the C++ front-end where
convert_and_check should be called, add testcases for C++ and updates
the documentation. Yes, I could combine both things: upgrade the
warning logic and fix the C++ front-end, but why? I believed that a
patch should be as simple as possible. Having two patches is simpler.
Cheers,
Manuel.
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-06 19:57 ` Manuel López-Ibáñez
@ 2007-02-06 22:22 ` Gabriel Dos Reis
2007-02-06 22:57 ` Manuel López-Ibáñez
0 siblings, 1 reply; 26+ messages in thread
From: Gabriel Dos Reis @ 2007-02-06 22:22 UTC (permalink / raw)
To: Manuel López-Ibáñez; +Cc: Paolo Carlini, gcc-patches
On Tue, 6 Feb 2007, Manuel López-Ibáñez wrote:
| I am waiting for patches to get reviewed. I hope that at least this is
| not my fault. If I can do something to get the patches reviewed
| faster, please, let me know.
The bits:
if (TREE_TYPE (op0) != result_type)
- op0 = cp_convert (result_type, op0);
- if (TREE_TYPE (op1) != result_type)
- op1 = cp_convert (result_type, op1);
+ {
+ convert_and_check (result_type, op0);
+ op0 = cp_convert (result_type, op0);
+ }
+ if (TREE_TYPE (op1) != result_type)
+ {
+ convert_and_check (result_type, op1);
+ op1 = cp_convert (result_type, op1);
+ }
convert op0, but throw the result away, then call cp_convert
to convert again. That looks curious to me. Why would we want to do
that?
-- Gaby
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-06 22:22 ` Gabriel Dos Reis
@ 2007-02-06 22:57 ` Manuel López-Ibáñez
2007-02-06 23:06 ` Manuel López-Ibáñez
2007-02-06 23:30 ` [PING^3] " Gabriel Dos Reis
0 siblings, 2 replies; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-02-06 22:57 UTC (permalink / raw)
To: Gabriel Dos Reis; +Cc: Paolo Carlini, gcc-patches
On 06/02/07, Gabriel Dos Reis <gdr@cs.tamu.edu> wrote:
> On Tue, 6 Feb 2007, Manuel López-Ibáñez wrote:
>
> | I am waiting for patches to get reviewed. I hope that at least this is
> | not my fault. If I can do something to get the patches reviewed
> | faster, please, let me know.
>
>
> The bits:
>
> if (TREE_TYPE (op0) != result_type)
> - op0 = cp_convert (result_type, op0);
> - if (TREE_TYPE (op1) != result_type)
> - op1 = cp_convert (result_type, op1);
> + {
> + convert_and_check (result_type, op0);
> + op0 = cp_convert (result_type, op0);
> + }
> + if (TREE_TYPE (op1) != result_type)
> + {
> + convert_and_check (result_type, op1);
> + op1 = cp_convert (result_type, op1);
> + }
>
>
> convert op0, but throw the result away, then call cp_convert
> to convert again. That looks curious to me. Why would we want to do
> that?
Well, I would love to just use convert_and_check. But it didn't seem
to me that cp_convert was the same as the convert function invoked
from convert_and_check. (Both are defined in cp/cvt.c). So I preferred
to be on the safe side rather than experiment with my ignorance.
If you think that it is safe to replace cp_convert with convert, then
it is safe to use the return value of convert_and_check.
Thanks for looking at this,
Manuel.
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-06 22:57 ` Manuel López-Ibáñez
@ 2007-02-06 23:06 ` Manuel López-Ibáñez
2007-02-06 23:32 ` Gabriel Dos Reis
2007-02-06 23:30 ` [PING^3] " Gabriel Dos Reis
1 sibling, 1 reply; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-02-06 23:06 UTC (permalink / raw)
To: Gabriel Dos Reis; +Cc: Paolo Carlini, gcc-patches
On 06/02/07, Manuel López-Ibáñez <lopezibanez@gmail.com> wrote:
> On 06/02/07, Gabriel Dos Reis <gdr@cs.tamu.edu> wrote:
> > On Tue, 6 Feb 2007, Manuel López-Ibáñez wrote:
> >
> > | I am waiting for patches to get reviewed. I hope that at least this is
> > | not my fault. If I can do something to get the patches reviewed
> > | faster, please, let me know.
> >
> >
> > The bits:
> >
> > if (TREE_TYPE (op0) != result_type)
> > - op0 = cp_convert (result_type, op0);
> > - if (TREE_TYPE (op1) != result_type)
> > - op1 = cp_convert (result_type, op1);
> > + {
> > + convert_and_check (result_type, op0);
> > + op0 = cp_convert (result_type, op0);
> > + }
> > + if (TREE_TYPE (op1) != result_type)
> > + {
> > + convert_and_check (result_type, op1);
> > + op1 = cp_convert (result_type, op1);
> > + }
> >
> >
> > convert op0, but throw the result away, then call cp_convert
> > to convert again. That looks curious to me. Why would we want to do
> > that?
>
> Well, I would love to just use convert_and_check. But it didn't seem
> to me that cp_convert was the same as the convert function invoked
> from convert_and_check. (Both are defined in cp/cvt.c). So I preferred
> to be on the safe side rather than experiment with my ignorance.
>
> If you think that it is safe to replace cp_convert with convert, then
> it is safe to use the return value of convert_and_check.
>
I am sure I already did this a long time ago, but to be sure, I did it
again, and some tests fail if we use the return value of
convert_and_check directly rather than calling cp_convert.
Cheers,
Manuel.
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-06 22:57 ` Manuel López-Ibáñez
2007-02-06 23:06 ` Manuel López-Ibáñez
@ 2007-02-06 23:30 ` Gabriel Dos Reis
1 sibling, 0 replies; 26+ messages in thread
From: Gabriel Dos Reis @ 2007-02-06 23:30 UTC (permalink / raw)
To: Manuel López-Ibáñez; +Cc: Paolo Carlini, gcc-patches
On Tue, 6 Feb 2007, Manuel López-Ibáñez wrote:
| On 06/02/07, Gabriel Dos Reis <gdr@cs.tamu.edu> wrote:
| > On Tue, 6 Feb 2007, Manuel López-Ibáñez wrote:
| >
| > | I am waiting for patches to get reviewed. I hope that at least this is
| > | not my fault. If I can do something to get the patches reviewed
| > | faster, please, let me know.
| >
| >
| > The bits:
| >
| > if (TREE_TYPE (op0) != result_type)
| > - op0 = cp_convert (result_type, op0);
| > - if (TREE_TYPE (op1) != result_type)
| > - op1 = cp_convert (result_type, op1);
| > + {
| > + convert_and_check (result_type, op0);
| > + op0 = cp_convert (result_type, op0);
| > + }
| > + if (TREE_TYPE (op1) != result_type)
| > + {
| > + convert_and_check (result_type, op1);
| > + op1 = cp_convert (result_type, op1);
| > + }
| >
| >
| > convert op0, but throw the result away, then call cp_convert
| > to convert again. That looks curious to me. Why would we want to do
| > that?
|
| Well, I would love to just use convert_and_check. But it didn't seem
| to me that cp_convert was the same as the convert function invoked
| from convert_and_check.
No, there aren't; but they seem to overlap.
What is needed is to understand why you can or cannot give the result
of convert_and_check to cp_convert. Just computing one and throwing
the result does not look right to me.
-- Gaby
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-06 23:06 ` Manuel López-Ibáñez
@ 2007-02-06 23:32 ` Gabriel Dos Reis
2007-02-07 0:29 ` Manuel López-Ibáñez
0 siblings, 1 reply; 26+ messages in thread
From: Gabriel Dos Reis @ 2007-02-06 23:32 UTC (permalink / raw)
To: Manuel López-Ibáñez; +Cc: Paolo Carlini, gcc-patches
On Tue, 6 Feb 2007, Manuel López-Ibáñez wrote:
| I am sure I already did this a long time ago, but to be sure, I did it
| again, and some tests fail if we use the return value of
| convert_and_check directly rather than calling cp_convert.
that should be expected. what is needed is the relationship of
convert_and_check and cp_convert.
-- Gaby
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-06 23:32 ` Gabriel Dos Reis
@ 2007-02-07 0:29 ` Manuel López-Ibáñez
2007-02-07 0:46 ` Gabriel Dos Reis
0 siblings, 1 reply; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-02-07 0:29 UTC (permalink / raw)
To: Gabriel Dos Reis; +Cc: Paolo Carlini, gcc-patches
On 06/02/07, Gabriel Dos Reis <gdr@cs.tamu.edu> wrote:
> On Tue, 6 Feb 2007, Manuel López-Ibáñez wrote:
>
> | I am sure I already did this a long time ago, but to be sure, I did it
> | again, and some tests fail if we use the return value of
> | convert_and_check directly rather than calling cp_convert.
>
> that should be expected. what is needed is the relationship of
> convert_and_check and cp_convert.
/* C++ conversions, preference to static cast conversions. */
tree
cp_convert (tree type, tree expr)
{
return ocp_convert (type, expr, CONV_OLD_CONVERT, LOOKUP_NORMAL);
}
while:
/* Create an expression whose value is that of EXPR,
converted to type TYPE. The TREE_TYPE of the value
is always TYPE. This function implements all reasonable
conversions; callers should filter out those that are
not permitted by the language being compiled.
Most of this routine is from build_reinterpret_cast.
The backend cannot call cp_convert (what was convert) because
conversions to/from basetypes may involve memory references
(vbases) and adding or subtracting small values (multiple
inheritance), but it calls convert from the constant folding code
on subtrees of already built trees after it has ripped them apart.
Also, if we ever support range variables, we'll probably also have to
do a little bit more work. */
tree
convert (tree type, tree expr)
{
tree intype;
if (type == error_mark_node || expr == error_mark_node)
return error_mark_node;
intype = TREE_TYPE (expr);
if (POINTER_TYPE_P (type) && POINTER_TYPE_P (intype))
return fold_if_not_in_template (build_nop (type, expr));
return ocp_convert (type, expr, CONV_OLD_CONVERT,
LOOKUP_NORMAL|LOOKUP_NO_CONVERSION);
}
So the basic differences are the call to fold_if_not_in_template and
the use of LOOKUP_NO_CONVERSION when calling ocp_convert. I honestly
cannot see how to relate cp_convert and convert. Do you have any
ideas?
Cheers,
Manuel.
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-07 0:29 ` Manuel López-Ibáñez
@ 2007-02-07 0:46 ` Gabriel Dos Reis
2007-02-07 9:13 ` Manuel López-Ibáñez
0 siblings, 1 reply; 26+ messages in thread
From: Gabriel Dos Reis @ 2007-02-07 0:46 UTC (permalink / raw)
To: Manuel López-Ibáñez; +Cc: Paolo Carlini, gcc-patches
"Manuel López-Ibáñez" <lopezibanez@gmail.com> writes:
[...]
| So the basic differences are the call to fold_if_not_in_template and
| the use of LOOKUP_NO_CONVERSION when calling ocp_convert. I honestly
| cannot see how to relate cp_convert and convert.
In that case, there does not seem reason to believe that the chain you
introduced is correct. We must conservatitely regard it as incorrect
until proven otherwise. the conversion code in cp/ has proven to be
tricky and sources of bugs, hence the caution that must be exercise.
I suspect the real understanding comes from looking at ocp_convert,
which tells you what it returns on the convtype flag.
-- Gaby
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-07 0:46 ` Gabriel Dos Reis
@ 2007-02-07 9:13 ` Manuel López-Ibáñez
2007-02-07 16:35 ` Gabriel Dos Reis
0 siblings, 1 reply; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-02-07 9:13 UTC (permalink / raw)
To: Gabriel Dos Reis; +Cc: Paolo Carlini, gcc-patches
On 06 Feb 2007 18:46:44 -0600, Gabriel Dos Reis <gdr@cs.tamu.edu> wrote:
> "Manuel López-Ibáñez" <lopezibanez@gmail.com> writes:
>
> [...]
>
> | So the basic differences are the call to fold_if_not_in_template and
> | the use of LOOKUP_NO_CONVERSION when calling ocp_convert. I honestly
> | cannot see how to relate cp_convert and convert.
>
> In that case, there does not seem reason to believe that the chain you
> introduced is correct. We must conservatitely regard it as incorrect
> until proven otherwise. the conversion code in cp/ has proven to be
> tricky and sources of bugs, hence the caution that must be exercise.
That is the reason for not using the return value of
convert_and_check. But, yes, it could be done better. Thanks for
helping me finding out a better solution.
> I suspect the real understanding comes from looking at ocp_convert,
> which tells you what it returns on the convtype flag.
>
Both cp_convert and convert call ocp_convert with convtype =
CONV_OLD_CONVERT. However, they use different flags as the third
argument for ocp_convert: LOOKUP_NORMAL versus (LOOKUP_NORMAL |
LOOKUP_NO_CONVERSION).
I could detect the case where one of the types is POINTER_TYPE_P, and
call cp_convert instead of convert_and_check. However, I don't know
how to solve the mismatch in the flags in the call to ocp_convert.
A different approach would be to have a cp_convert_and_check function
that uses cp_convert instead of convert. Perhaps that is the right
solution.
Please, let me know your opinion.
Cheers,
Manuel.
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-07 9:13 ` Manuel López-Ibáñez
@ 2007-02-07 16:35 ` Gabriel Dos Reis
2007-02-08 11:55 ` Manuel López-Ibáñez
0 siblings, 1 reply; 26+ messages in thread
From: Gabriel Dos Reis @ 2007-02-07 16:35 UTC (permalink / raw)
To: Manuel López-Ibáñez; +Cc: Paolo Carlini, gcc-patches
On Wed, 7 Feb 2007, Manuel López-Ibáñez wrote:
| On 06 Feb 2007 18:46:44 -0600, Gabriel Dos Reis <gdr@cs.tamu.edu> wrote:
| > "Manuel López-Ibáñez" <lopezibanez@gmail.com> writes:
| >
| > [...]
| >
| > | So the basic differences are the call to fold_if_not_in_template and
| > | the use of LOOKUP_NO_CONVERSION when calling ocp_convert. I honestly
| > | cannot see how to relate cp_convert and convert.
| >
| > In that case, there does not seem reason to believe that the chain you
| > introduced is correct. We must conservatitely regard it as incorrect
| > until proven otherwise. the conversion code in cp/ has proven to be
| > tricky and sources of bugs, hence the caution that must be exercise.
|
| That is the reason for not using the return value of
| convert_and_check.
actually it is a reason to be careful about calling the conversion
functions. I suspect I did not make my previous points clear enough:
(1) you must understand why you call each of the functions
(2) given that both convert() and cp_convert() convert, you must
understand their relations. Just quoting the definitions at me
is NOT what I was trying to get at.
(4) if you must call one function that does conversion, potentially
issues diagnostic but throws its result away, just to call
another conversion function that does similar computations, then
something is wrong.
(5) you must be able to explain your patch, what it does and why it
does it.
The difference here is in the flag parameters. Before a new function
cp_convert_and_check is introduced, you must explain why the existing
ones are insufficient -- that brings you back to understanding
ocp_convert.
Conversions in C++ can involve not just standard conversions (implicit
conversions defined for built-in types), but also user-defined
conversions. There is a well-defined ordering in which they must
happen -- see clause 4 of the C++ standard.
An implicit conversion sequence in C++ (they actions you need to take
to bring arguments to parameter types, etc.) in general is:
(1) standard conversion sequence, followed by
(2) a possible user-defined conversion, followed by
(3) another standard conversion sequence.
In both (1) and (3) you want to catch non-value preserving
conversions. And ocp_convert's job is to implement each step of the
conversion sequences.
Both convert() and cp_convert() essentially asks for doing the same
kind of conversions. They differ in "who" is allowed to participating
in the conversion sequence. More precisely, convert() cares only
about _standard conversion_ sequences. cp_convert() tolerates
user-defined conversions. It looks to me that you wan to have
ocp_convert() actually warns if necessary, instead of doing the
computations twice and throwing one results away.
-- Gaby
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-07 16:35 ` Gabriel Dos Reis
@ 2007-02-08 11:55 ` Manuel López-Ibáñez
2007-02-08 11:58 ` Gabriel Dos Reis
2007-02-08 12:02 ` Gabriel Dos Reis
0 siblings, 2 replies; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-02-08 11:55 UTC (permalink / raw)
To: Gabriel Dos Reis; +Cc: gcc-patches
On 07/02/07, Gabriel Dos Reis <gdr@cs.tamu.edu> wrote:
> On Wed, 7 Feb 2007, Manuel López-Ibáñez wrote:
>
>
> (1) standard conversion sequence, followed by
> (2) a possible user-defined conversion, followed by
> (3) another standard conversion sequence.
>
> In both (1) and (3) you want to catch non-value preserving
> conversions. And ocp_convert's job is to implement each step of the
> conversion sequences.
>
> Both convert() and cp_convert() essentially asks for doing the same
> kind of conversions. They differ in "who" is allowed to participating
> in the conversion sequence. More precisely, convert() cares only
> about _standard conversion_ sequences. cp_convert() tolerates
> user-defined conversions. It looks to me that you wan to have
> ocp_convert() actually warns if necessary, instead of doing the
> computations twice and throwing one results away.
Thanks for the explanation. My knowledge about the C++ front-end is
very limited and the conversion code is specially confusing to me.
Thus, any help is greatly appreciated.
I am not so sure that I want to have ocp_convert to warn if necessary.
In the same way as the C front-end has both convert_and_check and
convert, and the former is used in just a few places, I don't think
that invoking the warnings for every call to ocp_convert can actually
work.
Another problem is that I would need to encapsulate the warning logic
in convert_and_check on its own function, so it can be called from
convert_and_check and ocp_convert. That is fine except for the fact
that the C++ front-end already uses convert_and_check in a few places,
which in turn calls convert, which in turn calls ocp_convert, that
would generate warnings again. How could we fix this situation?
Third, the way that convert_and_check works is to invoke the original
convert and afterwards check the result and warn about
overflow/conversions. That cannot be implemented within ocp_convert
without modifying the whole ocp_convert, since there is not a single
conversion result but a lot of 'return' statements. It can be done
(for example, invoking the conversion warnings before each return) but
do you really want me to do this?
I would like to implement this in the best possible way but I don't
see how can I solve the problems described above. Do you have any
suggestions? Again, thanks for your help on solving this.
Cheers,
Manuel.
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-08 11:55 ` Manuel López-Ibáñez
@ 2007-02-08 11:58 ` Gabriel Dos Reis
2007-02-08 12:39 ` Manuel López-Ibáñez
2007-02-08 12:02 ` Gabriel Dos Reis
1 sibling, 1 reply; 26+ messages in thread
From: Gabriel Dos Reis @ 2007-02-08 11:58 UTC (permalink / raw)
To: Manuel López-Ibáñez; +Cc: gcc-patches
"Manuel López-Ibáñez" <lopezibanez@gmail.com> writes:
[...]
| I am not so sure that I want to have ocp_convert to warn if necessary.
| In the same way as the C front-end has both convert_and_check and
| convert, and the former is used in just a few places, I don't think
| that invoking the warnings for every call to ocp_convert can actually
| work.
You're not going to warn for every call to ocp_convert. ocp_convert
will warn only if necessary. Please have another look at the
ocp_convert definition. You cannot simply use convert_and_check,
because that function does not cover C++ conversions -- which is why
cp_convert existed.
You should abandon the idea of calling it twice for the same
conversion.
So, either you merge cp_convert and convert -- which is even riskier
as you say you're not familiar with the conversion functions, and this
area has proven fertile of bugs. Or, you go directly to the function
which both convert and cp_convert call to do the real work.
[...]
| I would like to implement this in the best possible way but I don't
| see how can I solve the problems described above. Do you have any
| suggestions?
ones that you will not summarily dismiss?
-- Gaby
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-08 11:55 ` Manuel López-Ibáñez
2007-02-08 11:58 ` Gabriel Dos Reis
@ 2007-02-08 12:02 ` Gabriel Dos Reis
2007-02-08 12:48 ` Manuel López-Ibáñez
1 sibling, 1 reply; 26+ messages in thread
From: Gabriel Dos Reis @ 2007-02-08 12:02 UTC (permalink / raw)
To: Manuel López-Ibáñez; +Cc: gcc-patches
"Manuel López-Ibáñez" <lopezibanez@gmail.com> writes:
[...]
| Another problem is that I would need to encapsulate the warning logic
| in convert_and_check on its own function, so it can be called from
| convert_and_check and ocp_convert. That is fine except for the fact
| that the C++ front-end already uses convert_and_check in a few places,
| which in turn calls convert, which in turn calls ocp_convert, that
| would generate warnings again. How could we fix this situation?
Make a list of all the places where the C++ front-end calls
convert_and_check, document why.
Make a list of all the places where the C++ front-end does not call
convert_and_check (that is already contained in your patch).
Document the differences in the "kinds" of conversions being checked
in both cases. That should give you a good start.
-- Gaby
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-08 11:58 ` Gabriel Dos Reis
@ 2007-02-08 12:39 ` Manuel López-Ibáñez
0 siblings, 0 replies; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-02-08 12:39 UTC (permalink / raw)
To: Gabriel Dos Reis; +Cc: gcc-patches
On 08 Feb 2007 05:55:35 -0600, Gabriel Dos Reis <gdr@cs.tamu.edu> wrote:
> "Manuel López-Ibáñez" <lopezibanez@gmail.com> writes:
>
> | I am not so sure that I want to have ocp_convert to warn if necessary.
> | In the same way as the C front-end has both convert_and_check and
> | convert, and the former is used in just a few places, I don't think
> | that invoking the warnings for every call to ocp_convert can actually
> | work.
>
> You're not going to warn for every call to ocp_convert. ocp_convert
> will warn only if necessary. Please have another look at the
> ocp_convert definition. You cannot simply use convert_and_check,
> because that function does not cover C++ conversions -- which is why
> cp_convert existed.
Thanks to your previous explanation I understand that I cannot simply
use convert_and_check. I am thinking on how to implement your
proposal. However, I don't know when the caller wants ocp_convert to
warn or not. The caller could pass a flag, but then every invokation
of ocp_convert (and cp_convert and convert and probably something
else) would need to be modified.
> You should abandon the idea of calling it twice for the same
> conversion.
OK. It is abandoned already. I was not suggesting that any more. I
cannot understand why you think I was.
> So, either you merge cp_convert and convert -- which is even riskier
> as you say you're not familiar with the conversion functions, and this
> area has proven fertile of bugs. Or, you go directly to the function
> which both convert and cp_convert call to do the real work.
I went there. I read the function and look for the places to do a call
to a hypothetical function that gives the warnings. Assuming that is
implemented somehow and there is a mechanism to know when the caller
wants to get warnings, what should I do now with convert_and_check? It
will call convert, which in turn calls ocp_convert which in turn needs
to know that warnings are not needed since convert_and_check is going
to handle that. However, convert_and_check also calls the C front-end
version of convert. And I think we don't want to modify the C
front-end's convert just to add a flag to signal ocp_convert that we
don't want warnings.
> | I would like to implement this in the best possible way but I don't
> | see how can I solve the problems described above. Do you have any
> | suggestions?
>
> ones that you will not summarily dismiss?
Gabriel, please. I am not dismissing anything, I considered your
suggestions and I started to think how to implement them and I made a
list of potential problems. Then I asked you if you have any
suggestions on how to solve them. Where is the dismissal? Where is the
summarily part? I honestly think that you are always reading my
messages in the wrong tone. You should read them with the tone of
someone that is truly confused and trying to work with something that
is new and without any pretentious, sarcastic or ironic ring.
Manuel.
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-08 12:02 ` Gabriel Dos Reis
@ 2007-02-08 12:48 ` Manuel López-Ibáñez
2007-02-08 14:06 ` Gabriel Dos Reis
0 siblings, 1 reply; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-02-08 12:48 UTC (permalink / raw)
To: Gabriel Dos Reis; +Cc: gcc-patches
On 08 Feb 2007 05:58:54 -0600, Gabriel Dos Reis <gdr@cs.tamu.edu> wrote:
> "Manuel López-Ibáñez" <lopezibanez@gmail.com> writes:
>
> [...]
>
> | Another problem is that I would need to encapsulate the warning logic
> | in convert_and_check on its own function, so it can be called from
> | convert_and_check and ocp_convert. That is fine except for the fact
> | that the C++ front-end already uses convert_and_check in a few places,
> | which in turn calls convert, which in turn calls ocp_convert, that
> | would generate warnings again. How could we fix this situation?
>
> Make a list of all the places where the C++ front-end calls
> convert_and_check, document why.
:-( I can prepare that list. It is short:
* call.c (convert_like_real)
* typeck.c (build_ptrmemfunc1)
* c-common.c (c_add_case_label)
However, I cannot know why the C++ front-end calls convert_and_check
(apart from the obvious reason of getting warnings for conversions).
> Make a list of all the places where the C++ front-end does not call
> convert_and_check (that is already contained in your patch).
I don't understand this. Do you mean the places where the C++
front-end calls a conversion function instead of convert_and_check ?
(and which ones? convert, cp_convert, ...). There are around 66 calls
to convert and 52 calls to cp_convert. :-(
Manuel.
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-08 12:48 ` Manuel López-Ibáñez
@ 2007-02-08 14:06 ` Gabriel Dos Reis
2007-02-10 8:53 ` Manuel López-Ibáñez
0 siblings, 1 reply; 26+ messages in thread
From: Gabriel Dos Reis @ 2007-02-08 14:06 UTC (permalink / raw)
To: Manuel López-Ibáñez; +Cc: gcc-patches
"Manuel López-Ibáñez" <lopezibanez@gmail.com> writes:
[...]
| > Make a list of all the places where the C++ front-end does not call
| > convert_and_check (that is already contained in your patch).
|
| I don't understand this. Do you mean the places where the C++
| front-end calls a conversion function instead of convert_and_check ?
Yes. Essentially, you can trace brack from ocp_convert, with a grep...
For ocp_convert() I have: force_rvalue(), cp_convert(), convert(),
convert_force(), initialize_handler_parm(), expand_default_init(),
convert_nontype_argument(), build_static_cast_1,
convert_for_initialization().
| (and which ones? convert, cp_convert, ...). There are around 66 calls
| to convert and 52 calls to cp_convert. :-(
-- Gaby
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-08 14:06 ` Gabriel Dos Reis
@ 2007-02-10 8:53 ` Manuel López-Ibáñez
2007-02-10 9:02 ` Manuel López-Ibáñez
2007-02-18 11:47 ` [PING^4] " Manuel López-Ibáñez
0 siblings, 2 replies; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-02-10 8:53 UTC (permalink / raw)
To: Gabriel Dos Reis; +Cc: gcc-patches
[-- Attachment #1: Type: text/plain, Size: 2714 bytes --]
On 08 Feb 2007 07:30:44 -0600, Gabriel Dos Reis <gdr@cs.tamu.edu> wrote:
> "Manuel López-Ibáñez" <lopezibanez@gmail.com> writes:
>
> [...]
>
> | > Make a list of all th without extensively modifying the C and C++ front-ends.e places where the C++ front-end does not call
> | > convert_and_check (that is already contained in your patch).
> |
> | I don't understand this. Do you mean the places where the C++
> | front-end calls a conversion function instead of convert_and_check ?
>
> Yes. Essentially, you can trace brack from ocp_convert, with a grep...
>
> For ocp_convert() I have: force_rvalue(), cp_convert(), convert(),
> convert_force(), initialize_handler_parm(), expand_default_init(),
> convert_nontype_argument(), build_static_cast_1,
> convert_for_initialization().
>
I have looked to those functions and I still don't understand what you
want me to do. I tried modifying ocp_convert to add the warnings there
and a new argument 'issue_conversion_warnings' as in
'convert_like_real', but the required modifications are too large and
intrusive. I really don't know how to implement your suggestion.
As an alternative, I have prepared the following patch. It addresses
the concerns about the original patch in two ways. First, it adds a
new function cp_convert_and_check, so 1) no need to call convert when
we actually want cp_convert, and 2) no result is thrown away.
Secondly, in 'convert_like_real', it uses the already existing call to
convert_and_check to detect conversions from floating-point to
integer, no additional call to convert_and_check is needed any more.
In order for this to work for references, we need to pass the original
value of issue_conversion_warnings to subsequent calls to
convert_like_real.
It bootstraps and passes all regression tests. Do you see any
potential problem with this version?
Cheers,
Manuel.
:ADDPATCH C++:
2007-02-10 Manuel Lopez-Ibanez <manu@gcc.gnu.org>
* doc/invoke.texi (-Wconversion): Document warnings specific to C++.
* c-common.c (convert_and_check): Move warning logic to...
(warnings_for_convert_and_check): ...here. Define.
* c-common.h (warnings_for_convert_and_check): Declare.
cp/
* cvt.c (cp_convert_and_check) : Define.
* cp-tree.h (cp_convert_and_check): Declare.
* call.c (convert_like_real): Use convert_and_check instead of
custom warning.
* typeck.c (build_binary_op): Use cp_convert_and_check to warn for
overflow and changes of value during conversion.
testsuite/
* g++.dg/warn/Wconversion-integer.C: New
* g++.dg/warn/Wconversion-real.C: New.
* g++.dg/warn/Wconversion-real-integer.C: New.
* g++.dg/warn/conv2.C: Modified.
[-- Attachment #2: wcoercion-4-gplusplus-try7.diff --]
[-- Type: text/plain, Size: 14920 bytes --]
Index: gcc/doc/invoke.texi
===================================================================
--- gcc/doc/invoke.texi (revision 121678)
+++ gcc/doc/invoke.texi (working copy)
@@ -3213,6 +3213,12 @@ like @code{unsigned ui = -1}; and conver
((int) x)} and @code{ui = (unsigned) -1}, or if the value is not
changed by the conversion like in @code{abs (2.0)}.
+For C++, also warn for conversions between @code{NULL} and non-pointer
+types; confusing overload resolution for user-defined conversions; and
+conversions that will never use a type conversion operator:
+conversions to @code{void}, the same type, a base class or a reference
+to them.
+
@item -Wempty-body
@opindex Wempty-body
An empty body occurs in an @samp{if} or @samp{else} statement.
Index: gcc/testsuite/g++.dg/warn/Wconversion-real-integer.C
===================================================================
--- gcc/testsuite/g++.dg/warn/Wconversion-real-integer.C (revision 0)
+++ gcc/testsuite/g++.dg/warn/Wconversion-real-integer.C (revision 0)
@@ -0,0 +1,73 @@
+/* Test for diagnostics for Wconversion between floating-point and
+ integers. C++ equivalent of
+ gcc/testsuite/gcc.dg/Wconversion-real-integer.c */
+
+/* { dg-do compile }
+/* { dg-options "-Wconversion" } */
+
+#include <limits.h>
+
+void fsi (signed int x);
+void fui (unsigned int x);
+void ffloat (float x);
+void fdouble (double x);
+
+float vfloat;
+double vdouble;
+
+void h (void)
+{
+ unsigned int ui = 3;
+ int si = 3;
+ unsigned char uc = 3;
+ signed char sc = 3;
+ float f = 3;
+ double d = 3;
+
+ fsi (3.1f); /* { dg-warning "conversion" } */
+ si = 3.1f; /* { dg-warning "conversion" } */
+ fsi (3.1); /* { dg-warning "conversion" } */
+ si = 3.1; /* { dg-warning "conversion" } */
+ fsi (d); /* { dg-warning "conversion" } */
+ si = d; /* { dg-warning "conversion" } */
+ fui (-1.0); /* { dg-warning "overflow" } */
+ ui = -1.0; /* { dg-warning "overflow" } */
+ ffloat (INT_MAX); /* { dg-warning "conversion" } */
+ vfloat = INT_MAX; /* { dg-warning "conversion" } */
+ ffloat (16777217); /* { dg-warning "conversion" } */
+ vfloat = 16777217; /* { dg-warning "conversion" } */
+ ffloat (si); /* { dg-warning "conversion" } */
+ vfloat = si; /* { dg-warning "conversion" } */
+ ffloat (ui); /* { dg-warning "conversion" } */
+ vfloat = ui; /* { dg-warning "conversion" } */
+
+ fsi (3);
+ si = 3;
+ fsi (3.0f);
+ si = 3.0f;
+ fsi (3.0);
+ si = 3.0;
+ fsi (16777217.0f);
+ si = 16777217.0f;
+ fsi ((int) 3.1);
+ si = (int) 3.1;
+ ffloat (3U);
+ vfloat = 3U;
+ ffloat (3);
+ vfloat = 3;
+ ffloat (INT_MIN);
+ vfloat = INT_MIN;
+ ffloat (uc);
+ vfloat = uc;
+ ffloat (sc);
+ vfloat = sc;
+
+ fdouble (UINT_MAX);
+ vdouble = UINT_MAX;
+ fdouble (ui);
+ vdouble = ui;
+ fdouble (si);
+ vdouble = si;
+}
+
+
Index: gcc/testsuite/g++.dg/warn/Wconversion-real.C
===================================================================
--- gcc/testsuite/g++.dg/warn/Wconversion-real.C (revision 0)
+++ gcc/testsuite/g++.dg/warn/Wconversion-real.C (revision 0)
@@ -0,0 +1,85 @@
+/* Test for diagnostics for Wconversion for floating-point.
+ C++ equivalent of gcc/testsuite/gcc.dg/Wconversion-real.c */
+
+/* { dg-do compile }
+/* { dg-options "-Wconversion" } */
+
+float vfloat;
+double vdouble;
+long double vlongdouble;
+
+void ffloat (float f);
+void fdouble (double d);
+void flongdouble (long double ld);
+
+void h (void)
+{
+ float f = 0;
+ double d = 0;
+ long double ld = 0;
+
+ ffloat (3.1); /* { dg-warning "conversion" } */
+ vfloat = 3.1; /* { dg-warning "conversion" } */
+ ffloat (3.1L); /* { dg-warning "conversion" } */
+ vfloat = 3.1L; /* { dg-warning "conversion" } */
+ fdouble (3.1L); /* { dg-warning "conversion" "" { target large_long_double } } */
+ vdouble = 3.1L; /* { dg-warning "conversion" "" { target large_long_double } } */
+ ffloat (vdouble); /* { dg-warning "conversion" } */
+ vfloat = vdouble; /* { dg-warning "conversion" } */
+ ffloat (vlongdouble); /* { dg-warning "conversion" } */
+ vfloat = vlongdouble; /* { dg-warning "conversion" } */
+ fdouble (vlongdouble); /* { dg-warning "conversion" "" { target large_long_double } } */
+ vdouble = vlongdouble; /* { dg-warning "conversion" "" { target large_long_double } } */
+
+
+ ffloat ((float) 3.1);
+ vfloat = (float) 3.1;
+ ffloat ((float) 3.1L);
+ vfloat = (float) 3.1L;
+ fdouble ((double) 3.1L);
+ vdouble = (double) 3.1L;
+ ffloat ((float) vdouble);
+ vfloat = (float) vdouble;
+ ffloat ((float) vlongdouble);
+ vfloat = (float) vlongdouble;
+ fdouble ((double) vlongdouble);
+ vdouble = (double) vlongdouble;
+
+
+ ffloat (3.0);
+ vfloat = 3.0;
+ ffloat (3.1f);
+ vfloat = 3.1f;
+ ffloat (0.25L);
+ vfloat = 0.25L;
+
+
+ fdouble (3.0);
+ vdouble = 3.0;
+ fdouble (3.1f);
+ vdouble = 3.1f;
+ fdouble (0.25L);
+ vdouble = 0.25L;
+
+ flongdouble (3.0);
+ vlongdouble = 3.0;
+ flongdouble (3.1f);
+ vlongdouble = 3.1f;
+ flongdouble (0.25L);
+ vlongdouble = 0.25L;
+
+ ffloat (f);
+ vfloat = f;
+ fdouble (f);
+ vdouble = f;
+ fdouble (d);
+ vdouble = d;
+ flongdouble (f);
+ vlongdouble = f;
+ flongdouble (d);
+ vlongdouble = d;
+ flongdouble (ld);
+ vlongdouble = ld;
+}
+
+
Index: gcc/testsuite/g++.dg/warn/Wconversion-integer.C
===================================================================
--- gcc/testsuite/g++.dg/warn/Wconversion-integer.C (revision 0)
+++ gcc/testsuite/g++.dg/warn/Wconversion-integer.C (revision 0)
@@ -0,0 +1,95 @@
+/* Test for diagnostics for implicit conversions between integer types
+ C++ equivalent of gcc/testsuite/gcc.dg/Wconversion-integer.c */
+
+// { dg-do compile }
+// { dg-options "-fsigned-char -Wconversion" }
+
+#include <limits.h>
+
+void fsc (signed char sc);
+void fuc (unsigned char uc);
+unsigned fui (unsigned int ui);
+void fsi (signed int ui);
+
+void h (int x)
+{
+ unsigned int ui = 3;
+ int si = 3;
+ unsigned char uc = 3;
+ signed char sc = 3;
+
+ fuc (-1); /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ uc = -1; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ fuc ('\xa0'); /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ uc = '\xa0'; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ uc = x ? 1U : -1; /* { dg-warning "conversion" } */
+ /* { dg-warning "negative integer implicitly converted to unsigned type" "" { target *-*-* } 25 } */
+ uc = x ? SCHAR_MIN : 1U; /* { dg-warning "conversion" } */
+ /* { dg-warning "negative integer implicitly converted to unsigned type" "" { target *-*-* } 27 } */
+
+ uc = x ? 1 : -1; /* { dg-warning "conversion" } */
+
+ uc = x ? SCHAR_MIN : 1; /* { dg-warning "conversion" } */
+
+ fuc ('A');
+ uc = 'A';
+ uc = (unsigned char) -1;
+
+ fui (-1); /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = -1; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = x ? 1U : -1; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = x ? INT_MIN : 1U; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = ui ? SCHAR_MIN : 1U; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = 1U * -1; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = ui + INT_MIN; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = x ? 1 : -1; /* { dg-warning "conversion" } */
+ ui = ui ? SCHAR_MIN : 1; /* { dg-warning "conversion" } */
+
+ ui = -1 * (1 * -1);
+ ui = (unsigned) -1;
+
+ fsc (uc); /* { dg-warning "conversion" } */
+ sc = uc; /* { dg-warning "conversion" } */
+ fuc (sc); /* { dg-warning "conversion" } */
+ uc = sc; /* { dg-warning "conversion" } */
+ fsi (ui); /* { dg-warning "conversion" } */
+ si = ui; /* { dg-warning "conversion" } */
+ fui (si); /* { dg-warning "conversion" } */
+ ui = si; /* { dg-warning "conversion" } */
+ fui (sc); /* { dg-warning "conversion" } */
+ ui = sc; /* { dg-warning "conversion" } */
+
+ fui ('\xa0');/* { dg-warning "negative integer implicitly converted to unsigned type" } */
+ ui = '\xa0'; /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+
+ fsi (si);
+ fui (ui);
+ fsi (uc);
+ si = uc;
+ fui (uc);
+ ui = uc;
+ fui ('A');
+ ui = 'A';
+ fsi ('A');
+ si = 'A';
+
+
+ fsi (UINT_MAX - 1); /* { dg-warning "conversion" } */
+ si = UINT_MAX - 1; /* { dg-warning "conversion" } */
+ fsi (UINT_MAX - 1U); /* { dg-warning "conversion" } */
+ si = UINT_MAX - 1U; /* { dg-warning "conversion" } */
+ fsi (UINT_MAX/3U);
+ si = UINT_MAX/3U;
+ fsi (UINT_MAX/3);
+ si = UINT_MAX/3;
+ fui (UINT_MAX - 1);
+ ui = UINT_MAX - 1;
+
+ fsi (0x80000000); /* { dg-warning "conversion" } */
+ si = 0x80000000; /* { dg-warning "conversion" } */
+}
+
+
+unsigned fui (unsigned a) { return a + -1; } /* { dg-warning "negative integer implicitly converted to unsigned type" } */
+
+
Index: gcc/testsuite/g++.dg/warn/conv2.C
===================================================================
--- gcc/testsuite/g++.dg/warn/conv2.C (revision 121678)
+++ gcc/testsuite/g++.dg/warn/conv2.C (working copy)
@@ -1,4 +1,5 @@
// PR c++/13932
// { dg-options "-Wconversion" }
-int i = 1.; // { dg-warning "converting" }
+int i = 1.;
+int j = 1.1; // { dg-warning "conversion" }
Index: gcc/cp/typeck.c
===================================================================
--- gcc/cp/typeck.c (revision 121678)
+++ gcc/cp/typeck.c (working copy)
@@ -3853,9 +3853,9 @@ build_binary_op (enum tree_code code, tr
if (! converted)
{
if (TREE_TYPE (op0) != result_type)
- op0 = cp_convert (result_type, op0);
+ op0 = cp_convert_and_check (result_type, op0);
if (TREE_TYPE (op1) != result_type)
- op1 = cp_convert (result_type, op1);
+ op1 = cp_convert_and_check (result_type, op1);
if (op0 == error_mark_node || op1 == error_mark_node)
return error_mark_node;
Index: gcc/cp/call.c
===================================================================
--- gcc/cp/call.c (revision 121678)
+++ gcc/cp/call.c (working copy)
@@ -4258,17 +4258,6 @@ convert_like_real (conversion *convs, tr
else
warning (OPT_Wconversion, "converting to non-pointer type %qT from NULL", t);
}
-
- /* Warn about assigning a floating-point type to an integer type. */
- if (TREE_CODE (TREE_TYPE (expr)) == REAL_TYPE
- && TREE_CODE (t) == INTEGER_TYPE)
- {
- if (fn)
- warning (OPT_Wconversion, "passing %qT for argument %P to %qD",
- TREE_TYPE (expr), argnum, fn);
- else
- warning (OPT_Wconversion, "converting to %qT from %qT", t, TREE_TYPE (expr));
- }
}
switch (convs->kind)
@@ -4356,7 +4345,7 @@ convert_like_real (conversion *convs, tr
expr = convert_like_real (convs->u.next, expr, fn, argnum,
convs->kind == ck_ref_bind ? -1 : 1,
- /*issue_conversion_warnings=*/false,
+ convs->kind == ck_ref_bind ? issue_conversion_warnings : false,
c_cast_p);
if (expr == error_mark_node)
return error_mark_node;
Index: gcc/cp/cvt.c
===================================================================
--- gcc/cp/cvt.c (revision 121678)
+++ gcc/cp/cvt.c (working copy)
@@ -593,6 +593,29 @@ cp_convert (tree type, tree expr)
return ocp_convert (type, expr, CONV_OLD_CONVERT, LOOKUP_NORMAL);
}
+/* C++ equivalent of convert_and_check but using cp_convert as the
+ conversion function.
+
+ Convert EXPR to TYPE, warning about conversion problems with constants.
+ Invoke this function on every expression that is converted implicitly,
+ i.e. because of language rules and not because of an explicit cast. */
+
+tree
+cp_convert_and_check (tree type, tree expr)
+{
+ tree result;
+
+ if (TREE_TYPE (expr) == type)
+ return expr;
+
+ result = cp_convert (type, expr);
+
+ if (!skip_evaluation)
+ warnings_for_convert_and_check (type, expr, result);
+
+ return result;
+}
+
/* Conversion...
FLAGS indicates how we should behave. */
Index: gcc/cp/cp-tree.h
===================================================================
--- gcc/cp/cp-tree.h (revision 121678)
+++ gcc/cp/cp-tree.h (working copy)
@@ -3874,6 +3874,7 @@ extern tree convert_from_reference (tre
extern tree force_rvalue (tree);
extern tree ocp_convert (tree, tree, int, int);
extern tree cp_convert (tree, tree);
+extern tree cp_convert_and_check (tree, tree);
extern tree convert_to_void (tree, const char */*implicit context*/);
extern tree convert_force (tree, tree, int);
extern tree build_expr_type_conversion (int, tree, bool);
Index: gcc/c-common.c
===================================================================
--- gcc/c-common.c (revision 121678)
+++ gcc/c-common.c (working copy)
@@ -1231,24 +1231,9 @@ conversion_warning (tree type, tree expr
}
}
-/* Convert EXPR to TYPE, warning about conversion problems with constants.
- Invoke this function on every expression that is converted implicitly,
- i.e. because of language rules and not because of an explicit cast. */
-
-tree
-convert_and_check (tree type, tree expr)
+void
+warnings_for_convert_and_check (tree type, tree expr, tree result)
{
- tree result;
-
- if (TREE_TYPE (expr) == type)
- return expr;
-
- result = convert (type, expr);
-
- if (skip_evaluation)
- return result;
-
-
if (TREE_CODE (expr) == INTEGER_CST
&& (TREE_CODE (type) == INTEGER_TYPE
|| TREE_CODE (type) == ENUMERAL_TYPE)
@@ -1290,7 +1275,26 @@ convert_and_check (tree type, tree expr)
"overflow in implicit constant conversion");
else if (warn_conversion)
conversion_warning (type, expr);
+}
+
+
+/* Convert EXPR to TYPE, warning about conversion problems with constants.
+ Invoke this function on every expression that is converted implicitly,
+ i.e. because of language rules and not because of an explicit cast. */
+
+tree
+convert_and_check (tree type, tree expr)
+{
+ tree result;
+
+ if (TREE_TYPE (expr) == type)
+ return expr;
+ result = convert (type, expr);
+
+ if (!skip_evaluation)
+ warnings_for_convert_and_check (type, expr, result);
+
return result;
}
\f
Index: gcc/c-common.h
===================================================================
--- gcc/c-common.h (revision 121678)
+++ gcc/c-common.h (working copy)
@@ -671,6 +671,7 @@ struct varray_head_tag;
extern void constant_expression_warning (tree);
extern void strict_aliasing_warning (tree, tree, tree);
extern void empty_body_warning (tree, tree);
+extern void warnings_for_convert_and_check (tree, tree, tree);
extern tree convert_and_check (tree, tree);
extern void overflow_warning (tree);
extern void check_main_parameter_types (tree decl);
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^3] Wconversion: fixes for C++ front-end
2007-02-10 8:53 ` Manuel López-Ibáñez
@ 2007-02-10 9:02 ` Manuel López-Ibáñez
2007-02-18 11:47 ` [PING^4] " Manuel López-Ibáñez
1 sibling, 0 replies; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-02-10 9:02 UTC (permalink / raw)
To: Gabriel Dos Reis; +Cc: gcc-patches
It seems I managed to mess up the quoted text (wrong middle-click!).
Please ignore it and just refer to previous emails for the relevant
parts.
Cheers,
Manuel.
^ permalink raw reply [flat|nested] 26+ messages in thread
* [PING^4] Wconversion: fixes for C++ front-end
2007-02-10 8:53 ` Manuel López-Ibáñez
2007-02-10 9:02 ` Manuel López-Ibáñez
@ 2007-02-18 11:47 ` Manuel López-Ibáñez
2007-03-01 18:13 ` [PING^5] " Manuel López-Ibáñez
1 sibling, 1 reply; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-02-18 11:47 UTC (permalink / raw)
To: gcc-patches
Please,
http://gcc.gnu.org/ml/gcc-patches/2007-02/msg00897.html
Thanks,
Manuel.
^ permalink raw reply [flat|nested] 26+ messages in thread
* [PING^5] Wconversion: fixes for C++ front-end
2007-02-18 11:47 ` [PING^4] " Manuel López-Ibáñez
@ 2007-03-01 18:13 ` Manuel López-Ibáñez
2007-03-10 23:32 ` Dirk Mueller
0 siblings, 1 reply; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-03-01 18:13 UTC (permalink / raw)
To: gcc-patches
PING^5: http://gcc.gnu.org/ml/gcc-patches/2007-02/msg00897.html
Thanks,
Manuel.
On 18/02/07, Manuel López-Ibáñez <lopezibanez@gmail.com> wrote:
> Please,
>
> http://gcc.gnu.org/ml/gcc-patches/2007-02/msg00897.html
>
> Thanks,
>
> Manuel.
>
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^5] Wconversion: fixes for C++ front-end
2007-03-01 18:13 ` [PING^5] " Manuel López-Ibáñez
@ 2007-03-10 23:32 ` Dirk Mueller
2007-03-10 23:36 ` Manuel López-Ibáñez
0 siblings, 1 reply; 26+ messages in thread
From: Dirk Mueller @ 2007-03-10 23:32 UTC (permalink / raw)
To: gcc-patches
On Thursday, 1. March 2007, Manuel López-Ibáñez wrote:
> PING^5: http://gcc.gnu.org/ml/gcc-patches/2007-02/msg00897.html
I've added this patch to my tree and noticed that
warnings_for_convert_and_check() is missing a comment.
Dirk
^ permalink raw reply [flat|nested] 26+ messages in thread
* Re: [PING^5] Wconversion: fixes for C++ front-end
2007-03-10 23:32 ` Dirk Mueller
@ 2007-03-10 23:36 ` Manuel López-Ibáñez
0 siblings, 0 replies; 26+ messages in thread
From: Manuel López-Ibáñez @ 2007-03-10 23:36 UTC (permalink / raw)
To: Dirk Mueller; +Cc: gcc-patches
Yes, it would said something such as:
/* Produce warnings after a conversion. RESULT is the result of
converting EXPR to TYPE. This is a helper function for
convert_and_check and cp_convert_and_check. */
I am amazed that it still applies cleanly to a recent revision...
well, 4 days still until the next PING^6.
Cheers,
Manuel.
On 10/03/07, Dirk Mueller <dmueller@suse.de> wrote:
> On Thursday, 1. March 2007, Manuel López-Ibáñez wrote:
>
> > PING^5: http://gcc.gnu.org/ml/gcc-patches/2007-02/msg00897.html
>
> I've added this patch to my tree and noticed that
> warnings_for_convert_and_check() is missing a comment.
>
>
> Dirk
>
^ permalink raw reply [flat|nested] 26+ messages in thread
end of thread, other threads:[~2007-03-10 20:18 UTC | newest]
Thread overview: 26+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2007-02-06 9:14 [PING^3] Wconversion: fixes for C++ front-end Manuel López-Ibáñez
2007-02-06 18:24 ` Paolo Carlini
2007-02-06 19:21 ` Gabriel Dos Reis
2007-02-06 19:57 ` Manuel López-Ibáñez
2007-02-06 22:22 ` Gabriel Dos Reis
2007-02-06 22:57 ` Manuel López-Ibáñez
2007-02-06 23:06 ` Manuel López-Ibáñez
2007-02-06 23:32 ` Gabriel Dos Reis
2007-02-07 0:29 ` Manuel López-Ibáñez
2007-02-07 0:46 ` Gabriel Dos Reis
2007-02-07 9:13 ` Manuel López-Ibáñez
2007-02-07 16:35 ` Gabriel Dos Reis
2007-02-08 11:55 ` Manuel López-Ibáñez
2007-02-08 11:58 ` Gabriel Dos Reis
2007-02-08 12:39 ` Manuel López-Ibáñez
2007-02-08 12:02 ` Gabriel Dos Reis
2007-02-08 12:48 ` Manuel López-Ibáñez
2007-02-08 14:06 ` Gabriel Dos Reis
2007-02-10 8:53 ` Manuel López-Ibáñez
2007-02-10 9:02 ` Manuel López-Ibáñez
2007-02-18 11:47 ` [PING^4] " Manuel López-Ibáñez
2007-03-01 18:13 ` [PING^5] " Manuel López-Ibáñez
2007-03-10 23:32 ` Dirk Mueller
2007-03-10 23:36 ` Manuel López-Ibáñez
2007-02-06 23:30 ` [PING^3] " Gabriel Dos Reis
2007-02-06 19:50 ` Manuel López-Ibáñez
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).