2 * sparse/smatch_modification_hooks.c
4 * Copyright (C) 2009 Dan Carpenter.
6 * Licensed under the Open Software License version 1.1
17 modification_hook
*call_back
;
21 ALLOCATOR(mcall_back
, "modification call backs");
22 DECLARE_PTR_LIST(mod_cb_list
, struct mcall_back
);
24 static struct hsearch_data var_hash
;
26 static struct mcall_back
*alloc_mcall_back(modification_hook
*call_back
,
29 struct mcall_back
*cb
;
31 cb
= __alloc_mcall_back(0);
32 cb
->call_back
= call_back
;
37 static struct mod_cb_list
*get_mcall_backs(const char *look_for
)
41 e
.key
= (char *)look_for
;
42 hsearch_r(e
, FIND
, &ep
, &var_hash
);
45 return (struct mod_cb_list
*)ep
->data
;
48 static void add_mcall_back(const char *look_for
, struct mcall_back
*cb
)
53 e
.key
= alloc_string(look_for
);
54 hsearch_r(e
, FIND
, &ep
, &var_hash
);
56 struct mod_cb_list
*list
= NULL
;
58 add_ptr_list(&list
, cb
);
63 add_ptr_list((struct mod_cb_list
**)&ep
->data
, cb
);
66 if (!hsearch_r(e
, ENTER
, &ep
, &var_hash
)) {
67 printf("Error hash table too small in smatch_modification_hooks.c\n");
73 void add_modification_hook(const char *variable
, modification_hook
*call_back
, void *info
)
75 struct mcall_back
*cb
;
77 cb
= alloc_mcall_back(call_back
, info
);
78 add_mcall_back(variable
, cb
);
81 static void call_call_backs(struct mod_cb_list
*list
,
84 struct expression
*expr
)
86 struct mcall_back
*tmp
;
88 FOR_EACH_PTR(list
, tmp
) {
89 (tmp
->call_back
)(variable
, sym
, expr
, tmp
->info
);
90 } END_FOR_EACH_PTR(tmp
);
94 static void match_assign(struct expression
*expr
)
96 struct mod_cb_list
*call_backs
;
97 struct expression
*left
;
101 left
= strip_expr(expr
->left
);
102 name
= get_variable_from_expr(left
, &sym
);
105 call_backs
= get_mcall_backs(name
);
108 call_call_backs(call_backs
, name
, sym
, expr
);
113 static void match_end_func(struct symbol
*sym
)
115 hdestroy_r(&var_hash
);
116 hcreate_r(1000, &var_hash
);
119 void register_modification_hooks(int id
)
121 hcreate_r(1000, &var_hash
);
122 add_hook(&match_assign
, ASSIGNMENT_HOOK
);
123 add_hook(&match_end_func
, END_FUNC_HOOK
);