Print this page
11506 smatch resync
Split |
Close |
Expand all |
Collapse all |
--- old/usr/src/tools/smatch/src/smatch_mtag_data.c
+++ new/usr/src/tools/smatch/src/smatch_mtag_data.c
1 1 /*
2 2 * Copyright (C) 2016 Oracle.
3 3 *
4 4 * This program is free software; you can redistribute it and/or
5 5 * modify it under the terms of the GNU General Public License
6 6 * as published by the Free Software Foundation; either version 2
7 7 * of the License, or (at your option) any later version.
8 8 *
9 9 * This program is distributed in the hope that it will be useful,
10 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 12 * GNU General Public License for more details.
13 13 *
14 14 * You should have received a copy of the GNU General Public License
15 15 * along with this program; if not, see http://www.gnu.org/copyleft/gpl.txt
16 16 */
17 17
18 18 /*
19 19 * What we're doing here is saving all the possible values for static variables.
20 20 * Later on we might do globals as well.
21 21 *
22 22 */
23 23
24 24 #include "smatch.h"
25 25 #include "smatch_slist.h"
26 26 #include "smatch_extra.h"
27 27
28 28 static int my_id;
↓ open down ↓ |
28 lines elided |
↑ open up ↑ |
29 29 static struct stree *vals;
30 30
31 31 static int save_rl(void *_rl, int argc, char **argv, char **azColName)
32 32 {
33 33 unsigned long *rl = _rl;
34 34
35 35 *rl = strtoul(argv[0], NULL, 10);
36 36 return 0;
37 37 }
38 38
39 -static struct range_list *select_orig_rl(sval_t sval)
39 +static struct range_list *select_orig(mtag_t tag, int offset)
40 40 {
41 41 struct range_list *rl = NULL;
42 - mtag_t tag = sval.uvalue & ~MTAG_OFFSET_MASK;
43 - int offset = sval.uvalue & MTAG_OFFSET_MASK;
44 42
45 43 mem_sql(&save_rl, &rl, "select value from mtag_data where tag = %lld and offset = %d;",
46 44 tag, offset);
47 45 return rl;
48 46 }
49 47
50 48 static int is_kernel_param(const char *name)
51 49 {
52 50 struct sm_state *tmp;
53 51 char buf[256];
54 52
55 53 /*
56 54 * I'm ignoring these because otherwise Smatch thinks that kernel
57 55 * parameters are always set to the default.
58 56 *
59 57 */
60 58
61 59 if (option_project != PROJ_KERNEL)
62 60 return 0;
63 61
↓ open down ↓ |
10 lines elided |
↑ open up ↑ |
64 62 snprintf(buf, sizeof(buf), "__param_%s.arg", name);
65 63
66 64 FOR_EACH_SM(vals, tmp) {
67 65 if (strcmp(tmp->name, buf) == 0)
68 66 return 1;
69 67 } END_FOR_EACH_SM(tmp);
70 68
71 69 return 0;
72 70 }
73 71
74 -void insert_mtag_data(sval_t sval, struct range_list *rl)
72 +static void insert_mtag_data(mtag_t tag, int offset, struct range_list *rl)
75 73 {
76 - mtag_t tag = sval.uvalue & ~MTAG_OFFSET_MASK;
77 - int offset = sval.uvalue & MTAG_OFFSET_MASK;
78 -
79 74 rl = clone_rl_permanent(rl);
80 75
81 76 mem_sql(NULL, NULL, "delete from mtag_data where tag = %lld and offset = %d and type = %d",
82 77 tag, offset, DATA_VALUE);
83 78 mem_sql(NULL, NULL, "insert into mtag_data values (%lld, %d, %d, '%lu');",
84 79 tag, offset, DATA_VALUE, (unsigned long)rl);
85 80 }
86 81
87 82 void update_mtag_data(struct expression *expr)
88 83 {
89 84 struct range_list *orig, *new, *rl;
85 + struct symbol *type;
90 86 char *name;
91 - sval_t sval;
87 + mtag_t tag;
88 + int offset;
92 89
93 90 name = expr_to_var(expr);
94 91 if (is_kernel_param(name)) {
95 92 free_string(name);
96 93 return;
97 94 }
98 95 free_string(name);
99 96
100 - if (!get_mtag_addr_sval(expr, &sval))
97 + if (!expr_to_mtag_offset(expr, &tag, &offset))
101 98 return;
102 99
100 + type = get_type(expr);
101 + if ((offset == 0) &&
102 + (!type || type == &void_ctype ||
103 + type->type == SYM_STRUCT || type->type == SYM_UNION || type->type == SYM_ARRAY))
104 + return;
105 +
103 106 get_absolute_rl(expr, &rl);
104 107
105 - orig = select_orig_rl(sval);
108 + orig = select_orig(tag, offset);
106 109 new = rl_union(orig, rl);
107 - insert_mtag_data(sval, new);
110 + insert_mtag_data(tag, offset, new);
108 111 }
109 112
110 113 static void match_global_assign(struct expression *expr)
111 114 {
112 115 struct range_list *rl;
113 - sval_t sval;
116 + mtag_t tag;
117 + int offset;
114 118 char *name;
115 119
116 120 name = expr_to_var(expr->left);
117 121 if (is_kernel_param(name)) {
118 122 free_string(name);
119 123 return;
120 124 }
121 125 free_string(name);
122 126
123 - if (!get_mtag_addr_sval(expr->left, &sval))
127 + if (!expr_to_mtag_offset(expr->left, &tag, &offset))
124 128 return;
125 129
126 130 get_absolute_rl(expr->right, &rl);
127 - insert_mtag_data(sval, rl);
131 + insert_mtag_data(tag, offset, rl);
128 132 }
129 133
130 134 static int save_mtag_data(void *_unused, int argc, char **argv, char **azColName)
131 135 {
132 136 struct range_list *rl;
133 137
134 138 if (argc != 4) {
135 139 sm_msg("Error saving mtag data");
136 140 return 0;
137 141 }
138 142 if (!option_info)
139 143 return 0;
140 144
141 145 rl = (struct range_list *)strtoul(argv[3], NULL, 10);
142 146 sm_msg("SQL: insert into mtag_data values ('%s', '%s', '%s', '%s');",
143 147 argv[0], argv[1], argv[2], show_rl(rl));
144 148
145 149 return 0;
146 150 }
147 151
148 152 static void match_end_file(struct symbol_list *sym_list)
149 153 {
150 154 mem_sql(&save_mtag_data, NULL, "select * from mtag_data where type = %d;",
151 155 DATA_VALUE);
152 156 }
153 157
154 158 struct db_info {
155 159 struct symbol *type;
156 160 struct range_list *rl;
157 161 };
158 162
159 163 static int get_vals(void *_db_info, int argc, char **argv, char **azColName)
160 164 {
161 165 struct db_info *db_info = _db_info;
162 166 struct range_list *tmp;
163 167
↓ open down ↓ |
26 lines elided |
↑ open up ↑ |
164 168 str_to_rl(db_info->type, argv[0], &tmp);
165 169 if (db_info->rl)
166 170 db_info->rl = rl_union(db_info->rl, tmp);
167 171 else
168 172 db_info->rl = tmp;
169 173
170 174 return 0;
171 175 }
172 176
173 177 struct db_cache_results {
174 - sval_t sval;
178 + mtag_t tag;
175 179 struct range_list *rl;
176 180 };
177 181 static struct db_cache_results cached_results[8];
178 182
179 -static int get_rl_from_mtag_sval(sval_t sval, struct symbol *type, struct range_list **rl)
183 +static int get_rl_from_mtag_offset(mtag_t tag, int offset, struct symbol *type, struct range_list **rl)
180 184 {
181 185 struct db_info db_info = {};
182 - mtag_t tag;
183 - int offset;
186 + mtag_t merged = tag | offset;
184 187 static int idx;
185 188 int ret;
186 189 int i;
187 190
191 + if (!type || type == &void_ctype ||
192 + (type->type == SYM_STRUCT || type->type == SYM_ARRAY || type->type == SYM_UNION))
193 + return 0;
194 +
188 195 for (i = 0; i < ARRAY_SIZE(cached_results); i++) {
189 - if (sval.uvalue == cached_results[i].sval.uvalue) {
196 + if (merged == cached_results[i].tag) {
190 197 if (cached_results[i].rl) {
191 198 *rl = cached_results[i].rl;
192 199 return 1;
193 200 }
194 201 return 0;
195 202 }
196 203 }
197 204
198 - tag = sval.uvalue & ~MTAG_OFFSET_MASK;
199 - offset = sval.uvalue & MTAG_OFFSET_MASK;
200 - if (offset == MTAG_OFFSET_MASK) {
201 - ret = 0;
202 - goto update_cache;
203 - }
204 205 db_info.type = type;
205 206
206 207 run_sql(get_vals, &db_info,
207 208 "select value from mtag_data where tag = %lld and offset = %d and type = %d;",
208 209 tag, offset, DATA_VALUE);
209 210 if (!db_info.rl || is_whole_rl(db_info.rl)) {
210 211 db_info.rl = NULL;
211 212 ret = 0;
212 213 goto update_cache;
213 214 }
214 215
215 216 *rl = db_info.rl;
216 217 ret = 1;
217 218
218 219 update_cache:
219 - cached_results[idx].sval = sval;
220 + cached_results[idx].tag = merged;
220 221 cached_results[idx].rl = db_info.rl;
221 222 idx = (idx + 1) % ARRAY_SIZE(cached_results);
222 223
223 224 return ret;
224 225 }
225 226
226 227 static void clear_cache(struct symbol *sym)
227 228 {
228 229 memset(cached_results, 0, sizeof(cached_results));
229 230 }
230 231
231 232 int get_mtag_rl(struct expression *expr, struct range_list **rl)
232 233 {
233 234 struct symbol *type;
234 - sval_t sval;
235 + mtag_t tag;
236 + int offset;
235 237
236 - if (!get_mtag_addr_sval(expr, &sval))
238 + if (!expr_to_mtag_offset(expr, &tag, &offset))
237 239 return 0;
240 + if (offset >= MTAG_OFFSET_MASK)
241 + return 0;
238 242
239 243 type = get_type(expr);
240 244 if (!type)
241 245 return 0;
242 246
243 - return get_rl_from_mtag_sval(sval, type, rl);
247 + return get_rl_from_mtag_offset(tag, offset, type, rl);
244 248 }
245 249
246 250 void register_mtag_data(int id)
247 251 {
248 252 my_id = id;
249 253
250 254 add_hook(&clear_cache, FUNC_DEF_HOOK);
251 255
252 256 // if (!option_info)
253 257 // return;
254 258 add_hook(&match_global_assign, GLOBAL_ASSIGNMENT_HOOK);
255 259 add_hook(&match_end_file, END_FILE_HOOK);
256 260 }
257 261
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX