1 /* 2 * Common code for probe-based Dynamic events. 3 * 4 * This program is free software; you can redistribute it and/or modify 5 * it under the terms of the GNU General Public License version 2 as 6 * published by the Free Software Foundation. 7 * 8 * This program is distributed in the hope that it will be useful, 9 * but WITHOUT ANY WARRANTY; without even the implied warranty of 10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 11 * GNU General Public License for more details. 12 * 13 * You should have received a copy of the GNU General Public License 14 * along with this program; if not, write to the Free Software 15 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 16 * 17 * This code was copied from kernel/trace/trace_kprobe.c written by 18 * Masami Hiramatsu <masami.hiramatsu.pt@hitachi.com> 19 * 20 * Updates to make this generic: 21 * Copyright (C) IBM Corporation, 2010-2011 22 * Author: Srikar Dronamraju 23 */ 24 25 #include "trace_probe.h" 26 27 const char *reserved_field_names[] = { 28 "common_type", 29 "common_flags", 30 "common_preempt_count", 31 "common_pid", 32 "common_tgid", 33 FIELD_STRING_IP, 34 FIELD_STRING_RETIP, 35 FIELD_STRING_FUNC, 36 }; 37 38 /* Printing in basic type function template */ 39 #define DEFINE_BASIC_PRINT_TYPE_FUNC(type, fmt) \ 40 int PRINT_TYPE_FUNC_NAME(type)(struct trace_seq *s, const char *name, \ 41 void *data, void *ent) \ 42 { \ 43 trace_seq_printf(s, " %s=" fmt, name, *(type *)data); \ 44 return !trace_seq_has_overflowed(s); \ 45 } \ 46 const char PRINT_TYPE_FMT_NAME(type)[] = fmt; \ 47 NOKPROBE_SYMBOL(PRINT_TYPE_FUNC_NAME(type)); 48 49 DEFINE_BASIC_PRINT_TYPE_FUNC(u8 , "0x%x") 50 DEFINE_BASIC_PRINT_TYPE_FUNC(u16, "0x%x") 51 DEFINE_BASIC_PRINT_TYPE_FUNC(u32, "0x%x") 52 DEFINE_BASIC_PRINT_TYPE_FUNC(u64, "0x%Lx") 53 DEFINE_BASIC_PRINT_TYPE_FUNC(s8, "%d") 54 DEFINE_BASIC_PRINT_TYPE_FUNC(s16, "%d") 55 DEFINE_BASIC_PRINT_TYPE_FUNC(s32, "%d") 56 DEFINE_BASIC_PRINT_TYPE_FUNC(s64, "%Ld") 57 58 /* Print type function for string type */ 59 int PRINT_TYPE_FUNC_NAME(string)(struct trace_seq *s, const char *name, 60 void *data, void *ent) 61 { 62 int len = *(u32 *)data >> 16; 63 64 if (!len) 65 trace_seq_printf(s, " %s=(fault)", name); 66 else 67 trace_seq_printf(s, " %s=\"%s\"", name, 68 (const char *)get_loc_data(data, ent)); 69 return !trace_seq_has_overflowed(s); 70 } 71 NOKPROBE_SYMBOL(PRINT_TYPE_FUNC_NAME(string)); 72 73 const char PRINT_TYPE_FMT_NAME(string)[] = "\\\"%s\\\""; 74 75 #define CHECK_FETCH_FUNCS(method, fn) \ 76 (((FETCH_FUNC_NAME(method, u8) == fn) || \ 77 (FETCH_FUNC_NAME(method, u16) == fn) || \ 78 (FETCH_FUNC_NAME(method, u32) == fn) || \ 79 (FETCH_FUNC_NAME(method, u64) == fn) || \ 80 (FETCH_FUNC_NAME(method, string) == fn) || \ 81 (FETCH_FUNC_NAME(method, string_size) == fn)) \ 82 && (fn != NULL)) 83 84 /* Data fetch function templates */ 85 #define DEFINE_FETCH_reg(type) \ 86 void FETCH_FUNC_NAME(reg, type)(struct pt_regs *regs, void *offset, void *dest) \ 87 { \ 88 *(type *)dest = (type)regs_get_register(regs, \ 89 (unsigned int)((unsigned long)offset)); \ 90 } \ 91 NOKPROBE_SYMBOL(FETCH_FUNC_NAME(reg, type)); 92 DEFINE_BASIC_FETCH_FUNCS(reg) 93 /* No string on the register */ 94 #define fetch_reg_string NULL 95 #define fetch_reg_string_size NULL 96 97 #define DEFINE_FETCH_retval(type) \ 98 void FETCH_FUNC_NAME(retval, type)(struct pt_regs *regs, \ 99 void *dummy, void *dest) \ 100 { \ 101 *(type *)dest = (type)regs_return_value(regs); \ 102 } \ 103 NOKPROBE_SYMBOL(FETCH_FUNC_NAME(retval, type)); 104 DEFINE_BASIC_FETCH_FUNCS(retval) 105 /* No string on the retval */ 106 #define fetch_retval_string NULL 107 #define fetch_retval_string_size NULL 108 109 /* Dereference memory access function */ 110 struct deref_fetch_param { 111 struct fetch_param orig; 112 long offset; 113 fetch_func_t fetch; 114 fetch_func_t fetch_size; 115 }; 116 117 #define DEFINE_FETCH_deref(type) \ 118 void FETCH_FUNC_NAME(deref, type)(struct pt_regs *regs, \ 119 void *data, void *dest) \ 120 { \ 121 struct deref_fetch_param *dprm = data; \ 122 unsigned long addr; \ 123 call_fetch(&dprm->orig, regs, &addr); \ 124 if (addr) { \ 125 addr += dprm->offset; \ 126 dprm->fetch(regs, (void *)addr, dest); \ 127 } else \ 128 *(type *)dest = 0; \ 129 } \ 130 NOKPROBE_SYMBOL(FETCH_FUNC_NAME(deref, type)); 131 DEFINE_BASIC_FETCH_FUNCS(deref) 132 DEFINE_FETCH_deref(string) 133 134 void FETCH_FUNC_NAME(deref, string_size)(struct pt_regs *regs, 135 void *data, void *dest) 136 { 137 struct deref_fetch_param *dprm = data; 138 unsigned long addr; 139 140 call_fetch(&dprm->orig, regs, &addr); 141 if (addr && dprm->fetch_size) { 142 addr += dprm->offset; 143 dprm->fetch_size(regs, (void *)addr, dest); 144 } else 145 *(string_size *)dest = 0; 146 } 147 NOKPROBE_SYMBOL(FETCH_FUNC_NAME(deref, string_size)); 148 149 static void update_deref_fetch_param(struct deref_fetch_param *data) 150 { 151 if (CHECK_FETCH_FUNCS(deref, data->orig.fn)) 152 update_deref_fetch_param(data->orig.data); 153 else if (CHECK_FETCH_FUNCS(symbol, data->orig.fn)) 154 update_symbol_cache(data->orig.data); 155 } 156 NOKPROBE_SYMBOL(update_deref_fetch_param); 157 158 static void free_deref_fetch_param(struct deref_fetch_param *data) 159 { 160 if (CHECK_FETCH_FUNCS(deref, data->orig.fn)) 161 free_deref_fetch_param(data->orig.data); 162 else if (CHECK_FETCH_FUNCS(symbol, data->orig.fn)) 163 free_symbol_cache(data->orig.data); 164 kfree(data); 165 } 166 NOKPROBE_SYMBOL(free_deref_fetch_param); 167 168 /* Bitfield fetch function */ 169 struct bitfield_fetch_param { 170 struct fetch_param orig; 171 unsigned char hi_shift; 172 unsigned char low_shift; 173 }; 174 175 #define DEFINE_FETCH_bitfield(type) \ 176 void FETCH_FUNC_NAME(bitfield, type)(struct pt_regs *regs, \ 177 void *data, void *dest) \ 178 { \ 179 struct bitfield_fetch_param *bprm = data; \ 180 type buf = 0; \ 181 call_fetch(&bprm->orig, regs, &buf); \ 182 if (buf) { \ 183 buf <<= bprm->hi_shift; \ 184 buf >>= bprm->low_shift; \ 185 } \ 186 *(type *)dest = buf; \ 187 } \ 188 NOKPROBE_SYMBOL(FETCH_FUNC_NAME(bitfield, type)); 189 DEFINE_BASIC_FETCH_FUNCS(bitfield) 190 #define fetch_bitfield_string NULL 191 #define fetch_bitfield_string_size NULL 192 193 static void 194 update_bitfield_fetch_param(struct bitfield_fetch_param *data) 195 { 196 /* 197 * Don't check the bitfield itself, because this must be the 198 * last fetch function. 199 */ 200 if (CHECK_FETCH_FUNCS(deref, data->orig.fn)) 201 update_deref_fetch_param(data->orig.data); 202 else if (CHECK_FETCH_FUNCS(symbol, data->orig.fn)) 203 update_symbol_cache(data->orig.data); 204 } 205 206 static void 207 free_bitfield_fetch_param(struct bitfield_fetch_param *data) 208 { 209 /* 210 * Don't check the bitfield itself, because this must be the 211 * last fetch function. 212 */ 213 if (CHECK_FETCH_FUNCS(deref, data->orig.fn)) 214 free_deref_fetch_param(data->orig.data); 215 else if (CHECK_FETCH_FUNCS(symbol, data->orig.fn)) 216 free_symbol_cache(data->orig.data); 217 218 kfree(data); 219 } 220 221 void FETCH_FUNC_NAME(comm, string)(struct pt_regs *regs, 222 void *data, void *dest) 223 { 224 int maxlen = get_rloc_len(*(u32 *)dest); 225 u8 *dst = get_rloc_data(dest); 226 long ret; 227 228 if (!maxlen) 229 return; 230 231 ret = strlcpy(dst, current->comm, maxlen); 232 *(u32 *)dest = make_data_rloc(ret, get_rloc_offs(*(u32 *)dest)); 233 } 234 NOKPROBE_SYMBOL(FETCH_FUNC_NAME(comm, string)); 235 236 void FETCH_FUNC_NAME(comm, string_size)(struct pt_regs *regs, 237 void *data, void *dest) 238 { 239 *(u32 *)dest = strlen(current->comm) + 1; 240 } 241 NOKPROBE_SYMBOL(FETCH_FUNC_NAME(comm, string_size)); 242 243 static const struct fetch_type *find_fetch_type(const char *type, 244 const struct fetch_type *ftbl) 245 { 246 int i; 247 248 if (!type) 249 type = DEFAULT_FETCH_TYPE_STR; 250 251 /* Special case: bitfield */ 252 if (*type == 'b') { 253 unsigned long bs; 254 255 type = strchr(type, '/'); 256 if (!type) 257 goto fail; 258 259 type++; 260 if (kstrtoul(type, 0, &bs)) 261 goto fail; 262 263 switch (bs) { 264 case 8: 265 return find_fetch_type("u8", ftbl); 266 case 16: 267 return find_fetch_type("u16", ftbl); 268 case 32: 269 return find_fetch_type("u32", ftbl); 270 case 64: 271 return find_fetch_type("u64", ftbl); 272 default: 273 goto fail; 274 } 275 } 276 277 for (i = 0; ftbl[i].name; i++) { 278 if (strcmp(type, ftbl[i].name) == 0) 279 return &ftbl[i]; 280 } 281 282 fail: 283 return NULL; 284 } 285 286 /* Special function : only accept unsigned long */ 287 static void fetch_kernel_stack_address(struct pt_regs *regs, void *dummy, void *dest) 288 { 289 *(unsigned long *)dest = kernel_stack_pointer(regs); 290 } 291 NOKPROBE_SYMBOL(fetch_kernel_stack_address); 292 293 static void fetch_user_stack_address(struct pt_regs *regs, void *dummy, void *dest) 294 { 295 *(unsigned long *)dest = user_stack_pointer(regs); 296 } 297 NOKPROBE_SYMBOL(fetch_user_stack_address); 298 299 static fetch_func_t get_fetch_size_function(const struct fetch_type *type, 300 fetch_func_t orig_fn, 301 const struct fetch_type *ftbl) 302 { 303 int i; 304 305 if (type != &ftbl[FETCH_TYPE_STRING]) 306 return NULL; /* Only string type needs size function */ 307 308 for (i = 0; i < FETCH_MTD_END; i++) 309 if (type->fetch[i] == orig_fn) 310 return ftbl[FETCH_TYPE_STRSIZE].fetch[i]; 311 312 WARN_ON(1); /* This should not happen */ 313 314 return NULL; 315 } 316 317 /* Split symbol and offset. */ 318 int traceprobe_split_symbol_offset(char *symbol, unsigned long *offset) 319 { 320 char *tmp; 321 int ret; 322 323 if (!offset) 324 return -EINVAL; 325 326 tmp = strchr(symbol, '+'); 327 if (tmp) { 328 /* skip sign because kstrtoul doesn't accept '+' */ 329 ret = kstrtoul(tmp + 1, 0, offset); 330 if (ret) 331 return ret; 332 333 *tmp = '\0'; 334 } else 335 *offset = 0; 336 337 return 0; 338 } 339 340 #define PARAM_MAX_STACK (THREAD_SIZE / sizeof(unsigned long)) 341 342 static int parse_probe_vars(char *arg, const struct fetch_type *t, 343 struct fetch_param *f, bool is_return, 344 bool is_kprobe) 345 { 346 int ret = 0; 347 unsigned long param; 348 349 if (strcmp(arg, "retval") == 0) { 350 if (is_return) 351 f->fn = t->fetch[FETCH_MTD_retval]; 352 else 353 ret = -EINVAL; 354 } else if (strncmp(arg, "stack", 5) == 0) { 355 if (arg[5] == '\0') { 356 if (strcmp(t->name, DEFAULT_FETCH_TYPE_STR)) 357 return -EINVAL; 358 359 if (is_kprobe) 360 f->fn = fetch_kernel_stack_address; 361 else 362 f->fn = fetch_user_stack_address; 363 } else if (isdigit(arg[5])) { 364 ret = kstrtoul(arg + 5, 10, ¶m); 365 if (ret || (is_kprobe && param > PARAM_MAX_STACK)) 366 ret = -EINVAL; 367 else { 368 f->fn = t->fetch[FETCH_MTD_stack]; 369 f->data = (void *)param; 370 } 371 } else 372 ret = -EINVAL; 373 } else if (strcmp(arg, "comm") == 0) { 374 if (strcmp(t->name, "string") != 0 && 375 strcmp(t->name, "string_size") != 0) 376 return -EINVAL; 377 f->fn = t->fetch[FETCH_MTD_comm]; 378 } else 379 ret = -EINVAL; 380 381 return ret; 382 } 383 384 /* Recursive argument parser */ 385 static int parse_probe_arg(char *arg, const struct fetch_type *t, 386 struct fetch_param *f, bool is_return, bool is_kprobe, 387 const struct fetch_type *ftbl) 388 { 389 unsigned long param; 390 long offset; 391 char *tmp; 392 int ret = 0; 393 394 switch (arg[0]) { 395 case '$': 396 ret = parse_probe_vars(arg + 1, t, f, is_return, is_kprobe); 397 break; 398 399 case '%': /* named register */ 400 ret = regs_query_register_offset(arg + 1); 401 if (ret >= 0) { 402 f->fn = t->fetch[FETCH_MTD_reg]; 403 f->data = (void *)(unsigned long)ret; 404 ret = 0; 405 } 406 break; 407 408 case '@': /* memory, file-offset or symbol */ 409 if (isdigit(arg[1])) { 410 ret = kstrtoul(arg + 1, 0, ¶m); 411 if (ret) 412 break; 413 414 f->fn = t->fetch[FETCH_MTD_memory]; 415 f->data = (void *)param; 416 } else if (arg[1] == '+') { 417 /* kprobes don't support file offsets */ 418 if (is_kprobe) 419 return -EINVAL; 420 421 ret = kstrtol(arg + 2, 0, &offset); 422 if (ret) 423 break; 424 425 f->fn = t->fetch[FETCH_MTD_file_offset]; 426 f->data = (void *)offset; 427 } else { 428 /* uprobes don't support symbols */ 429 if (!is_kprobe) 430 return -EINVAL; 431 432 ret = traceprobe_split_symbol_offset(arg + 1, &offset); 433 if (ret) 434 break; 435 436 f->data = alloc_symbol_cache(arg + 1, offset); 437 if (f->data) 438 f->fn = t->fetch[FETCH_MTD_symbol]; 439 } 440 break; 441 442 case '+': /* deref memory */ 443 arg++; /* Skip '+', because kstrtol() rejects it. */ 444 case '-': 445 tmp = strchr(arg, '('); 446 if (!tmp) 447 break; 448 449 *tmp = '\0'; 450 ret = kstrtol(arg, 0, &offset); 451 452 if (ret) 453 break; 454 455 arg = tmp + 1; 456 tmp = strrchr(arg, ')'); 457 458 if (tmp) { 459 struct deref_fetch_param *dprm; 460 const struct fetch_type *t2; 461 462 t2 = find_fetch_type(NULL, ftbl); 463 *tmp = '\0'; 464 dprm = kzalloc(sizeof(struct deref_fetch_param), GFP_KERNEL); 465 466 if (!dprm) 467 return -ENOMEM; 468 469 dprm->offset = offset; 470 dprm->fetch = t->fetch[FETCH_MTD_memory]; 471 dprm->fetch_size = get_fetch_size_function(t, 472 dprm->fetch, ftbl); 473 ret = parse_probe_arg(arg, t2, &dprm->orig, is_return, 474 is_kprobe, ftbl); 475 if (ret) 476 kfree(dprm); 477 else { 478 f->fn = t->fetch[FETCH_MTD_deref]; 479 f->data = (void *)dprm; 480 } 481 } 482 break; 483 } 484 if (!ret && !f->fn) { /* Parsed, but do not find fetch method */ 485 pr_info("%s type has no corresponding fetch method.\n", t->name); 486 ret = -EINVAL; 487 } 488 489 return ret; 490 } 491 492 #define BYTES_TO_BITS(nb) ((BITS_PER_LONG * (nb)) / sizeof(long)) 493 494 /* Bitfield type needs to be parsed into a fetch function */ 495 static int __parse_bitfield_probe_arg(const char *bf, 496 const struct fetch_type *t, 497 struct fetch_param *f) 498 { 499 struct bitfield_fetch_param *bprm; 500 unsigned long bw, bo; 501 char *tail; 502 503 if (*bf != 'b') 504 return 0; 505 506 bprm = kzalloc(sizeof(*bprm), GFP_KERNEL); 507 if (!bprm) 508 return -ENOMEM; 509 510 bprm->orig = *f; 511 f->fn = t->fetch[FETCH_MTD_bitfield]; 512 f->data = (void *)bprm; 513 bw = simple_strtoul(bf + 1, &tail, 0); /* Use simple one */ 514 515 if (bw == 0 || *tail != '@') 516 return -EINVAL; 517 518 bf = tail + 1; 519 bo = simple_strtoul(bf, &tail, 0); 520 521 if (tail == bf || *tail != '/') 522 return -EINVAL; 523 524 bprm->hi_shift = BYTES_TO_BITS(t->size) - (bw + bo); 525 bprm->low_shift = bprm->hi_shift + bo; 526 527 return (BYTES_TO_BITS(t->size) < (bw + bo)) ? -EINVAL : 0; 528 } 529 530 /* String length checking wrapper */ 531 int traceprobe_parse_probe_arg(char *arg, ssize_t *size, 532 struct probe_arg *parg, bool is_return, bool is_kprobe, 533 const struct fetch_type *ftbl) 534 { 535 const char *t; 536 int ret; 537 538 if (strlen(arg) > MAX_ARGSTR_LEN) { 539 pr_info("Argument is too long.: %s\n", arg); 540 return -ENOSPC; 541 } 542 parg->comm = kstrdup(arg, GFP_KERNEL); 543 if (!parg->comm) { 544 pr_info("Failed to allocate memory for command '%s'.\n", arg); 545 return -ENOMEM; 546 } 547 t = strchr(parg->comm, ':'); 548 if (t) { 549 arg[t - parg->comm] = '\0'; 550 t++; 551 } 552 /* 553 * The default type of $comm should be "string", and it can't be 554 * dereferenced. 555 */ 556 if (!t && strcmp(arg, "$comm") == 0) 557 t = "string"; 558 parg->type = find_fetch_type(t, ftbl); 559 if (!parg->type) { 560 pr_info("Unsupported type: %s\n", t); 561 return -EINVAL; 562 } 563 parg->offset = *size; 564 *size += parg->type->size; 565 ret = parse_probe_arg(arg, parg->type, &parg->fetch, is_return, 566 is_kprobe, ftbl); 567 568 if (ret >= 0 && t != NULL) 569 ret = __parse_bitfield_probe_arg(t, parg->type, &parg->fetch); 570 571 if (ret >= 0) { 572 parg->fetch_size.fn = get_fetch_size_function(parg->type, 573 parg->fetch.fn, 574 ftbl); 575 parg->fetch_size.data = parg->fetch.data; 576 } 577 578 return ret; 579 } 580 581 /* Return 1 if name is reserved or already used by another argument */ 582 int traceprobe_conflict_field_name(const char *name, 583 struct probe_arg *args, int narg) 584 { 585 int i; 586 587 for (i = 0; i < ARRAY_SIZE(reserved_field_names); i++) 588 if (strcmp(reserved_field_names[i], name) == 0) 589 return 1; 590 591 for (i = 0; i < narg; i++) 592 if (strcmp(args[i].name, name) == 0) 593 return 1; 594 595 return 0; 596 } 597 598 void traceprobe_update_arg(struct probe_arg *arg) 599 { 600 if (CHECK_FETCH_FUNCS(bitfield, arg->fetch.fn)) 601 update_bitfield_fetch_param(arg->fetch.data); 602 else if (CHECK_FETCH_FUNCS(deref, arg->fetch.fn)) 603 update_deref_fetch_param(arg->fetch.data); 604 else if (CHECK_FETCH_FUNCS(symbol, arg->fetch.fn)) 605 update_symbol_cache(arg->fetch.data); 606 } 607 608 void traceprobe_free_probe_arg(struct probe_arg *arg) 609 { 610 if (CHECK_FETCH_FUNCS(bitfield, arg->fetch.fn)) 611 free_bitfield_fetch_param(arg->fetch.data); 612 else if (CHECK_FETCH_FUNCS(deref, arg->fetch.fn)) 613 free_deref_fetch_param(arg->fetch.data); 614 else if (CHECK_FETCH_FUNCS(symbol, arg->fetch.fn)) 615 free_symbol_cache(arg->fetch.data); 616 617 kfree(arg->name); 618 kfree(arg->comm); 619 } 620 621 int traceprobe_command(const char *buf, int (*createfn)(int, char **)) 622 { 623 char **argv; 624 int argc, ret; 625 626 argc = 0; 627 ret = 0; 628 argv = argv_split(GFP_KERNEL, buf, &argc); 629 if (!argv) 630 return -ENOMEM; 631 632 if (argc) 633 ret = createfn(argc, argv); 634 635 argv_free(argv); 636 637 return ret; 638 } 639 640 #define WRITE_BUFSIZE 4096 641 642 ssize_t traceprobe_probes_write(struct file *file, const char __user *buffer, 643 size_t count, loff_t *ppos, 644 int (*createfn)(int, char **)) 645 { 646 char *kbuf, *tmp; 647 int ret = 0; 648 size_t done = 0; 649 size_t size; 650 651 kbuf = kmalloc(WRITE_BUFSIZE, GFP_KERNEL); 652 if (!kbuf) 653 return -ENOMEM; 654 655 while (done < count) { 656 size = count - done; 657 658 if (size >= WRITE_BUFSIZE) 659 size = WRITE_BUFSIZE - 1; 660 661 if (copy_from_user(kbuf, buffer + done, size)) { 662 ret = -EFAULT; 663 goto out; 664 } 665 kbuf[size] = '\0'; 666 tmp = strchr(kbuf, '\n'); 667 668 if (tmp) { 669 *tmp = '\0'; 670 size = tmp - kbuf + 1; 671 } else if (done + size < count) { 672 pr_warn("Line length is too long: Should be less than %d\n", 673 WRITE_BUFSIZE); 674 ret = -EINVAL; 675 goto out; 676 } 677 done += size; 678 /* Remove comments */ 679 tmp = strchr(kbuf, '#'); 680 681 if (tmp) 682 *tmp = '\0'; 683 684 ret = traceprobe_command(kbuf, createfn); 685 if (ret) 686 goto out; 687 } 688 ret = done; 689 690 out: 691 kfree(kbuf); 692 693 return ret; 694 } 695 696 static int __set_print_fmt(struct trace_probe *tp, char *buf, int len, 697 bool is_return) 698 { 699 int i; 700 int pos = 0; 701 702 const char *fmt, *arg; 703 704 if (!is_return) { 705 fmt = "(%lx)"; 706 arg = "REC->" FIELD_STRING_IP; 707 } else { 708 fmt = "(%lx <- %lx)"; 709 arg = "REC->" FIELD_STRING_FUNC ", REC->" FIELD_STRING_RETIP; 710 } 711 712 /* When len=0, we just calculate the needed length */ 713 #define LEN_OR_ZERO (len ? len - pos : 0) 714 715 pos += snprintf(buf + pos, LEN_OR_ZERO, "\"%s", fmt); 716 717 for (i = 0; i < tp->nr_args; i++) { 718 pos += snprintf(buf + pos, LEN_OR_ZERO, " %s=%s", 719 tp->args[i].name, tp->args[i].type->fmt); 720 } 721 722 pos += snprintf(buf + pos, LEN_OR_ZERO, "\", %s", arg); 723 724 for (i = 0; i < tp->nr_args; i++) { 725 if (strcmp(tp->args[i].type->name, "string") == 0) 726 pos += snprintf(buf + pos, LEN_OR_ZERO, 727 ", __get_str(%s)", 728 tp->args[i].name); 729 else 730 pos += snprintf(buf + pos, LEN_OR_ZERO, ", REC->%s", 731 tp->args[i].name); 732 } 733 734 #undef LEN_OR_ZERO 735 736 /* return the length of print_fmt */ 737 return pos; 738 } 739 740 int set_print_fmt(struct trace_probe *tp, bool is_return) 741 { 742 int len; 743 char *print_fmt; 744 745 /* First: called with 0 length to calculate the needed length */ 746 len = __set_print_fmt(tp, NULL, 0, is_return); 747 print_fmt = kmalloc(len + 1, GFP_KERNEL); 748 if (!print_fmt) 749 return -ENOMEM; 750 751 /* Second: actually write the @print_fmt */ 752 __set_print_fmt(tp, print_fmt, len + 1, is_return); 753 tp->call.print_fmt = print_fmt; 754 755 return 0; 756 } 757