hypfs_vm_fs.c 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139
  1. // SPDX-License-Identifier: GPL-2.0
  2. /*
  3. * Hypervisor filesystem for Linux on s390. z/VM implementation.
  4. *
  5. * Copyright IBM Corp. 2006
  6. * Author(s): Michael Holzheu <holzheu@de.ibm.com>
  7. */
  8. #include <linux/types.h>
  9. #include <linux/errno.h>
  10. #include <linux/string.h>
  11. #include <linux/vmalloc.h>
  12. #include <asm/extable.h>
  13. #include <asm/diag.h>
  14. #include <asm/ebcdic.h>
  15. #include <asm/timex.h>
  16. #include "hypfs_vm.h"
  17. #include "hypfs.h"
  18. #define ATTRIBUTE(dir, name, member) \
  19. do { \
  20. void *rc; \
  21. rc = hypfs_create_u64(dir, name, member); \
  22. if (IS_ERR(rc)) \
  23. return PTR_ERR(rc); \
  24. } while (0)
  25. static int hypfs_vm_create_guest(struct dentry *systems_dir,
  26. struct diag2fc_data *data)
  27. {
  28. char guest_name[DIAG2FC_NAME_LEN + 1] = {};
  29. struct dentry *guest_dir, *cpus_dir, *samples_dir, *mem_dir;
  30. int dedicated_flag, capped_value;
  31. capped_value = (data->flags & 0x00000006) >> 1;
  32. dedicated_flag = (data->flags & 0x00000008) >> 3;
  33. /* guest dir */
  34. memcpy(guest_name, data->guest_name, DIAG2FC_NAME_LEN);
  35. EBCASC(guest_name, DIAG2FC_NAME_LEN);
  36. strim(guest_name);
  37. guest_dir = hypfs_mkdir(systems_dir, guest_name);
  38. if (IS_ERR(guest_dir))
  39. return PTR_ERR(guest_dir);
  40. ATTRIBUTE(guest_dir, "onlinetime_us", data->el_time);
  41. /* logical cpu information */
  42. cpus_dir = hypfs_mkdir(guest_dir, "cpus");
  43. if (IS_ERR(cpus_dir))
  44. return PTR_ERR(cpus_dir);
  45. ATTRIBUTE(cpus_dir, "cputime_us", data->used_cpu);
  46. ATTRIBUTE(cpus_dir, "capped", capped_value);
  47. ATTRIBUTE(cpus_dir, "dedicated", dedicated_flag);
  48. ATTRIBUTE(cpus_dir, "count", data->vcpus);
  49. /*
  50. * Note: The "weight_min" attribute got the wrong name.
  51. * The value represents the number of non-stopped (operating)
  52. * CPUS.
  53. */
  54. ATTRIBUTE(cpus_dir, "weight_min", data->ocpus);
  55. ATTRIBUTE(cpus_dir, "weight_max", data->cpu_max);
  56. ATTRIBUTE(cpus_dir, "weight_cur", data->cpu_shares);
  57. /* memory information */
  58. mem_dir = hypfs_mkdir(guest_dir, "mem");
  59. if (IS_ERR(mem_dir))
  60. return PTR_ERR(mem_dir);
  61. ATTRIBUTE(mem_dir, "min_KiB", data->mem_min_kb);
  62. ATTRIBUTE(mem_dir, "max_KiB", data->mem_max_kb);
  63. ATTRIBUTE(mem_dir, "used_KiB", data->mem_used_kb);
  64. ATTRIBUTE(mem_dir, "share_KiB", data->mem_share_kb);
  65. /* samples */
  66. samples_dir = hypfs_mkdir(guest_dir, "samples");
  67. if (IS_ERR(samples_dir))
  68. return PTR_ERR(samples_dir);
  69. ATTRIBUTE(samples_dir, "cpu_using", data->cpu_use_samp);
  70. ATTRIBUTE(samples_dir, "cpu_delay", data->cpu_delay_samp);
  71. ATTRIBUTE(samples_dir, "mem_delay", data->page_wait_samp);
  72. ATTRIBUTE(samples_dir, "idle", data->idle_samp);
  73. ATTRIBUTE(samples_dir, "other", data->other_samp);
  74. ATTRIBUTE(samples_dir, "total", data->total_samp);
  75. return 0;
  76. }
  77. int hypfs_vm_create_files(struct dentry *root)
  78. {
  79. struct dentry *dir, *file;
  80. struct diag2fc_data *data;
  81. unsigned int count = 0;
  82. int rc, i;
  83. data = diag2fc_store(diag2fc_guest_query, &count, 0);
  84. if (IS_ERR(data))
  85. return PTR_ERR(data);
  86. /* Hypervisor Info */
  87. dir = hypfs_mkdir(root, "hyp");
  88. if (IS_ERR(dir)) {
  89. rc = PTR_ERR(dir);
  90. goto failed;
  91. }
  92. file = hypfs_create_str(dir, "type", "z/VM Hypervisor");
  93. if (IS_ERR(file)) {
  94. rc = PTR_ERR(file);
  95. goto failed;
  96. }
  97. /* physical cpus */
  98. dir = hypfs_mkdir(root, "cpus");
  99. if (IS_ERR(dir)) {
  100. rc = PTR_ERR(dir);
  101. goto failed;
  102. }
  103. file = hypfs_create_u64(dir, "count", data->lcpus);
  104. if (IS_ERR(file)) {
  105. rc = PTR_ERR(file);
  106. goto failed;
  107. }
  108. /* guests */
  109. dir = hypfs_mkdir(root, "systems");
  110. if (IS_ERR(dir)) {
  111. rc = PTR_ERR(dir);
  112. goto failed;
  113. }
  114. for (i = 0; i < count; i++) {
  115. rc = hypfs_vm_create_guest(dir, &data[i]);
  116. if (rc)
  117. goto failed;
  118. }
  119. diag2fc_free(data);
  120. return 0;
  121. failed:
  122. diag2fc_free(data);
  123. return rc;
  124. }