parse-regs-options.c 1.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172
  1. // SPDX-License-Identifier: GPL-2.0
  2. #include "perf.h"
  3. #include "util/util.h"
  4. #include "util/debug.h"
  5. #include <subcmd/parse-options.h>
  6. #include "util/parse-regs-options.h"
  7. int
  8. parse_regs(const struct option *opt, const char *str, int unset)
  9. {
  10. uint64_t *mode = (uint64_t *)opt->value;
  11. const struct sample_reg *r;
  12. char *s, *os = NULL, *p;
  13. int ret = -1;
  14. if (unset)
  15. return 0;
  16. /*
  17. * cannot set it twice
  18. */
  19. if (*mode)
  20. return -1;
  21. /* str may be NULL in case no arg is passed to -I */
  22. if (str) {
  23. /* because str is read-only */
  24. s = os = strdup(str);
  25. if (!s)
  26. return -1;
  27. for (;;) {
  28. p = strchr(s, ',');
  29. if (p)
  30. *p = '\0';
  31. if (!strcmp(s, "?")) {
  32. fprintf(stderr, "available registers: ");
  33. for (r = sample_reg_masks; r->name; r++) {
  34. fprintf(stderr, "%s ", r->name);
  35. }
  36. fputc('\n', stderr);
  37. /* just printing available regs */
  38. goto error;
  39. }
  40. for (r = sample_reg_masks; r->name; r++) {
  41. if (!strcasecmp(s, r->name))
  42. break;
  43. }
  44. if (!r->name) {
  45. ui__warning("unknown register %s,"
  46. " check man page\n", s);
  47. goto error;
  48. }
  49. *mode |= r->mask;
  50. if (!p)
  51. break;
  52. s = p + 1;
  53. }
  54. }
  55. ret = 0;
  56. /* default to all possible regs */
  57. if (*mode == 0)
  58. *mode = PERF_REGS_MASK;
  59. error:
  60. free(os);
  61. return ret;
  62. }