*new* check_macros: find macro precedence bugs
[smatch.git] / smatch_type.c
blob8896c3acbe2bb6f22511f19226aed4beb67dfbc6
1 /*
2 * sparse/smatch_types.c
4 * Copyright (C) 2009 Dan Carpenter.
6 * Licensed under the Open Software License version 1.1
8 */
11 * The idea here is that you have an expression and you
12 * want to know what the type is for that.
15 #include "smatch.h"
17 static struct symbol *get_type_symbol(struct expression *expr)
19 if (!expr || expr->type != EXPR_SYMBOL || !expr->symbol)
20 return NULL;
22 return get_base_type(expr->symbol);
25 static struct symbol *get_symbol_from_deref(struct expression *expr)
27 struct ident *member;
28 struct symbol *struct_sym;
29 struct symbol *tmp;
31 if (!expr || expr->type != EXPR_DEREF)
32 return NULL;
34 member = expr->member;
35 struct_sym = get_type(expr->deref);
36 if (!struct_sym) {
37 // sm_msg("could not find struct type");
38 return NULL;
40 if (struct_sym->type == SYM_PTR)
41 struct_sym = get_base_type(struct_sym);
42 FOR_EACH_PTR(struct_sym->symbol_list, tmp) {
43 if (tmp->ident == member)
44 return get_base_type(tmp);
45 } END_FOR_EACH_PTR(tmp);
46 return NULL;
49 static struct symbol *get_return_type(struct expression *expr)
51 struct symbol *tmp;
53 tmp = get_type(expr->fn);
54 if (!tmp)
55 return NULL;
56 return get_base_type(tmp);
59 static struct symbol *get_pointer_type(struct expression *expr)
61 struct symbol *sym;
63 sym = get_type(expr);
64 if (!sym || sym->type != SYM_PTR)
65 return NULL;
66 return get_base_type(sym);
69 static struct symbol *fake_pointer_sym(struct expression *expr)
71 struct symbol *sym;
72 struct symbol *base;
74 sym = alloc_symbol(expr->pos, SYM_PTR);
75 expr = expr->unop;
76 base = get_type(expr);
77 if (!base)
78 return NULL;
79 sym->ctype.base_type = base;
80 return sym;
83 struct symbol *get_type(struct expression *expr)
85 struct symbol *tmp;
87 if (!expr)
88 return NULL;
89 expr = strip_parens(expr);
91 switch (expr->type) {
92 case EXPR_SYMBOL:
93 return get_type_symbol(expr);
94 case EXPR_DEREF:
95 return get_symbol_from_deref(expr);
96 case EXPR_PREOP:
97 if (expr->op == '&')
98 return fake_pointer_sym(expr);
99 if (expr->op == '*')
100 return get_pointer_type(expr->unop);
101 return get_type(expr->unop);
102 case EXPR_CAST:
103 case EXPR_FORCE_CAST:
104 case EXPR_IMPLIED_CAST:
105 return get_base_type(expr->cast_type);
106 case EXPR_BINOP:
107 if (expr->op != '+')
108 return NULL;
109 tmp = get_type(expr->left);
110 if (!tmp || (tmp->type != SYM_ARRAY && tmp->type != SYM_PTR))
111 return NULL;
112 return get_base_type(tmp);
113 case EXPR_CALL:
114 return get_return_type(expr);
115 default:
116 return expr->ctype;
117 // sm_msg("unhandled type %d", expr->type);
121 return NULL;
124 int type_unsigned(struct symbol *base_type)
126 if (base_type->ctype.modifiers & MOD_UNSIGNED)
127 return 1;
128 return 0;
131 long long type_max(struct symbol *base_type)
133 long long ret = whole_range.max;
134 int bits;
136 if (!base_type || !base_type->bit_size)
137 return ret;
138 bits = base_type->bit_size;
139 if (bits == 64)
140 return ret;
141 if (!type_unsigned(base_type))
142 bits--;
143 ret >>= (63 - bits);
144 return ret;
147 long long type_min(struct symbol *base_type)
149 long long ret = whole_range.min;
150 int bits;
152 if (!base_type || !base_type->bit_size)
153 return ret;
154 if (type_unsigned(base_type))
155 return 0;
156 ret = whole_range.max;
157 bits = base_type->bit_size - 1;
158 ret >>= (63 - bits);
159 return -(ret + 1);