1 /* 2 * Copyright (C) 2014 Oracle. 3 * 4 * This program is free software; you can redistribute it and/or 5 * modify it under the terms of the GNU General Public License 6 * as published by the Free Software Foundation; either version 2 7 * of the License, or (at your option) any later version. 8 * 9 * This program is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 * GNU General Public License for more details. 13 * 14 * You should have received a copy of the GNU General Public License 15 * along with this program; if not, see http://www.gnu.org/copyleft/gpl.txt 16 */ 17 18 #include "smatch.h" 19 #include "smatch_slist.h" 20 21 static int my_id; 22 23 static int *auto_copy; 24 25 void set_auto_copy(int owner) 26 { 27 if (owner <= 1 || owner > num_checks) { 28 sm_ierror("bogus set_auto_copy()"); 29 return; 30 } 31 auto_copy[owner] = 1; 32 } 33 34 static void match_assign(struct expression *expr) 35 { 36 char *left_name = NULL; 37 char *right_name = NULL; 38 struct symbol *left_sym, *right_sym; 39 struct state_list *slist = NULL; 40 struct sm_state *sm; 41 42 left_name = expr_to_var_sym(expr->left, &left_sym); 43 if (!left_name || !left_sym) 44 goto free; 45 right_name = expr_to_var_sym(expr->right, &right_sym); 46 if (!right_name || !right_sym) 47 goto free; 48 49 FOR_EACH_SM(__get_cur_stree(), sm) { 50 if (sm->owner <= 1 || sm->owner > num_checks) 51 continue; 52 if (!auto_copy[sm->owner]) 53 continue; 54 if (right_sym != sm->sym) 55 continue; 56 if (strcmp(right_name, sm->name) != 0) 57 continue; 58 add_ptr_list(&slist, sm); 59 } END_FOR_EACH_SM(sm); 60 61 62 FOR_EACH_PTR(slist, sm) { 63 set_state(sm->owner, left_name, left_sym, sm->state); 64 } END_FOR_EACH_PTR(sm); 65 66 free: 67 free_slist(&slist); 68 free_string(left_name); 69 free_string(right_name); 70 } 71 72 void register_auto_copy(int id) 73 { 74 my_id = id; 75 auto_copy = malloc((num_checks + 1) * sizeof(*auto_copy)); 76 memset(auto_copy, 0, (num_checks + 1) * sizeof(*auto_copy)); 77 78 add_hook(&match_assign, ASSIGNMENT_HOOK); 79 }