Print this page
11972 resync smatch


  33 
  34         /*
  35          * typeof(&dib0070_attach) __a =
  36          * ((((typeof(&dib0070_attach)) (__symbol_get("dib0070_attach")))) ?:
  37          *  (__request_module(true, "symbol:" "dib0070_attach"), (((typeof(&dib0070_attach))(__symbol_get("dib0070_attach"))))));
  38          */
  39 
  40         expr = strip_expr(expr);
  41 
  42         if (expr->type != EXPR_CALL)
  43                 return NULL;
  44         if (!sym_name_is("__symbol_get", expr->fn))
  45                 return NULL;
  46         arg = get_argument_from_call_expr(expr->args, 0);
  47         if (!arg || arg->type != EXPR_STRING)
  48                 return NULL;
  49 
  50         return alloc_string(arg->string->data);
  51 }
  52 








































  53 static char *get_array_ptr(struct expression *expr)
  54 {
  55         struct expression *array;
  56         struct symbol *type;
  57         char *name;
  58         char buf[256];
  59 
  60         array = get_array_base(expr);
  61 
  62         if (array) {
  63                 name = get_member_name(array);
  64                 if (name)
  65                         return name;
  66         }
  67 
  68         /* FIXME:  is_array() should probably be is_array_element() */
  69         type = get_type(expr);
  70         if (!array && type && type->type == SYM_ARRAY)
  71                 array = expr;
  72         if (array) {
  73                 name = expr_to_var(array);
  74                 if (!name)
  75                         return NULL;
  76                 snprintf(buf, sizeof(buf), "%s[]", name);
  77                 return alloc_string(buf);
  78         }
  79 
  80         expr = get_assigned_expr(expr);
  81         array = get_array_base(expr);
  82         if (!array)
  83                 return NULL;
  84         name = expr_to_var(array);
  85         if (!name)
  86                 return NULL;
  87         snprintf(buf, sizeof(buf), "%s[]", name);
  88         free_string(name);
  89         return alloc_string(buf);
  90 }
  91 
  92 static int is_local_symbol(struct symbol *sym)
  93 {
  94         if (!sym ||
  95             !(sym->ctype.modifiers & MOD_TOPLEVEL))
  96                 return 1;
  97         return 0;
  98 }
  99 
 100 static char *ptr_prefix(struct symbol *sym)
 101 {


 124                 return NULL;
 125 
 126         type = get_type(expr);
 127         if (type && type->type == SYM_PTR)
 128                 type = get_real_base_type(type);
 129         if (!type || type->type != SYM_FN)
 130                 return NULL;
 131 
 132         name = expr_to_var(expr->fn);
 133         if (!name)
 134                 return NULL;
 135         snprintf(buf, sizeof(buf), "r %s()", name);
 136         free_string(name);
 137         return alloc_string(buf);
 138 }
 139 
 140 char *get_fnptr_name(struct expression *expr)
 141 {
 142         char *name;
 143 
 144         if (is_zero(expr))
 145                 return NULL;
 146 
 147         expr = strip_expr(expr);
 148 
 149         /* (*ptrs[0])(a, b, c) is the same as ptrs[0](a, b, c); */
 150         if (expr->type == EXPR_PREOP && expr->op == '*')
 151                 expr = strip_expr(expr->unop);
 152 
 153         name = get_from__symbol_get(expr);
 154         if (name)
 155                 return name;
 156 
 157         name = get_array_ptr(expr);
 158         if (name)
 159                 return name;
 160 
 161         name = get_returned_ptr(expr);
 162         if (name)
 163                 return name;
 164 


 238 
 239         *row_count = 0;
 240         if (argc != 1)
 241                 return 0;
 242         *row_count = atoi(argv[0]);
 243         return 0;
 244 }
 245 
 246 static int can_hold_function_ptr(struct expression *expr)
 247 {
 248         struct symbol *type;
 249 
 250         type = get_type(expr);
 251         if (!type)
 252                 return 0;
 253         if (type->type == SYM_PTR || type->type == SYM_ARRAY) {
 254                 type = get_real_base_type(type);
 255                 if (!type)
 256                         return 0;
 257         }






 258         if (type->type == SYM_FN)
 259                 return 1;
 260         if (type == &ulong_ctype && expr->type == EXPR_DEREF)
 261                 return 1;
 262         if (type == &void_ctype)
 263                 return 1;
 264         return 0;
 265 }
 266 
 267 static void match_function_assign(struct expression *expr)
 268 {
 269         struct expression *right;
 270         struct symbol *type;
 271         char *fn_name;
 272         char *ptr_name;
 273 
 274         if (__in_fake_assign)
 275                 return;
 276 
 277         right = strip_expr(expr->right);
 278         if (right->type == EXPR_PREOP && right->op == '&')
 279                 right = strip_expr(right->unop);
 280 
 281         if (right->type != EXPR_SYMBOL &&
 282             right->type != EXPR_DEREF)

 283                 return;
 284 
 285         if (!can_hold_function_ptr(right) ||
 286             !can_hold_function_ptr(expr->left))
 287                 return;
 288 
 289         fn_name = get_fnptr_name(right);
 290         ptr_name = get_fnptr_name(expr->left);
 291         if (!fn_name || !ptr_name)
 292                 goto free;
 293         if (strcmp(fn_name, ptr_name) == 0)
 294                 goto free;
 295 
 296 
 297         type = get_type(right);
 298         if (!type)
 299                 return;
 300         if (type->type == SYM_PTR || type->type == SYM_ARRAY) {
 301                 type = get_real_base_type(type);
 302                 if (!type)




  33 
  34         /*
  35          * typeof(&dib0070_attach) __a =
  36          * ((((typeof(&dib0070_attach)) (__symbol_get("dib0070_attach")))) ?:
  37          *  (__request_module(true, "symbol:" "dib0070_attach"), (((typeof(&dib0070_attach))(__symbol_get("dib0070_attach"))))));
  38          */
  39 
  40         expr = strip_expr(expr);
  41 
  42         if (expr->type != EXPR_CALL)
  43                 return NULL;
  44         if (!sym_name_is("__symbol_get", expr->fn))
  45                 return NULL;
  46         arg = get_argument_from_call_expr(expr->args, 0);
  47         if (!arg || arg->type != EXPR_STRING)
  48                 return NULL;
  49 
  50         return alloc_string(arg->string->data);
  51 }
  52 
  53 static int xxx_is_array(struct expression *expr)
  54 {
  55         struct symbol *type;
  56 
  57         expr = strip_expr(expr);
  58         if (!expr)
  59                 return 0;
  60 
  61         if (expr->type == EXPR_PREOP && expr->op == '*') {
  62                 expr = strip_expr(expr->unop);
  63                 if (!expr)
  64                         return 0;
  65                 if (expr->type == EXPR_BINOP && expr->op == '+')
  66                         return 1;
  67         }
  68 
  69         if (expr->type != EXPR_BINOP || expr->op != '+')
  70                 return 0;
  71 
  72         type = get_type(expr->left);
  73         if (!type)
  74                 return 0;
  75         if (type->type != SYM_ARRAY && type->type != SYM_PTR)
  76                 return 0;
  77 
  78         return 1;
  79 }
  80 
  81 static struct expression *xxx_get_array_base(struct expression *expr)
  82 {
  83         if (!xxx_is_array(expr))
  84                 return NULL;
  85         expr = strip_expr(expr);
  86         if (expr->type == EXPR_PREOP && expr->op == '*')
  87                 expr = strip_expr(expr->unop);
  88         if (expr->type != EXPR_BINOP || expr->op != '+')
  89                 return NULL;
  90         return strip_parens(expr->left);
  91 }
  92 
  93 static char *get_array_ptr(struct expression *expr)
  94 {
  95         struct expression *array;
  96         struct symbol *type;
  97         char *name;
  98         char buf[256];
  99 
 100         array = xxx_get_array_base(expr);
 101 
 102         if (array) {
 103                 name = get_member_name(array);
 104                 if (name)
 105                         return name;
 106         }
 107 
 108         /* FIXME:  is_array() should probably be is_array_element() */
 109         type = get_type(expr);
 110         if (!array && type && type->type == SYM_ARRAY)
 111                 array = expr;
 112         if (array) {
 113                 name = expr_to_var(array);
 114                 if (!name)
 115                         return NULL;
 116                 snprintf(buf, sizeof(buf), "%s[]", name);
 117                 return alloc_string(buf);
 118         }
 119 
 120         expr = get_assigned_expr(expr);
 121         array = xxx_get_array_base(expr);
 122         if (!array)
 123                 return NULL;
 124         name = expr_to_var(array);
 125         if (!name)
 126                 return NULL;
 127         snprintf(buf, sizeof(buf), "%s[]", name);
 128         free_string(name);
 129         return alloc_string(buf);
 130 }
 131 
 132 static int is_local_symbol(struct symbol *sym)
 133 {
 134         if (!sym ||
 135             !(sym->ctype.modifiers & MOD_TOPLEVEL))
 136                 return 1;
 137         return 0;
 138 }
 139 
 140 static char *ptr_prefix(struct symbol *sym)
 141 {


 164                 return NULL;
 165 
 166         type = get_type(expr);
 167         if (type && type->type == SYM_PTR)
 168                 type = get_real_base_type(type);
 169         if (!type || type->type != SYM_FN)
 170                 return NULL;
 171 
 172         name = expr_to_var(expr->fn);
 173         if (!name)
 174                 return NULL;
 175         snprintf(buf, sizeof(buf), "r %s()", name);
 176         free_string(name);
 177         return alloc_string(buf);
 178 }
 179 
 180 char *get_fnptr_name(struct expression *expr)
 181 {
 182         char *name;
 183 
 184         if (expr_is_zero(expr))
 185                 return NULL;
 186 
 187         expr = strip_expr(expr);
 188 
 189         /* (*ptrs[0])(a, b, c) is the same as ptrs[0](a, b, c); */
 190         if (expr->type == EXPR_PREOP && expr->op == '*')
 191                 expr = strip_expr(expr->unop);
 192 
 193         name = get_from__symbol_get(expr);
 194         if (name)
 195                 return name;
 196 
 197         name = get_array_ptr(expr);
 198         if (name)
 199                 return name;
 200 
 201         name = get_returned_ptr(expr);
 202         if (name)
 203                 return name;
 204 


 278 
 279         *row_count = 0;
 280         if (argc != 1)
 281                 return 0;
 282         *row_count = atoi(argv[0]);
 283         return 0;
 284 }
 285 
 286 static int can_hold_function_ptr(struct expression *expr)
 287 {
 288         struct symbol *type;
 289 
 290         type = get_type(expr);
 291         if (!type)
 292                 return 0;
 293         if (type->type == SYM_PTR || type->type == SYM_ARRAY) {
 294                 type = get_real_base_type(type);
 295                 if (!type)
 296                         return 0;
 297         }
 298         /* pointer to a pointer */
 299         if (type->type == SYM_PTR || type->type == SYM_ARRAY) {
 300                 type = get_real_base_type(type);
 301                 if (!type)
 302                         return 0;
 303         }
 304         if (type->type == SYM_FN)
 305                 return 1;
 306         if (type == &ulong_ctype && expr->type == EXPR_DEREF)
 307                 return 1;
 308         if (type == &void_ctype)
 309                 return 1;
 310         return 0;
 311 }
 312 
 313 static void match_function_assign(struct expression *expr)
 314 {
 315         struct expression *right;
 316         struct symbol *type;
 317         char *fn_name;
 318         char *ptr_name;
 319 
 320         if (__in_fake_assign)
 321                 return;
 322 
 323         right = strip_expr(expr->right);
 324         if (right->type == EXPR_PREOP && right->op == '&')
 325                 right = strip_expr(right->unop);
 326 
 327         if (right->type != EXPR_SYMBOL &&
 328             right->type != EXPR_DEREF &&
 329             right->type != EXPR_CALL)
 330                 return;
 331 
 332         if (!can_hold_function_ptr(right) ||
 333             !can_hold_function_ptr(expr->left))
 334                 return;
 335 
 336         fn_name = get_fnptr_name(right);
 337         ptr_name = get_fnptr_name(expr->left);
 338         if (!fn_name || !ptr_name)
 339                 goto free;
 340         if (strcmp(fn_name, ptr_name) == 0)
 341                 goto free;
 342 
 343 
 344         type = get_type(right);
 345         if (!type)
 346                 return;
 347         if (type->type == SYM_PTR || type->type == SYM_ARRAY) {
 348                 type = get_real_base_type(type);
 349                 if (!type)