[RFC/PATCH 9/9] constant: add -Wconstant-size warning

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



>From 8764999aa78415e217fd3106a8c8518a5b40c20c Mon Sep 17 00:00:00 2001
From: Ramsay Jones <ramsay@xxxxxxxxxxxxxxxxxxxx>
Date: Sun, 18 Nov 2018 23:52:23 +0000
Subject: [PATCH 9/9] constant: add -Wconstant-size warning

Signed-off-by: Ramsay Jones <ramsay@xxxxxxxxxxxxxxxxxxxx>
---
 cgcc                          |  2 +-
 expression.c                  |  2 +-
 lib.c                         |  2 ++
 lib.h                         |  1 +
 sparse.1                      | 10 ++++++++++
 validation/constant-size-32.c | 15 +++++++++++++++
 validation/constant-size-64.c | 15 +++++++++++++++
 7 files changed, 45 insertions(+), 2 deletions(-)
 create mode 100644 validation/constant-size-32.c
 create mode 100644 validation/constant-size-64.c

diff --git a/cgcc b/cgcc
index 7611dc9..8ad766d 100755
--- a/cgcc
+++ b/cgcc
@@ -101,7 +101,7 @@ exit 0;
 
 sub check_only_option {
     my ($arg) = @_;
-    return 1 if $arg =~ /^-W(no-?)?(address-space|bitwise|cast-to-as|cast-truncate|context|decl|default-bitfield-sign|designated-init|do-while|enum-mismatch|init-cstring|memcpy-max-count|non-pointer-null|old-initializer|one-bit-signed-bitfield|override-init-all|paren-string|ptr-subtraction-blows|return-void|sizeof-bool|sparse-all|sparse-error|transparent-union|typesign|undef|unknown-attribute)$/;
+    return 1 if $arg =~ /^-W(no-?)?(address-space|bitwise|cast-to-as|cast-truncate|constant-size|context|decl|default-bitfield-sign|designated-init|do-while|enum-mismatch|init-cstring|memcpy-max-count|non-pointer-null|old-initializer|one-bit-signed-bitfield|override-init-all|paren-string|ptr-subtraction-blows|return-void|sizeof-bool|sparse-all|sparse-error|transparent-union|typesign|undef|unknown-attribute)$/;
     return 1 if $arg =~ /^-v(no-?)?(entry|dead)$/;
     return 1 if $arg =~ /^-f(dump-ir|memcpy-max-count|diagnostic-prefix)(=\S*)?$/;
     return 1 if $arg =~ /^-f(mem2reg|optim)(-enable|-disable|=last)?$/;
diff --git a/expression.c b/expression.c
index 6f4300b..d6ad74e 100644
--- a/expression.c
+++ b/expression.c
@@ -324,7 +324,7 @@ static void get_number_value(struct expression *expr, struct token *token)
 			show_token(token));
 	want_unsigned = 1;
 got_it:
-	if (do_warn)
+	if (do_warn && Wconstant_size)
 		warning(expr->pos, "constant %s is so big it is%s%s%s",
 			show_token(token),
 			want_unsigned ? " unsigned":"",
diff --git a/lib.c b/lib.c
index 08dc299..a8ebb7d 100644
--- a/lib.c
+++ b/lib.c
@@ -253,6 +253,7 @@ int Wbitwise = 1;
 int Wcast_from_as = 0;
 int Wcast_to_as = 0;
 int Wcast_truncate = 1;
+int Wconstant_size = 0;
 int Wconstexpr_not_const = 0;
 int Wcontext = 1;
 int Wdecl = 1;
@@ -689,6 +690,7 @@ static const struct flag warnings[] = {
 	{ "cast-from-as", &Wcast_from_as },
 	{ "cast-to-as", &Wcast_to_as },
 	{ "cast-truncate", &Wcast_truncate },
+	{ "constant-size", &Wconstant_size },
 	{ "constexpr-not-const", &Wconstexpr_not_const},
 	{ "context", &Wcontext },
 	{ "decl", &Wdecl },
diff --git a/lib.h b/lib.h
index ae0e981..507eb69 100644
--- a/lib.h
+++ b/lib.h
@@ -141,6 +141,7 @@ extern int Wbitwise;
 extern int Wcast_from_as;
 extern int Wcast_to_as;
 extern int Wcast_truncate;
+extern int Wconstant_size;
 extern int Wconstexpr_not_const;
 extern int Wcontext;
 extern int Wdecl;
diff --git a/sparse.1 b/sparse.1
index 3e13523..26299b3 100644
--- a/sparse.1
+++ b/sparse.1
@@ -101,6 +101,16 @@ Sparse issues these warnings by default.  To turn them off, use
 \fB\-Wno\-cast\-truncate\fR.
 .
 .TP
+.B \-Wconstant-size
+Warn if an integer constant is larger than the maximum representable value
+of the type indicated by the type suffix (if any). For example, on a 64-bit
+system, the constant 0xfffff00000000000U is larger than can be represented
+by an int and so requires an unsigned long type suffix. (So, in this case,
+the warning could be suppressed by using the UL type suffix).
+
+Sparse does not issue these warnings by default.
+.
+.TP
 .B \-Wconstexpr-not-const
 Warn if a non-constant expression is encountered when really expecting a
 constant expression instead.
diff --git a/validation/constant-size-32.c b/validation/constant-size-32.c
new file mode 100644
index 0000000..164734e
--- /dev/null
+++ b/validation/constant-size-32.c
@@ -0,0 +1,15 @@
+#define BIGU 0xfffff00000000000U
+#define BIGULL 0xfffff00000000000ULL
+
+static unsigned long long a = BIGU;
+static unsigned long long b = BIGULL;
+
+/*
+ * check-name: constant-size
+ * check-command: sparse -m32 -Wconstant-size $file
+ *
+ * check-error-start
+constant-size-32.c:4:31: warning: constant 0xfffff00000000000U is so big it is unsigned long long
+ * check-error-end
+ */
+
diff --git a/validation/constant-size-64.c b/validation/constant-size-64.c
new file mode 100644
index 0000000..471f6bc
--- /dev/null
+++ b/validation/constant-size-64.c
@@ -0,0 +1,15 @@
+#define BIGU 0xfffff00000000000U
+#define BIGUL 0xfffff00000000000UL
+
+static unsigned long a = BIGU;
+static unsigned long b = BIGUL;
+
+/*
+ * check-name: constant-size
+ * check-command: sparse -m64 -Wconstant-size $file
+ *
+ * check-error-start
+constant-size-64.c:4:26: warning: constant 0xfffff00000000000U is so big it is unsigned long
+ * check-error-end
+ */
+
-- 
2.19.0



[Index of Archives]     [Newbies FAQ]     [LKML]     [IETF Annouce]     [DCCP]     [Netdev]     [Networking]     [Security]     [Bugtraq]     [Yosemite]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux SCSI]     [Trinity Fuzzer Tool]

  Powered by Linux