math: cleanup: get rid of IMPLIED_SINGLE
[smatch.git] / check_precedence.c
blob5cbe036a124335f558ed6e172e068e93cfb051f6
1 /*
2 * sparse/check_precedence.c
4 * Copyright (C) 2010 Dan Carpenter.
6 * Licensed under the Open Software License version 1.1
8 */
10 #include "smatch.h"
12 static int my_id;
14 static int is_bool(struct expression *expr)
16 struct symbol *type;
18 type = get_type(expr);
19 if (!type)
20 return 0;
21 if (type->bit_size == 1 && type->ctype.modifiers & MOD_UNSIGNED)
22 return 1;
23 return 0;
26 static int is_bool_op(struct expression *expr)
28 expr = strip_expr(expr);
30 if (expr->type == EXPR_PREOP && expr->op == '!')
31 return 1;
32 if (expr->type == EXPR_COMPARE)
33 return 1;
34 if (expr->type == EXPR_LOGICAL)
35 return 1;
36 return is_bool(expr);
39 static void match_condition(struct expression *expr)
41 int print = 0;
43 if (expr->type == EXPR_COMPARE) {
44 if (expr->left->type == EXPR_COMPARE || expr->right->type == EXPR_COMPARE)
45 print = 1;
46 if (expr->left->op == '!') {
47 if (expr->left->type == EXPR_PREOP && expr->left->unop->op == '!')
48 return;
49 if (expr->right->op == '!')
50 return;
51 if (is_bool(expr->right))
52 return;
53 if (is_bool(expr->left->unop))
54 return;
55 print = 1;
59 if (expr->type == EXPR_BINOP) {
60 if (expr->left->type == EXPR_COMPARE || expr->right->type == EXPR_COMPARE)
61 print = 1;
64 if (print) {
65 sm_msg("warn: add some parenthesis here?");
66 return;
69 if (expr->type == EXPR_BINOP && expr->op == '&') {
70 int i = 0;
72 if (is_bool_op(expr->left))
73 i++;
74 if (is_bool_op(expr->right))
75 i++;
76 if (i == 1)
77 sm_msg("warn: maybe use && instead of &");
81 static void match_binop(struct expression *expr)
83 if (expr->op != '&')
84 return;
85 if (expr->left->op == '!')
86 sm_msg("warn: add some parenthesis here?");
89 void check_precedence(int id)
91 my_id = id;
93 add_hook(&match_condition, CONDITION_HOOK);
94 add_hook(&match_binop, BINOP_HOOK);