Print this page
new smatch
*** 81,115 ****
static struct smatch_state *empty_state(struct sm_state *sm)
{
return alloc_estate_empty();
}
! static void pre_merge_hook(struct sm_state *sm)
{
! struct smatch_state *user;
struct smatch_state *extra;
struct smatch_state *state;
struct range_list *rl;
- sval_t dummy;
- sval_t sval_100;
! sval_100.value = 100;
! sval_100.type = &int_ctype;
!
! user = __get_state(my_id, sm->name, sm->sym);
! if (!user || !estate_rl(user))
! return;
! extra = __get_state(SMATCH_EXTRA, sm->name, sm->sym);
if (!extra)
return;
rl = rl_intersection(estate_rl(user), estate_rl(extra));
- if (rl_to_sval(rl, &dummy))
- rl = NULL;
state = alloc_estate_rl(clone_rl(rl));
! if (estate_capped(user) || is_capped_var_sym(sm->name, sm->sym))
estate_set_capped(state);
! set_state(my_id, sm->name, sm->sym, state);
}
static void extra_nomod_hook(const char *name, struct symbol *sym, struct expression *expr, struct smatch_state *state)
{
struct smatch_state *user, *new;
--- 81,107 ----
static struct smatch_state *empty_state(struct sm_state *sm)
{
return alloc_estate_empty();
}
! static void pre_merge_hook(struct sm_state *cur, struct sm_state *other)
{
! struct smatch_state *user = cur->state;
struct smatch_state *extra;
struct smatch_state *state;
struct range_list *rl;
! extra = __get_state(SMATCH_EXTRA, cur->name, cur->sym);
if (!extra)
return;
rl = rl_intersection(estate_rl(user), estate_rl(extra));
state = alloc_estate_rl(clone_rl(rl));
! if (estate_capped(user) || is_capped_var_sym(cur->name, cur->sym))
estate_set_capped(state);
! if (estate_treat_untagged(user))
! estate_set_treat_untagged(state);
! set_state(my_id, cur->name, cur->sym, state);
}
static void extra_nomod_hook(const char *name, struct symbol *sym, struct expression *expr, struct smatch_state *state)
{
struct smatch_state *user, *new;
*** 122,131 ****
--- 114,125 ----
if (rl_equiv(rl, estate_rl(user)))
return;
new = alloc_estate_rl(rl);
if (estate_capped(user))
estate_set_capped(new);
+ if (estate_treat_untagged(user))
+ estate_set_treat_untagged(new);
set_state(my_id, name, sym, new);
}
static bool binop_capped(struct expression *expr)
{
*** 179,188 ****
--- 173,204 ----
return false; /* uncapped user data */
return true; /* not actually user data */
}
+ bool user_rl_treat_untagged(struct expression *expr)
+ {
+ struct smatch_state *state;
+ struct range_list *rl;
+ sval_t sval;
+
+ expr = strip_expr(expr);
+ if (!expr)
+ return false;
+ if (get_value(expr, &sval))
+ return true;
+
+ state = get_state_expr(my_id, expr);
+ if (state)
+ return estate_treat_untagged(state);
+
+ if (get_user_rl(expr, &rl))
+ return false; /* uncapped user data */
+
+ return true; /* not actually user data */
+ }
+
static void tag_inner_struct_members(struct expression *expr, struct symbol *member)
{
struct expression *edge_member;
struct symbol *base = get_real_base_type(member);
struct symbol *tmp;
*** 544,554 ****
name = get_macro_name(expr->pos);
if (!name || strcmp(name, "get_user") != 0)
return 0;
name = expr_to_var(expr->right);
! if (!name || strcmp(name, "__val_gu") != 0)
goto free;
set_state_expr(my_id, expr->left, alloc_estate_whole(get_type(expr->left)));
ret = 1;
free:
free_string(name);
--- 560,570 ----
name = get_macro_name(expr->pos);
if (!name || strcmp(name, "get_user") != 0)
return 0;
name = expr_to_var(expr->right);
! if (!name || (strcmp(name, "__val_gu") != 0 && strcmp(name, "__gu_val") != 0))
goto free;
set_state_expr(my_id, expr->left, alloc_estate_whole(get_type(expr->left)));
ret = 1;
free:
free_string(name);
*** 580,589 ****
--- 596,607 ----
rl = cast_rl(get_type(expr->left), rl);
state = alloc_estate_rl(rl);
if (user_rl_capped(binop_expr))
estate_set_capped(state);
+ if (user_rl_treat_untagged(expr->left))
+ estate_set_treat_untagged(state);
set_state_expr(my_id, expr->left, state);
return true;
}
return false;
}
*** 621,632 ****
--- 639,653 ----
if (!get_user_rl(expr->right, &rl))
goto clear_old_state;
rl = cast_rl(get_type(expr->left), rl);
state = alloc_estate_rl(rl);
+
if (user_rl_capped(expr->right))
estate_set_capped(state);
+ if (user_rl_treat_untagged(expr->right))
+ estate_set_treat_untagged(state);
set_state_expr(my_id, expr->left, state);
return;
clear_old_state:
*** 658,676 ****
}
static struct range_list *strip_negatives(struct range_list *rl)
{
sval_t min = rl_min(rl);
! sval_t minus_one;
! sval_t over;
sval_t max = sval_type_max(rl_type(rl));
- minus_one.type = rl_type(rl);
- minus_one.value = INT_MAX + 1ULL;
- over.type = rl_type(rl);
- over.value = -1;
-
if (!rl)
return NULL;
if (type_unsigned(rl_type(rl)) && type_bits(rl_type(rl)) > 31)
return remove_range(rl, over, max);
--- 679,692 ----
}
static struct range_list *strip_negatives(struct range_list *rl)
{
sval_t min = rl_min(rl);
! sval_t minus_one = { .type = rl_type(rl), .value = -1 };
! sval_t over = { .type = rl_type(rl), .value = INT_MAX + 1ULL };
sval_t max = sval_type_max(rl_type(rl));
if (!rl)
return NULL;
if (type_unsigned(rl_type(rl)) && type_bits(rl_type(rl)) > 31)
return remove_range(rl, over, max);
*** 1018,1029 ****
static char buf[64];
if (!get_user_rl(expr, &rl))
return NULL;
rl = cast_rl(type, rl);
! snprintf(buf, sizeof(buf), "%s%s",
! show_rl(rl), user_rl_capped(expr) ? "[c]" : "");
return buf;
}
static void match_call_info(struct expression *expr)
{
--- 1034,1047 ----
static char buf[64];
if (!get_user_rl(expr, &rl))
return NULL;
rl = cast_rl(type, rl);
! snprintf(buf, sizeof(buf), "%s%s%s",
! show_rl(rl),
! user_rl_capped(expr) ? "[c]" : "",
! user_rl_treat_untagged(expr) ? "[u]" : "");
return buf;
}
static void match_call_info(struct expression *expr)
{
*** 1091,1102 ****
rl = rl_intersection(estate_rl(sm->state), estate_rl(state));
if (!rl)
return;
! snprintf(buf, sizeof(buf), "%s%s", show_rl(rl),
! estate_capped(sm->state) ? "[c]" : "");
sql_insert_caller_info(call, USER_DATA, param, printed_name, buf);
}
static void db_param_set(struct expression *expr, int param, char *key, char *value)
{
--- 1109,1121 ----
rl = rl_intersection(estate_rl(sm->state), estate_rl(state));
if (!rl)
return;
! snprintf(buf, sizeof(buf), "%s%s%s", show_rl(rl),
! estate_capped(sm->state) ? "[c]" : "",
! estate_treat_untagged(sm->state) ? "[u]" : "");
sql_insert_caller_info(call, USER_DATA, param, printed_name, buf);
}
static void db_param_set(struct expression *expr, int param, char *key, char *value)
{
*** 1131,1140 ****
--- 1150,1166 ----
if (strstr(value, ",c") || strstr(value, "[c"))
return true;
return false;
}
+ static bool param_data_treat_untagged(const char *value)
+ {
+ if (strstr(value, ",u") || strstr(value, "[u"))
+ return true;
+ return false;
+ }
+
static void set_param_user_data(const char *name, struct symbol *sym, char *key, char *value)
{
struct range_list *rl = NULL;
struct smatch_state *state;
struct expression *expr;
*** 1178,1187 ****
--- 1204,1215 ----
str_to_rl(type, value, &rl);
state = alloc_estate_rl(rl);
if (param_data_capped(value) || is_capped(expr))
estate_set_capped(state);
+ if (param_data_treat_untagged(value) || sym->ctype.as == 5)
+ estate_set_treat_untagged(state);
set_state(my_id, fullname, sym, state);
}
static void set_called(const char *name, struct symbol *sym, char *key, char *value)
{
*** 1250,1259 ****
--- 1278,1289 ----
call_results_to_rl(expr, type, value, &rl);
state = alloc_estate_rl(rl);
if (param_data_capped(value))
estate_set_capped(state);
+ if (param_data_treat_untagged(value))
+ estate_set_treat_untagged(state);
set_state(my_id, name, sym, state);
free:
free_string(name);
}
*** 1357,1369 ****
if (!param_name)
continue;
if (strcmp(param_name, "$") == 0) /* The -1 param is handled after the loop */
continue;
! snprintf(buf, sizeof(buf), "%s%s",
show_rl(estate_rl(sm->state)),
! estate_capped(sm->state) ? "[c]" : "");
sql_insert_return_states(return_id, return_ranges,
func_gets_user_data ? USER_DATA_SET : USER_DATA,
param, param_name, buf);
} END_FOR_EACH_SM(sm);
--- 1387,1400 ----
if (!param_name)
continue;
if (strcmp(param_name, "$") == 0) /* The -1 param is handled after the loop */
continue;
! snprintf(buf, sizeof(buf), "%s%s%s",
show_rl(estate_rl(sm->state)),
! estate_capped(sm->state) ? "[c]" : "",
! estate_treat_untagged(sm->state) ? "[u]" : "");
sql_insert_return_states(return_id, return_ranges,
func_gets_user_data ? USER_DATA_SET : USER_DATA,
param, param_name, buf);
} END_FOR_EACH_SM(sm);
*** 1379,1400 ****
continue;
if (strcmp(param_name, "$") == 0)
return_found = true;
if (strcmp(param_name, "*$") == 0)
pointed_at_found = true;
! snprintf(buf, sizeof(buf), "%s%s",
show_rl(estate_rl(sm->state)),
! estate_capped(sm->state) ? "[c]" : "");
sql_insert_return_states(return_id, return_ranges,
func_gets_user_data ? USER_DATA_SET : USER_DATA,
-1, param_name, buf);
} END_FOR_EACH_SM(sm);
/* This if for "return ntohl(foo);" */
if (!return_found && get_user_rl(expr, &rl)) {
! snprintf(buf, sizeof(buf), "%s%s",
! show_rl(rl), user_rl_capped(expr) ? "[c]" : "");
sql_insert_return_states(return_id, return_ranges,
func_gets_user_data ? USER_DATA_SET : USER_DATA,
-1, "$", buf);
}
--- 1410,1434 ----
continue;
if (strcmp(param_name, "$") == 0)
return_found = true;
if (strcmp(param_name, "*$") == 0)
pointed_at_found = true;
! snprintf(buf, sizeof(buf), "%s%s%s",
show_rl(estate_rl(sm->state)),
! estate_capped(sm->state) ? "[c]" : "",
! estate_treat_untagged(sm->state) ? "[u]" : "");
sql_insert_return_states(return_id, return_ranges,
func_gets_user_data ? USER_DATA_SET : USER_DATA,
-1, param_name, buf);
} END_FOR_EACH_SM(sm);
/* This if for "return ntohl(foo);" */
if (!return_found && get_user_rl(expr, &rl)) {
! snprintf(buf, sizeof(buf), "%s%s%s",
! show_rl(rl),
! user_rl_capped(expr) ? "[c]" : "",
! user_rl_treat_untagged(expr) ? "[u]" : "");
sql_insert_return_states(return_id, return_ranges,
func_gets_user_data ? USER_DATA_SET : USER_DATA,
-1, "$", buf);
}
*** 1510,1514 ****
--- 1544,1549 ----
if (option_project != PROJ_KERNEL)
return;
select_caller_info_hook(set_called, INTERNAL);
}
+