diff options
| author | Luc Van Oostenryck <luc.vanoostenryck@gmail.com> | 2017-01-29 12:34:09 +0100 |
|---|---|---|
| committer | Christopher Li <sparse@chrisli.org> | 2017-02-13 09:34:45 +0800 |
| commit | 7e9d18754cf8ebc6bc24f4d744720282d62531ad (patch) | |
| tree | 850ccf8465e50ac50a23d776a62d4f74159a6105 /validation | |
| parent | 05adbae426c87e6f644ebb7eca95a2d66a190048 (diff) | |
| download | sparse-dev-7e9d18754cf8ebc6bc24f4d744720282d62531ad.tar.gz | |
validate expression's type in conditionals
This wasn't done yet, in particular void values was accepted
inside if statements, which lead to strange situations after
linearization.
Implement this simply by calling the newly created is_scalar_type()
in evaluate_conditional() and issuing an appropriate diagnostic
when the check fail.
Signed-off-by: Luc Van Oostenryck <luc.vanoostenryck@gmail.com>
Signed-off-by: Christopher Li <sparse@chrisli.org>
Diffstat (limited to 'validation')
| -rw-r--r-- | validation/conditional-type.c | 99 |
1 files changed, 99 insertions, 0 deletions
diff --git a/validation/conditional-type.c b/validation/conditional-type.c new file mode 100644 index 00000000..a14c05ec --- /dev/null +++ b/validation/conditional-type.c @@ -0,0 +1,99 @@ +extern void afun(void); +extern void vcond(void); +static int array[3]; + +struct state { + int nr:2; +}; + +enum number { + zero, + one, + two, + many, +}; + +static int bad_if(struct state s) +{ + if (vcond()) return 1; + if (s) return 1; + return 0; +} +static void bad_if2(int *a, int *b) +{ + if (vcond()) *a = 1; + *b = 0; +} +static int bad_sel(struct state s) +{ + return vcond() ? 1 : 0; + return s ? 1 : 0; +} +static int bad_loop_void(void) +{ + while (vcond()) + ; + for (;vcond();) + ; + do + ; + while (vcond()); + return 0; +} + + +static int good_if_int(int a, _Bool b, long c, unsigned char d) +{ + if (a) return 1; + if (b) return 1; + if (c) return 1; + if (d) return 1; + return 0; +} +static int good_if_float(float a, double b) +{ + if (a) return 1; + if (b) return 1; + return 0; +} +static int good_if_enum(void) +{ + if (many) return 1; + return 0; +} +static int good_if_bitfield(struct state s, struct state *p) +{ + if (s.nr) return 1; + if (p->nr) return 1; + return 0; +} +static int good_if_ptr(void *ptr) +{ + if (ptr) return 1; + if (array) return 1; + if (afun) return 1; + return 0; +} + +/* + * check-name: conditional-type + * + * check-error-start +conditional-type.c:18:18: error: incorrect type in conditional +conditional-type.c:18:18: got void +conditional-type.c:19:13: error: incorrect type in conditional +conditional-type.c:19:13: got struct state s +conditional-type.c:24:18: error: incorrect type in conditional +conditional-type.c:24:18: got void +conditional-type.c:29:21: error: incorrect type in conditional +conditional-type.c:29:21: got void +conditional-type.c:30:16: error: incorrect type in conditional +conditional-type.c:30:16: got struct state s +conditional-type.c:34:21: error: incorrect type in conditional +conditional-type.c:34:21: got void +conditional-type.c:36:20: error: incorrect type in conditional +conditional-type.c:36:20: got void +conditional-type.c:40:21: error: incorrect type in conditional +conditional-type.c:40:21: got void + * check-error-end + */ |
