}
/* Issue a diagnostic message if casting from SRC_TYPE to DEST_TYPE
- casts away constness. DIAG_FN gives the function to call if we
- need to issue a diagnostic; if it is NULL, no diagnostic will be
- issued. DESCRIPTION explains what operation is taking place. */
+ casts away constness. CAST gives the type of cast. */
static void
check_for_casting_away_constness (tree src_type, tree dest_type,
- void (*diag_fn)(const char *, ...) ATTRIBUTE_GCC_CXXDIAG(1,2),
- const char *description)
+ enum tree_code cast)
{
- if (diag_fn && casts_away_constness (src_type, dest_type))
- diag_fn ("%s from type %qT to type %qT casts away constness",
- description, src_type, dest_type);
+ /* C-style casts are allowed to cast away constness. With
+ WARN_CAST_QUAL, we still want to issue a warning. */
+ if (cast == CAST_EXPR && !warn_cast_qual)
+ return;
+
+ if (casts_away_constness (src_type, dest_type))
+ switch (cast)
+ {
+ case CAST_EXPR:
+ warning (OPT_Wcast_qual,
+ "cast from type %qT to type %qT casts away constness",
+ src_type, dest_type);
+ return;
+
+ case STATIC_CAST_EXPR:
+ error ("static_cast from type %qT to type %qT casts away constness",
+ src_type, dest_type);
+ return;
+
+ case REINTERPRET_CAST_EXPR:
+ error ("reinterpret_cast from type %qT to type %qT casts away constness",
+ src_type, dest_type);
+ return;
+ default:
+ gcc_unreachable();
+ }
}
/* Convert EXPR (an expression with pointer-to-member type) to TYPE
tree intype;
tree result;
tree orig;
- void (*diag_fn)(const char*, ...) ATTRIBUTE_GCC_CXXDIAG(1,2);
- const char *desc;
/* Assume the cast is valid. */
*valid_p = true;
/* Save casted types in the function's used types hash table. */
used_types_insert (type);
- /* Determine what to do when casting away constness. */
- if (c_cast_p)
- {
- /* C-style casts are allowed to cast away constness. With
- WARN_CAST_QUAL, we still want to issue a warning. */
- diag_fn = warn_cast_qual ? warning0 : NULL;
- desc = "cast";
- }
- else
- {
- /* A static_cast may not cast away constness. */
- diag_fn = error;
- desc = "static_cast";
- }
-
/* [expr.static.cast]
An lvalue of type "cv1 B", where B is a class type, can be cast
tree base;
if (!c_cast_p)
- check_for_casting_away_constness (intype, type, diag_fn, desc);
+ check_for_casting_away_constness (intype, type, STATIC_CAST_EXPR);
base = lookup_base (TREE_TYPE (type), TREE_TYPE (intype),
c_cast_p ? ba_unique : ba_check,
NULL);
if (can_convert (t1, t2) || can_convert (t2, t1))
{
if (!c_cast_p)
- check_for_casting_away_constness (intype, type, diag_fn,
- desc);
+ check_for_casting_away_constness (intype, type, STATIC_CAST_EXPR);
return convert_ptrmem (type, expr, /*allow_inverse_p=*/1,
c_cast_p);
}
&& TYPE_PTROB_P (type))
{
if (!c_cast_p)
- check_for_casting_away_constness (intype, type, diag_fn, desc);
+ check_for_casting_away_constness (intype, type, STATIC_CAST_EXPR);
return build_nop (type, expr);
}
tree sexpr = expr;
if (!c_cast_p)
- check_for_casting_away_constness (intype, type, error,
- "reinterpret_cast");
+ check_for_casting_away_constness (intype, type, REINTERPRET_CAST_EXPR);
/* Warn about possible alignment problems. */
if (STRICT_ALIGNMENT && warn_cast_align
&& !VOID_TYPE_P (type)
*valid_p = true;
/* This cast is actually a C-style cast. Issue a warning if
the user is making a potentially unsafe cast. */
- if (warn_cast_qual)
- check_for_casting_away_constness (src_type, dst_type,
- warning0,
- "cast");
+ check_for_casting_away_constness (src_type, dst_type, CAST_EXPR);
}
if (reference_type)
{