2 * Copyright (C) 2017 Oracle.
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.
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.
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
19 * This is to help create Trinity fuzzer templates.
24 #include "smatch_slist.h"
36 // nr_segs * sizeof(struct iovec)
37 // if (nr_segs > UIO_MAXIOV)
40 STATE(arg_sockaddrlen
);
41 STATE(arg_socketinfo
);
44 struct smatch_state
*merge_states(struct smatch_state
*s1
, struct smatch_state
*s2
)
51 struct typedef_lookup
{
57 static struct symbol
*_typedef_lookup(const char *name
)
62 id
= built_in_ident(name
);
65 node
= lookup_symbol(id
, NS_TYPEDEF
);
66 if (!node
|| node
->type
!= SYM_NODE
)
68 return get_real_base_type(node
);
71 static void typedef_lookup(struct typedef_lookup
*tl
)
73 if (tl
->sym
|| tl
->failed
)
75 tl
->sym
= _typedef_lookup(tl
->name
);
80 static int is_mode_t(struct symbol
*sym
)
82 static struct typedef_lookup umode_t
= { .name
= "umode_t" };
85 typedef_lookup(&umode_t
);
88 type
= get_base_type(sym
);
89 if (type
== umode_t
.sym
)
94 static int is_pid_t(struct symbol
*sym
)
96 static struct typedef_lookup pid_t
= { .name
= "pid_t" };
99 typedef_lookup(&pid_t
);
102 type
= get_base_type(sym
);
103 if (type
== pid_t
.sym
)
108 static const char *get_arg_type_from_type(struct symbol
*sym
)
117 type
= get_real_base_type(sym
);
118 if (!type
|| type
->type
!= SYM_PTR
)
120 type
= get_real_base_type(type
);
123 if (type
== &char_ctype
)
127 if (strcmp(type
->ident
->name
, "iovec") == 0)
129 if (strcmp(type
->ident
->name
, "sockaddr") == 0)
130 return "ARG_SOCKADDR";
131 return "ARG_ADDRESS";
134 static void match_fdget(const char *fn
, struct expression
*expr
, void *unused
)
136 struct expression
*arg
;
138 arg
= get_argument_from_call_expr(expr
->args
, 0);
139 set_state_expr(my_id
, arg
, &ARG_FD
);
142 const char *get_syscall_arg_type(struct symbol
*sym
)
144 struct smatch_state
*state
;
147 if (!sym
|| !sym
->ident
)
148 return "ARG_UNDEFINED";
149 type
= get_arg_type_from_type(sym
);
152 state
= get_state(my_id
, sym
->ident
->name
, sym
);
154 return "ARG_UNDEFINED";
158 void check_syscall_arg_type(int id
)
161 if (option_project
!= PROJ_KERNEL
)
164 set_dynamic_states(my_id
);
165 add_merge_hook(my_id
, &merge_states
);
166 add_function_hook("fdget", &match_fdget
, NULL
);