1061 struct db_callback_info *db_info = _info;
1062 struct range_list *ret_range;
1063 int type, param;
1064 char *ret_str, *key, *value;
1065 struct return_implies_callback *tmp;
1066 struct stree *stree;
1067 int return_id;
1068 char buf[64];
1069
1070 if (argc != 6)
1071 return 0;
1072
1073 return_id = atoi(argv[0]);
1074 ret_str = argv[1];
1075 type = atoi(argv[2]);
1076 param = atoi(argv[3]);
1077 key = argv[4];
1078 value = argv[5];
1079
1080 if (db_info->prev_return_id != -1 && type == INTERNAL) {
1081 stree = __pop_fake_cur_stree();
1082 if (!db_info->cull)
1083 merge_fake_stree(&db_info->stree, stree);
1084 free_stree(&stree);
1085 __push_fake_cur_stree();
1086 __unnullify_path();
1087 db_info->cull = 0;
1088 }
1089 db_info->prev_return_id = return_id;
1090
1091 if (type == INTERNAL && func_type_mismatch(db_info->expr, value))
1092 db_info->cull = 1;
1093 if (db_info->cull)
1094 return 0;
1095 if (type == CULL_PATH) {
1096 db_info->cull = 1;
1097 return 0;
1098 }
1099 if (is_impossible_data(type, db_info->expr, param, key, value)) {
1100 db_info->cull = 1;
1101 return 0;
1102 }
1103
1104 if (type == PARAM_LIMIT)
1105 param_limit_implications(db_info->expr, param, key, value);
1106
1107 call_results_to_rl(db_info->expr, get_type(strip_expr(db_info->expr)), ret_str, &ret_range);
1108 ret_range = cast_rl(get_type(db_info->expr), ret_range);
1109
1110 if (type == INTERNAL) {
1111 set_state(-1, "unnull_path", NULL, &true_state);
1112 __add_return_comparison(strip_expr(db_info->expr), ret_str);
1113 __add_return_to_param_mapping(db_info->expr, ret_str);
1114 }
1115
1116 FOR_EACH_PTR(db_return_states_list, tmp) {
1117 if (tmp->type == type)
1118 tmp->callback(db_info->expr, param, key, value);
1119 } END_FOR_EACH_PTR(tmp);
1120
1121 /*
1122 * We want to store the return values so that we can split the strees
1123 * in smatch_db.c. This uses set_state() directly because it's not a
1124 * real smatch_extra state.
1125 */
1126 snprintf(buf, sizeof(buf), "return %p", db_info->expr);
1127 set_state(SMATCH_EXTRA, buf, NULL, alloc_estate_rl(ret_range));
1128
1129 return 0;
1130 }
1131
1132 static void db_return_states(struct expression *expr)
1133 {
1134 struct sm_state *sm;
1135 struct stree *stree;
1136 struct db_callback_info db_info = {};
1137
1138 if (!__get_cur_stree()) /* no return functions */
1139 return;
1140
1141 db_info.prev_return_id = -1;
1142 db_info.expr = expr;
1143 db_info.stree = NULL;
1144
1145 call_return_states_before_hooks();
1146
1147 __push_fake_cur_stree();
1148 __unnullify_path();
1149 sql_select_return_states("return_id, return, type, parameter, key, value",
1150 expr, db_return_states_callback, &db_info);
1151 stree = __pop_fake_cur_stree();
1152 if (!db_info.cull)
1153 merge_fake_stree(&db_info.stree, stree);
1154 free_stree(&stree);
1155
1156 FOR_EACH_SM(db_info.stree, sm) {
1157 __set_sm(sm);
1158 } END_FOR_EACH_SM(sm);
1159
1160 free_stree(&db_info.stree);
1161 call_return_states_after_hooks(expr);
1162 }
1163
1164 static int is_condition_call(struct expression *expr)
1165 {
1166 struct expression *tmp;
1167
1168 FOR_EACH_PTR_REVERSE(big_condition_stack, tmp) {
1169 if (expr == tmp || expr_get_parent_expr(expr) == tmp)
1170 return 1;
|
1061 struct db_callback_info *db_info = _info;
1062 struct range_list *ret_range;
1063 int type, param;
1064 char *ret_str, *key, *value;
1065 struct return_implies_callback *tmp;
1066 struct stree *stree;
1067 int return_id;
1068 char buf[64];
1069
1070 if (argc != 6)
1071 return 0;
1072
1073 return_id = atoi(argv[0]);
1074 ret_str = argv[1];
1075 type = atoi(argv[2]);
1076 param = atoi(argv[3]);
1077 key = argv[4];
1078 value = argv[5];
1079
1080 if (db_info->prev_return_id != -1 && type == INTERNAL) {
1081 call_ranged_return_hooks(db_info);
1082 stree = __pop_fake_cur_stree();
1083 if (!db_info->cull)
1084 merge_fake_stree(&db_info->stree, stree);
1085 free_stree(&stree);
1086 __push_fake_cur_stree();
1087 __unnullify_path();
1088 db_info->cull = 0;
1089 }
1090 db_info->prev_return_id = return_id;
1091
1092 if (type == INTERNAL && func_type_mismatch(db_info->expr, value))
1093 db_info->cull = 1;
1094 if (db_info->cull)
1095 return 0;
1096 if (type == CULL_PATH) {
1097 db_info->cull = 1;
1098 return 0;
1099 }
1100 if (is_impossible_data(type, db_info->expr, param, key, value)) {
1101 db_info->cull = 1;
1102 return 0;
1103 }
1104
1105 if (type == PARAM_LIMIT)
1106 param_limit_implications(db_info->expr, param, key, value);
1107
1108 call_results_to_rl(db_info->expr, get_type(strip_expr(db_info->expr)), ret_str, &ret_range);
1109 ret_range = cast_rl(get_type(db_info->expr), ret_range);
1110
1111 if (type == INTERNAL) {
1112 struct smatch_state *state;
1113
1114 set_state(-1, "unnull_path", NULL, &true_state);
1115 __add_return_comparison(strip_expr(db_info->expr), ret_str);
1116 __add_return_to_param_mapping(db_info->expr, ret_str);
1117 /*
1118 * We want to store the return values so that we can split the strees
1119 * in smatch_db.c. This uses set_state() directly because it's not a
1120 * real smatch_extra state.
1121 */
1122 snprintf(buf, sizeof(buf), "return %p", db_info->expr);
1123 state = alloc_estate_rl(ret_range);
1124 set_state(SMATCH_EXTRA, buf, NULL, state);
1125 store_return_state(db_info, ret_str, state);
1126 }
1127
1128 FOR_EACH_PTR(db_return_states_list, tmp) {
1129 if (tmp->type == type)
1130 tmp->callback(db_info->expr, param, key, value);
1131 } END_FOR_EACH_PTR(tmp);
1132
1133
1134 return 0;
1135 }
1136
1137 static void db_return_states(struct expression *expr)
1138 {
1139 struct sm_state *sm;
1140 struct stree *stree;
1141 struct db_callback_info db_info = {};
1142
1143 if (!__get_cur_stree()) /* no return functions */
1144 return;
1145
1146 db_info.prev_return_id = -1;
1147 db_info.expr = expr;
1148 db_info.stree = NULL;
1149
1150 call_return_states_before_hooks();
1151
1152 __push_fake_cur_stree();
1153 __unnullify_path();
1154 sql_select_return_states("return_id, return, type, parameter, key, value",
1155 expr, db_return_states_callback, &db_info);
1156 call_ranged_return_hooks(&db_info);
1157 stree = __pop_fake_cur_stree();
1158 if (!db_info.cull)
1159 merge_fake_stree(&db_info.stree, stree);
1160 free_stree(&stree);
1161
1162 FOR_EACH_SM(db_info.stree, sm) {
1163 __set_sm(sm);
1164 } END_FOR_EACH_SM(sm);
1165
1166 free_stree(&db_info.stree);
1167 call_return_states_after_hooks(expr);
1168 }
1169
1170 static int is_condition_call(struct expression *expr)
1171 {
1172 struct expression *tmp;
1173
1174 FOR_EACH_PTR_REVERSE(big_condition_stack, tmp) {
1175 if (expr == tmp || expr_get_parent_expr(expr) == tmp)
1176 return 1;
|