env.c 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128
  1. // SPDX-License-Identifier: GPL-2.0
  2. #include "cpumap.h"
  3. #include "env.h"
  4. #include "util.h"
  5. #include <errno.h>
  6. #include <sys/utsname.h>
  7. struct perf_env perf_env;
  8. void perf_env__exit(struct perf_env *env)
  9. {
  10. int i;
  11. zfree(&env->hostname);
  12. zfree(&env->os_release);
  13. zfree(&env->version);
  14. zfree(&env->arch);
  15. zfree(&env->cpu_desc);
  16. zfree(&env->cpuid);
  17. zfree(&env->cmdline);
  18. zfree(&env->cmdline_argv);
  19. zfree(&env->sibling_cores);
  20. zfree(&env->sibling_threads);
  21. zfree(&env->pmu_mappings);
  22. zfree(&env->cpu);
  23. for (i = 0; i < env->nr_numa_nodes; i++)
  24. cpu_map__put(env->numa_nodes[i].map);
  25. zfree(&env->numa_nodes);
  26. for (i = 0; i < env->caches_cnt; i++)
  27. cpu_cache_level__free(&env->caches[i]);
  28. zfree(&env->caches);
  29. }
  30. int perf_env__set_cmdline(struct perf_env *env, int argc, const char *argv[])
  31. {
  32. int i;
  33. /* do not include NULL termination */
  34. env->cmdline_argv = calloc(argc, sizeof(char *));
  35. if (env->cmdline_argv == NULL)
  36. goto out_enomem;
  37. /*
  38. * Must copy argv contents because it gets moved around during option
  39. * parsing:
  40. */
  41. for (i = 0; i < argc ; i++) {
  42. env->cmdline_argv[i] = argv[i];
  43. if (env->cmdline_argv[i] == NULL)
  44. goto out_free;
  45. }
  46. env->nr_cmdline = argc;
  47. return 0;
  48. out_free:
  49. zfree(&env->cmdline_argv);
  50. out_enomem:
  51. return -ENOMEM;
  52. }
  53. int perf_env__read_cpu_topology_map(struct perf_env *env)
  54. {
  55. int cpu, nr_cpus;
  56. if (env->cpu != NULL)
  57. return 0;
  58. if (env->nr_cpus_avail == 0)
  59. env->nr_cpus_avail = cpu__max_present_cpu();
  60. nr_cpus = env->nr_cpus_avail;
  61. if (nr_cpus == -1)
  62. return -EINVAL;
  63. env->cpu = calloc(nr_cpus, sizeof(env->cpu[0]));
  64. if (env->cpu == NULL)
  65. return -ENOMEM;
  66. for (cpu = 0; cpu < nr_cpus; ++cpu) {
  67. env->cpu[cpu].core_id = cpu_map__get_core_id(cpu);
  68. env->cpu[cpu].socket_id = cpu_map__get_socket_id(cpu);
  69. }
  70. env->nr_cpus_avail = nr_cpus;
  71. return 0;
  72. }
  73. static int perf_env__read_arch(struct perf_env *env)
  74. {
  75. struct utsname uts;
  76. if (env->arch)
  77. return 0;
  78. if (!uname(&uts))
  79. env->arch = strdup(uts.machine);
  80. return env->arch ? 0 : -ENOMEM;
  81. }
  82. static int perf_env__read_nr_cpus_avail(struct perf_env *env)
  83. {
  84. if (env->nr_cpus_avail == 0)
  85. env->nr_cpus_avail = cpu__max_present_cpu();
  86. return env->nr_cpus_avail ? 0 : -ENOENT;
  87. }
  88. const char *perf_env__raw_arch(struct perf_env *env)
  89. {
  90. return env && !perf_env__read_arch(env) ? env->arch : "unknown";
  91. }
  92. int perf_env__nr_cpus_avail(struct perf_env *env)
  93. {
  94. return env && !perf_env__read_nr_cpus_avail(env) ? env->nr_cpus_avail : 0;
  95. }
  96. void cpu_cache_level__free(struct cpu_cache_level *cache)
  97. {
  98. free(cache->type);
  99. free(cache->map);
  100. free(cache->size);
  101. }