linux/include/linux/part_stat.h
<<
>>
Prefs
   1/* SPDX-License-Identifier: GPL-2.0 */
   2#ifndef _LINUX_PART_STAT_H
   3#define _LINUX_PART_STAT_H
   4
   5#include <linux/genhd.h>
   6#include <asm/local.h>
   7
   8struct disk_stats {
   9        u64 nsecs[NR_STAT_GROUPS];
  10        unsigned long sectors[NR_STAT_GROUPS];
  11        unsigned long ios[NR_STAT_GROUPS];
  12        unsigned long merges[NR_STAT_GROUPS];
  13        unsigned long io_ticks;
  14        local_t in_flight[2];
  15};
  16
  17/*
  18 * Macros to operate on percpu disk statistics:
  19 *
  20 * {disk|part|all}_stat_{add|sub|inc|dec}() modify the stat counters and should
  21 * be called between disk_stat_lock() and disk_stat_unlock().
  22 *
  23 * part_stat_read() can be called at any time.
  24 */
  25#define part_stat_lock()        preempt_disable()
  26#define part_stat_unlock()      preempt_enable()
  27
  28#define part_stat_get_cpu(part, field, cpu)                             \
  29        (per_cpu_ptr((part)->bd_stats, (cpu))->field)
  30
  31#define part_stat_get(part, field)                                      \
  32        part_stat_get_cpu(part, field, smp_processor_id())
  33
  34#define part_stat_read(part, field)                                     \
  35({                                                                      \
  36        typeof((part)->bd_stats->field) res = 0;                        \
  37        unsigned int _cpu;                                              \
  38        for_each_possible_cpu(_cpu)                                     \
  39                res += per_cpu_ptr((part)->bd_stats, _cpu)->field; \
  40        res;                                                            \
  41})
  42
  43static inline void part_stat_set_all(struct block_device *part, int value)
  44{
  45        int i;
  46
  47        for_each_possible_cpu(i)
  48                memset(per_cpu_ptr(part->bd_stats, i), value,
  49                                sizeof(struct disk_stats));
  50}
  51
  52#define part_stat_read_accum(part, field)                               \
  53        (part_stat_read(part, field[STAT_READ]) +                       \
  54         part_stat_read(part, field[STAT_WRITE]) +                      \
  55         part_stat_read(part, field[STAT_DISCARD]))
  56
  57#define __part_stat_add(part, field, addnd)                             \
  58        __this_cpu_add((part)->bd_stats->field, addnd)
  59
  60#define part_stat_add(part, field, addnd)       do {                    \
  61        __part_stat_add((part), field, addnd);                          \
  62        if ((part)->bd_partno)                                          \
  63                __part_stat_add(bdev_whole(part), field, addnd);        \
  64} while (0)
  65
  66#define part_stat_dec(part, field)                                      \
  67        part_stat_add(part, field, -1)
  68#define part_stat_inc(part, field)                                      \
  69        part_stat_add(part, field, 1)
  70#define part_stat_sub(part, field, subnd)                               \
  71        part_stat_add(part, field, -subnd)
  72
  73#define part_stat_local_dec(part, field)                                \
  74        local_dec(&(part_stat_get(part, field)))
  75#define part_stat_local_inc(part, field)                                \
  76        local_inc(&(part_stat_get(part, field)))
  77#define part_stat_local_read(part, field)                               \
  78        local_read(&(part_stat_get(part, field)))
  79#define part_stat_local_read_cpu(part, field, cpu)                      \
  80        local_read(&(part_stat_get_cpu(part, field, cpu)))
  81
  82#endif /* _LINUX_PART_STAT_H */
  83