summaryrefslogtreecommitdiff
path: root/drivers
diff options
context:
space:
mode:
authorMike Christie <michael.christie@oracle.com>2025-09-17 17:12:54 -0500
committerMartin K. Petersen <martin.petersen@oracle.com>2025-11-02 22:06:11 -0500
commited6b97a79577db9bf9d7b21fd623f24f499e3acc (patch)
tree0b061c38daa56bdf33d1aa1d925f472bdb6ffca9 /drivers
parent95aa2041c654161d1b5c1eca5379d67d91ef1cf2 (diff)
scsi: target: Create and use macro helpers for per-CPU stats
Create some macros to reduce code duplication for when we handle per-CPU stats. Convert the existing LUN and auth cases. Note: This is similar to percpu_counters but they only support s64 since they are also used for non-stat counters where you need to handle/prevent rollover more gracefully. Our use is just for stats where the spec defines u64 use plus we already have some files exporting u64 values so it's not possible to directly use percpu_counters. Signed-off-by: Mike Christie <michael.christie@oracle.com> Reviewed-by: Dmitry Bogdanov <d.bogdanov@yadro.com> Link: https://patch.msgid.link/20250917221338.14813-3-michael.christie@oracle.com Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/target/target_core_stat.c197
1 files changed, 61 insertions, 136 deletions
diff --git a/drivers/target/target_core_stat.c b/drivers/target/target_core_stat.c
index 4fdc307ea38b..e29d43dacaf7 100644
--- a/drivers/target/target_core_stat.c
+++ b/drivers/target/target_core_stat.c
@@ -276,56 +276,39 @@ static ssize_t target_stat_lu_state_bit_show(struct config_item *item,
return snprintf(page, PAGE_SIZE, "exposed\n");
}
-static ssize_t target_stat_lu_num_cmds_show(struct config_item *item,
- char *page)
-{
- struct se_device *dev = to_stat_lu_dev(item);
- struct se_dev_io_stats *stats;
- unsigned int cpu;
- u64 cmds = 0;
-
- for_each_possible_cpu(cpu) {
- stats = per_cpu_ptr(dev->stats, cpu);
- cmds += stats->total_cmds;
- }
-
- /* scsiLuNumCommands */
- return snprintf(page, PAGE_SIZE, "%llu\n", cmds);
-}
-
-static ssize_t target_stat_lu_read_mbytes_show(struct config_item *item,
- char *page)
-{
- struct se_device *dev = to_stat_lu_dev(item);
- struct se_dev_io_stats *stats;
- unsigned int cpu;
- u64 bytes = 0;
-
- for_each_possible_cpu(cpu) {
- stats = per_cpu_ptr(dev->stats, cpu);
- bytes += stats->read_bytes;
- }
-
- /* scsiLuReadMegaBytes */
- return snprintf(page, PAGE_SIZE, "%llu\n", bytes >> 20);
-}
-
-static ssize_t target_stat_lu_write_mbytes_show(struct config_item *item,
- char *page)
-{
- struct se_device *dev = to_stat_lu_dev(item);
- struct se_dev_io_stats *stats;
- unsigned int cpu;
- u64 bytes = 0;
-
- for_each_possible_cpu(cpu) {
- stats = per_cpu_ptr(dev->stats, cpu);
- bytes += stats->write_bytes;
- }
-
- /* scsiLuWrittenMegaBytes */
- return snprintf(page, PAGE_SIZE, "%llu\n", bytes >> 20);
-}
+#define per_cpu_stat_snprintf(stats_struct, prefix, field, shift) \
+static ssize_t \
+per_cpu_stat_##prefix##_snprintf(struct stats_struct __percpu *per_cpu_stats, \
+ char *page) \
+{ \
+ struct stats_struct *stats; \
+ unsigned int cpu; \
+ u64 sum = 0; \
+ \
+ for_each_possible_cpu(cpu) { \
+ stats = per_cpu_ptr(per_cpu_stats, cpu); \
+ sum += stats->field; \
+ } \
+ \
+ return snprintf(page, PAGE_SIZE, "%llu\n", sum >> shift); \
+}
+
+#define lu_show_per_cpu_stat(prefix, field, shift) \
+per_cpu_stat_snprintf(se_dev_io_stats, prefix, field, shift); \
+static ssize_t \
+target_stat_##prefix##_show(struct config_item *item, char *page) \
+{ \
+ struct se_device *dev = to_stat_lu_dev(item); \
+ \
+ return per_cpu_stat_##prefix##_snprintf(dev->stats, page); \
+} \
+
+/* scsiLuNumCommands */
+lu_show_per_cpu_stat(lu_num_cmds, total_cmds, 0);
+/* scsiLuReadMegaBytes */
+lu_show_per_cpu_stat(lu_read_mbytes, read_bytes, 20);
+/* scsiLuWrittenMegaBytes */
+lu_show_per_cpu_stat(lu_write_mbytes, write_bytes, 20);
static ssize_t target_stat_lu_resets_show(struct config_item *item, char *page)
{
@@ -1035,92 +1018,34 @@ static ssize_t target_stat_auth_att_count_show(struct config_item *item,
return ret;
}
-static ssize_t target_stat_auth_num_cmds_show(struct config_item *item,
- char *page)
-{
- struct se_lun_acl *lacl = auth_to_lacl(item);
- struct se_node_acl *nacl = lacl->se_lun_nacl;
- struct se_dev_entry_io_stats *stats;
- struct se_dev_entry *deve;
- unsigned int cpu;
- ssize_t ret;
- u64 cmds = 0;
-
- rcu_read_lock();
- deve = target_nacl_find_deve(nacl, lacl->mapped_lun);
- if (!deve) {
- rcu_read_unlock();
- return -ENODEV;
- }
-
- for_each_possible_cpu(cpu) {
- stats = per_cpu_ptr(deve->stats, cpu);
- cmds += stats->total_cmds;
- }
-
- /* scsiAuthIntrOutCommands */
- ret = snprintf(page, PAGE_SIZE, "%llu\n", cmds);
- rcu_read_unlock();
- return ret;
-}
-
-static ssize_t target_stat_auth_read_mbytes_show(struct config_item *item,
- char *page)
-{
- struct se_lun_acl *lacl = auth_to_lacl(item);
- struct se_node_acl *nacl = lacl->se_lun_nacl;
- struct se_dev_entry_io_stats *stats;
- struct se_dev_entry *deve;
- unsigned int cpu;
- ssize_t ret;
- u64 bytes = 0;
-
- rcu_read_lock();
- deve = target_nacl_find_deve(nacl, lacl->mapped_lun);
- if (!deve) {
- rcu_read_unlock();
- return -ENODEV;
- }
-
- for_each_possible_cpu(cpu) {
- stats = per_cpu_ptr(deve->stats, cpu);
- bytes += stats->read_bytes;
- }
-
- /* scsiAuthIntrReadMegaBytes */
- ret = snprintf(page, PAGE_SIZE, "%llu\n", bytes >> 20);
- rcu_read_unlock();
- return ret;
-}
-
-static ssize_t target_stat_auth_write_mbytes_show(struct config_item *item,
- char *page)
-{
- struct se_lun_acl *lacl = auth_to_lacl(item);
- struct se_node_acl *nacl = lacl->se_lun_nacl;
- struct se_dev_entry_io_stats *stats;
- struct se_dev_entry *deve;
- unsigned int cpu;
- ssize_t ret;
- u64 bytes = 0;
-
- rcu_read_lock();
- deve = target_nacl_find_deve(nacl, lacl->mapped_lun);
- if (!deve) {
- rcu_read_unlock();
- return -ENODEV;
- }
-
- for_each_possible_cpu(cpu) {
- stats = per_cpu_ptr(deve->stats, cpu);
- bytes += stats->write_bytes;
- }
-
- /* scsiAuthIntrWrittenMegaBytes */
- ret = snprintf(page, PAGE_SIZE, "%llu\n", bytes >> 20);
- rcu_read_unlock();
- return ret;
-}
+#define auth_show_per_cpu_stat(prefix, field, shift) \
+per_cpu_stat_snprintf(se_dev_entry_io_stats, prefix, field, shift); \
+static ssize_t \
+target_stat_##prefix##_show(struct config_item *item, char *page) \
+{ \
+ struct se_lun_acl *lacl = auth_to_lacl(item); \
+ struct se_node_acl *nacl = lacl->se_lun_nacl; \
+ struct se_dev_entry *deve; \
+ int ret; \
+ \
+ rcu_read_lock(); \
+ deve = target_nacl_find_deve(nacl, lacl->mapped_lun); \
+ if (!deve) { \
+ rcu_read_unlock(); \
+ return -ENODEV; \
+ } \
+ \
+ ret = per_cpu_stat_##prefix##_snprintf(deve->stats, page); \
+ rcu_read_unlock(); \
+ return ret; \
+}
+
+/* scsiAuthIntrOutCommands */
+auth_show_per_cpu_stat(auth_num_cmds, total_cmds, 0);
+/* scsiAuthIntrReadMegaBytes */
+auth_show_per_cpu_stat(auth_read_mbytes, read_bytes, 20);
+/* scsiAuthIntrWrittenMegaBytes */
+auth_show_per_cpu_stat(auth_write_mbytes, write_bytes, 20);
static ssize_t target_stat_auth_hs_num_cmds_show(struct config_item *item,
char *page)