smatch_clear_buffer: memcpy() should set the destination to unknown
[smatch.git] / check_macros.c
blob378ea645de056c8e38905dfea4594a506bab6d92
1 /*
2 * smatch/check_macros.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 void match_inside(struct expression *expr, struct position pos)
16 char *name;
17 int matched = 0;
19 if (positions_eq(expr->pos, pos))
20 matched++;
21 if (positions_eq(expr->unop->pos, pos))
22 matched++;
23 if (matched != 1)
24 return;
25 name = get_macro_name(pos);
26 if (!name)
27 return;
28 sm_msg("warn: the '%s' macro might need parens", name);
31 static void match_one_side(struct expression *expr, struct position pos, int op)
33 char *name;
34 int matched = 0;
36 if ((op == '+' || op == '*' || op == '|' || op == '&') && expr->op == op)
37 return;
38 if (positions_eq(expr->right->pos, pos))
39 matched++;
40 if (positions_eq(expr->left->pos, pos))
41 matched++;
42 if (matched != 1)
43 return;
44 name = get_macro_name(pos);
45 if (!name)
46 return;
47 if (option_project == PROJ_WINE && !strcmp("BEGIN", name))
48 return;
49 sm_msg("warn: the '%s' macro might need parens", name);
52 static void match_join(struct expression *expr)
54 if (expr->left->type == EXPR_PREOP)
55 match_inside(expr->left, expr->pos);
56 if (expr->right->type == EXPR_POSTOP)
57 match_inside(expr->right, expr->pos);
59 if (expr->left->type == EXPR_BINOP)
60 match_one_side(expr->left, expr->pos, expr->op);
61 if (expr->right->type == EXPR_BINOP)
62 match_one_side(expr->right, expr->pos, expr->op);
65 void check_macros(int id)
67 my_id = id;
68 add_hook(&match_join, BINOP_HOOK);
69 add_hook(&match_join, LOGIC_HOOK);