|
@@ -753,186 +753,227 @@ blkiocg_reset_stats(struct cgroup *cgroup, struct cftype *cftype, u64 val)
|
|
|
return 0;
|
|
|
}
|
|
|
|
|
|
-static void blkio_get_key_name(enum blkg_rwstat_type type, const char *dname,
|
|
|
- char *str, int chars_left, bool diskname_only)
|
|
|
-{
|
|
|
- snprintf(str, chars_left, "%s", dname);
|
|
|
- chars_left -= strlen(str);
|
|
|
- if (chars_left <= 0) {
|
|
|
- printk(KERN_WARNING
|
|
|
- "Possibly incorrect cgroup stat display format");
|
|
|
- return;
|
|
|
- }
|
|
|
- if (diskname_only)
|
|
|
- return;
|
|
|
- switch (type) {
|
|
|
- case BLKG_RWSTAT_READ:
|
|
|
- strlcat(str, " Read", chars_left);
|
|
|
- break;
|
|
|
- case BLKG_RWSTAT_WRITE:
|
|
|
- strlcat(str, " Write", chars_left);
|
|
|
- break;
|
|
|
- case BLKG_RWSTAT_SYNC:
|
|
|
- strlcat(str, " Sync", chars_left);
|
|
|
- break;
|
|
|
- case BLKG_RWSTAT_ASYNC:
|
|
|
- strlcat(str, " Async", chars_left);
|
|
|
- break;
|
|
|
- case BLKG_RWSTAT_TOTAL:
|
|
|
- strlcat(str, " Total", chars_left);
|
|
|
- break;
|
|
|
- default:
|
|
|
- strlcat(str, " Invalid", chars_left);
|
|
|
- }
|
|
|
+static const char *blkg_dev_name(struct blkio_group *blkg)
|
|
|
+{
|
|
|
+ /* some drivers (floppy) instantiate a queue w/o disk registered */
|
|
|
+ if (blkg->q->backing_dev_info.dev)
|
|
|
+ return dev_name(blkg->q->backing_dev_info.dev);
|
|
|
+ return NULL;
|
|
|
}
|
|
|
|
|
|
-static uint64_t blkio_read_stat_cpu(struct blkio_group *blkg, int plid,
|
|
|
- enum stat_type_cpu type,
|
|
|
- enum blkg_rwstat_type sub_type)
|
|
|
+/**
|
|
|
+ * blkcg_print_blkgs - helper for printing per-blkg data
|
|
|
+ * @sf: seq_file to print to
|
|
|
+ * @blkcg: blkcg of interest
|
|
|
+ * @prfill: fill function to print out a blkg
|
|
|
+ * @pol: policy in question
|
|
|
+ * @data: data to be passed to @prfill
|
|
|
+ * @show_total: to print out sum of prfill return values or not
|
|
|
+ *
|
|
|
+ * This function invokes @prfill on each blkg of @blkcg if pd for the
|
|
|
+ * policy specified by @pol exists. @prfill is invoked with @sf, the
|
|
|
+ * policy data and @data. If @show_total is %true, the sum of the return
|
|
|
+ * values from @prfill is printed with "Total" label at the end.
|
|
|
+ *
|
|
|
+ * This is to be used to construct print functions for
|
|
|
+ * cftype->read_seq_string method.
|
|
|
+ */
|
|
|
+static void blkcg_print_blkgs(struct seq_file *sf, struct blkio_cgroup *blkcg,
|
|
|
+ u64 (*prfill)(struct seq_file *,
|
|
|
+ struct blkg_policy_data *, int),
|
|
|
+ int pol, int data, bool show_total)
|
|
|
{
|
|
|
- struct blkg_policy_data *pd = blkg->pd[plid];
|
|
|
- u64 val = 0;
|
|
|
- int cpu;
|
|
|
+ struct blkio_group *blkg;
|
|
|
+ struct hlist_node *n;
|
|
|
+ u64 total = 0;
|
|
|
|
|
|
- if (pd->stats_cpu == NULL)
|
|
|
- return val;
|
|
|
+ spin_lock_irq(&blkcg->lock);
|
|
|
+ hlist_for_each_entry(blkg, n, &blkcg->blkg_list, blkcg_node)
|
|
|
+ if (blkg->pd[pol])
|
|
|
+ total += prfill(sf, blkg->pd[pol], data);
|
|
|
+ spin_unlock_irq(&blkcg->lock);
|
|
|
+
|
|
|
+ if (show_total)
|
|
|
+ seq_printf(sf, "Total %llu\n", (unsigned long long)total);
|
|
|
+}
|
|
|
+
|
|
|
+/**
|
|
|
+ * __blkg_prfill_u64 - prfill helper for a single u64 value
|
|
|
+ * @sf: seq_file to print to
|
|
|
+ * @pd: policy data of interest
|
|
|
+ * @v: value to print
|
|
|
+ *
|
|
|
+ * Print @v to @sf for the device assocaited with @pd.
|
|
|
+ */
|
|
|
+static u64 __blkg_prfill_u64(struct seq_file *sf, struct blkg_policy_data *pd,
|
|
|
+ u64 v)
|
|
|
+{
|
|
|
+ const char *dname = blkg_dev_name(pd->blkg);
|
|
|
+
|
|
|
+ if (!dname)
|
|
|
+ return 0;
|
|
|
+
|
|
|
+ seq_printf(sf, "%s %llu\n", dname, (unsigned long long)v);
|
|
|
+ return v;
|
|
|
+}
|
|
|
+
|
|
|
+/**
|
|
|
+ * __blkg_prfill_rwstat - prfill helper for a blkg_rwstat
|
|
|
+ * @sf: seq_file to print to
|
|
|
+ * @pd: policy data of interest
|
|
|
+ * @rwstat: rwstat to print
|
|
|
+ *
|
|
|
+ * Print @rwstat to @sf for the device assocaited with @pd.
|
|
|
+ */
|
|
|
+static u64 __blkg_prfill_rwstat(struct seq_file *sf,
|
|
|
+ struct blkg_policy_data *pd,
|
|
|
+ const struct blkg_rwstat *rwstat)
|
|
|
+{
|
|
|
+ static const char *rwstr[] = {
|
|
|
+ [BLKG_RWSTAT_READ] = "Read",
|
|
|
+ [BLKG_RWSTAT_WRITE] = "Write",
|
|
|
+ [BLKG_RWSTAT_SYNC] = "Sync",
|
|
|
+ [BLKG_RWSTAT_ASYNC] = "Async",
|
|
|
+ };
|
|
|
+ const char *dname = blkg_dev_name(pd->blkg);
|
|
|
+ u64 v;
|
|
|
+ int i;
|
|
|
+
|
|
|
+ if (!dname)
|
|
|
+ return 0;
|
|
|
+
|
|
|
+ for (i = 0; i < BLKG_RWSTAT_NR; i++)
|
|
|
+ seq_printf(sf, "%s %s %llu\n", dname, rwstr[i],
|
|
|
+ (unsigned long long)rwstat->cnt[i]);
|
|
|
+
|
|
|
+ v = rwstat->cnt[BLKG_RWSTAT_READ] + rwstat->cnt[BLKG_RWSTAT_WRITE];
|
|
|
+ seq_printf(sf, "%s Total %llu\n", dname, (unsigned long long)v);
|
|
|
+ return v;
|
|
|
+}
|
|
|
+
|
|
|
+static u64 blkg_prfill_stat(struct seq_file *sf, struct blkg_policy_data *pd,
|
|
|
+ int off)
|
|
|
+{
|
|
|
+ return __blkg_prfill_u64(sf, pd,
|
|
|
+ blkg_stat_read((void *)&pd->stats + off));
|
|
|
+}
|
|
|
+
|
|
|
+static u64 blkg_prfill_rwstat(struct seq_file *sf, struct blkg_policy_data *pd,
|
|
|
+ int off)
|
|
|
+{
|
|
|
+ struct blkg_rwstat rwstat = blkg_rwstat_read((void *)&pd->stats + off);
|
|
|
+
|
|
|
+ return __blkg_prfill_rwstat(sf, pd, &rwstat);
|
|
|
+}
|
|
|
+
|
|
|
+/* print blkg_stat specified by BLKCG_STAT_PRIV() */
|
|
|
+static int blkcg_print_stat(struct cgroup *cgrp, struct cftype *cft,
|
|
|
+ struct seq_file *sf)
|
|
|
+{
|
|
|
+ struct blkio_cgroup *blkcg = cgroup_to_blkio_cgroup(cgrp);
|
|
|
+
|
|
|
+ blkcg_print_blkgs(sf, blkcg, blkg_prfill_stat,
|
|
|
+ BLKCG_STAT_POL(cft->private),
|
|
|
+ BLKCG_STAT_OFF(cft->private), false);
|
|
|
+ return 0;
|
|
|
+}
|
|
|
+
|
|
|
+/* print blkg_rwstat specified by BLKCG_STAT_PRIV() */
|
|
|
+static int blkcg_print_rwstat(struct cgroup *cgrp, struct cftype *cft,
|
|
|
+ struct seq_file *sf)
|
|
|
+{
|
|
|
+ struct blkio_cgroup *blkcg = cgroup_to_blkio_cgroup(cgrp);
|
|
|
+
|
|
|
+ blkcg_print_blkgs(sf, blkcg, blkg_prfill_rwstat,
|
|
|
+ BLKCG_STAT_POL(cft->private),
|
|
|
+ BLKCG_STAT_OFF(cft->private), true);
|
|
|
+ return 0;
|
|
|
+}
|
|
|
+
|
|
|
+static u64 blkg_prfill_cpu_stat(struct seq_file *sf,
|
|
|
+ struct blkg_policy_data *pd, int off)
|
|
|
+{
|
|
|
+ u64 v = 0;
|
|
|
+ int cpu;
|
|
|
|
|
|
for_each_possible_cpu(cpu) {
|
|
|
- struct blkio_group_stats_cpu *stats_cpu =
|
|
|
+ struct blkio_group_stats_cpu *sc =
|
|
|
per_cpu_ptr(pd->stats_cpu, cpu);
|
|
|
- struct blkg_rwstat rws;
|
|
|
|
|
|
- switch (type) {
|
|
|
- case BLKIO_STAT_CPU_SECTORS:
|
|
|
- val += blkg_stat_read(&stats_cpu->sectors);
|
|
|
- break;
|
|
|
- case BLKIO_STAT_CPU_SERVICE_BYTES:
|
|
|
- rws = blkg_rwstat_read(&stats_cpu->service_bytes);
|
|
|
- val += rws.cnt[sub_type];
|
|
|
- break;
|
|
|
- case BLKIO_STAT_CPU_SERVICED:
|
|
|
- rws = blkg_rwstat_read(&stats_cpu->serviced);
|
|
|
- val += rws.cnt[sub_type];
|
|
|
- break;
|
|
|
- }
|
|
|
+ v += blkg_stat_read((void *)sc + off);
|
|
|
}
|
|
|
|
|
|
- return val;
|
|
|
+ return __blkg_prfill_u64(sf, pd, v);
|
|
|
}
|
|
|
|
|
|
-static uint64_t blkio_get_stat_cpu(struct blkio_group *blkg, int plid,
|
|
|
- struct cgroup_map_cb *cb, const char *dname,
|
|
|
- enum stat_type_cpu type)
|
|
|
+static u64 blkg_prfill_cpu_rwstat(struct seq_file *sf,
|
|
|
+ struct blkg_policy_data *pd, int off)
|
|
|
{
|
|
|
- uint64_t disk_total, val;
|
|
|
- char key_str[MAX_KEY_LEN];
|
|
|
- enum blkg_rwstat_type sub_type;
|
|
|
+ struct blkg_rwstat rwstat = { }, tmp;
|
|
|
+ int i, cpu;
|
|
|
|
|
|
- if (type == BLKIO_STAT_CPU_SECTORS) {
|
|
|
- val = blkio_read_stat_cpu(blkg, plid, type, 0);
|
|
|
- blkio_get_key_name(0, dname, key_str, MAX_KEY_LEN, true);
|
|
|
- cb->fill(cb, key_str, val);
|
|
|
- return val;
|
|
|
- }
|
|
|
+ for_each_possible_cpu(cpu) {
|
|
|
+ struct blkio_group_stats_cpu *sc =
|
|
|
+ per_cpu_ptr(pd->stats_cpu, cpu);
|
|
|
|
|
|
- for (sub_type = BLKG_RWSTAT_READ; sub_type < BLKG_RWSTAT_NR;
|
|
|
- sub_type++) {
|
|
|
- blkio_get_key_name(sub_type, dname, key_str, MAX_KEY_LEN,
|
|
|
- false);
|
|
|
- val = blkio_read_stat_cpu(blkg, plid, type, sub_type);
|
|
|
- cb->fill(cb, key_str, val);
|
|
|
+ tmp = blkg_rwstat_read((void *)sc + off);
|
|
|
+ for (i = 0; i < BLKG_RWSTAT_NR; i++)
|
|
|
+ rwstat.cnt[i] += tmp.cnt[i];
|
|
|
}
|
|
|
|
|
|
- disk_total = blkio_read_stat_cpu(blkg, plid, type, BLKG_RWSTAT_READ) +
|
|
|
- blkio_read_stat_cpu(blkg, plid, type, BLKG_RWSTAT_WRITE);
|
|
|
-
|
|
|
- blkio_get_key_name(BLKG_RWSTAT_TOTAL, dname, key_str, MAX_KEY_LEN,
|
|
|
- false);
|
|
|
- cb->fill(cb, key_str, disk_total);
|
|
|
- return disk_total;
|
|
|
+ return __blkg_prfill_rwstat(sf, pd, &rwstat);
|
|
|
}
|
|
|
|
|
|
-static uint64_t blkio_get_stat(struct blkio_group *blkg, int plid,
|
|
|
- struct cgroup_map_cb *cb, const char *dname,
|
|
|
- enum stat_type type)
|
|
|
+/* print per-cpu blkg_stat specified by BLKCG_STAT_PRIV() */
|
|
|
+static int blkcg_print_cpu_stat(struct cgroup *cgrp, struct cftype *cft,
|
|
|
+ struct seq_file *sf)
|
|
|
{
|
|
|
- struct blkio_group_stats *stats = &blkg->pd[plid]->stats;
|
|
|
- uint64_t v = 0, disk_total = 0;
|
|
|
- char key_str[MAX_KEY_LEN];
|
|
|
- struct blkg_rwstat rws = { };
|
|
|
- int st;
|
|
|
+ struct blkio_cgroup *blkcg = cgroup_to_blkio_cgroup(cgrp);
|
|
|
|
|
|
- if (type >= BLKIO_STAT_ARR_NR) {
|
|
|
- switch (type) {
|
|
|
- case BLKIO_STAT_TIME:
|
|
|
- v = blkg_stat_read(&stats->time);
|
|
|
- break;
|
|
|
-#ifdef CONFIG_DEBUG_BLK_CGROUP
|
|
|
- case BLKIO_STAT_UNACCOUNTED_TIME:
|
|
|
- v = blkg_stat_read(&stats->unaccounted_time);
|
|
|
- break;
|
|
|
- case BLKIO_STAT_AVG_QUEUE_SIZE: {
|
|
|
- uint64_t samples;
|
|
|
+ blkcg_print_blkgs(sf, blkcg, blkg_prfill_cpu_stat,
|
|
|
+ BLKCG_STAT_POL(cft->private),
|
|
|
+ BLKCG_STAT_OFF(cft->private), false);
|
|
|
+ return 0;
|
|
|
+}
|
|
|
|
|
|
- samples = blkg_stat_read(&stats->avg_queue_size_samples);
|
|
|
- if (samples) {
|
|
|
- v = blkg_stat_read(&stats->avg_queue_size_sum);
|
|
|
- do_div(v, samples);
|
|
|
- }
|
|
|
- break;
|
|
|
- }
|
|
|
- case BLKIO_STAT_IDLE_TIME:
|
|
|
- v = blkg_stat_read(&stats->idle_time);
|
|
|
- break;
|
|
|
- case BLKIO_STAT_EMPTY_TIME:
|
|
|
- v = blkg_stat_read(&stats->empty_time);
|
|
|
- break;
|
|
|
- case BLKIO_STAT_DEQUEUE:
|
|
|
- v = blkg_stat_read(&stats->dequeue);
|
|
|
- break;
|
|
|
- case BLKIO_STAT_GROUP_WAIT_TIME:
|
|
|
- v = blkg_stat_read(&stats->group_wait_time);
|
|
|
- break;
|
|
|
-#endif
|
|
|
- default:
|
|
|
- WARN_ON_ONCE(1);
|
|
|
- }
|
|
|
+/* print per-cpu blkg_rwstat specified by BLKCG_STAT_PRIV() */
|
|
|
+static int blkcg_print_cpu_rwstat(struct cgroup *cgrp, struct cftype *cft,
|
|
|
+ struct seq_file *sf)
|
|
|
+{
|
|
|
+ struct blkio_cgroup *blkcg = cgroup_to_blkio_cgroup(cgrp);
|
|
|
|
|
|
- blkio_get_key_name(0, dname, key_str, MAX_KEY_LEN, true);
|
|
|
- cb->fill(cb, key_str, v);
|
|
|
- return v;
|
|
|
- }
|
|
|
+ blkcg_print_blkgs(sf, blkcg, blkg_prfill_cpu_rwstat,
|
|
|
+ BLKCG_STAT_POL(cft->private),
|
|
|
+ BLKCG_STAT_OFF(cft->private), true);
|
|
|
+ return 0;
|
|
|
+}
|
|
|
|
|
|
- switch (type) {
|
|
|
- case BLKIO_STAT_MERGED:
|
|
|
- rws = blkg_rwstat_read(&stats->merged);
|
|
|
- break;
|
|
|
- case BLKIO_STAT_SERVICE_TIME:
|
|
|
- rws = blkg_rwstat_read(&stats->service_time);
|
|
|
- break;
|
|
|
- case BLKIO_STAT_WAIT_TIME:
|
|
|
- rws = blkg_rwstat_read(&stats->wait_time);
|
|
|
- break;
|
|
|
- case BLKIO_STAT_QUEUED:
|
|
|
- rws = blkg_rwstat_read(&stats->queued);
|
|
|
- break;
|
|
|
- default:
|
|
|
- WARN_ON_ONCE(true);
|
|
|
- break;
|
|
|
- }
|
|
|
+#ifdef CONFIG_DEBUG_BLK_CGROUP
|
|
|
+static u64 blkg_prfill_avg_queue_size(struct seq_file *sf,
|
|
|
+ struct blkg_policy_data *pd, int off)
|
|
|
+{
|
|
|
+ u64 samples = blkg_stat_read(&pd->stats.avg_queue_size_samples);
|
|
|
+ u64 v = 0;
|
|
|
|
|
|
- for (st = BLKG_RWSTAT_READ; st < BLKG_RWSTAT_NR; st++) {
|
|
|
- blkio_get_key_name(st, dname, key_str, MAX_KEY_LEN, false);
|
|
|
- cb->fill(cb, key_str, rws.cnt[st]);
|
|
|
- if (st == BLKG_RWSTAT_READ || st == BLKG_RWSTAT_WRITE)
|
|
|
- disk_total += rws.cnt[st];
|
|
|
+ if (samples) {
|
|
|
+ v = blkg_stat_read(&pd->stats.avg_queue_size_sum);
|
|
|
+ do_div(v, samples);
|
|
|
}
|
|
|
+ __blkg_prfill_u64(sf, pd, v);
|
|
|
+ return 0;
|
|
|
+}
|
|
|
+
|
|
|
+/* print avg_queue_size */
|
|
|
+static int blkcg_print_avg_queue_size(struct cgroup *cgrp, struct cftype *cft,
|
|
|
+ struct seq_file *sf)
|
|
|
+{
|
|
|
+ struct blkio_cgroup *blkcg = cgroup_to_blkio_cgroup(cgrp);
|
|
|
|
|
|
- blkio_get_key_name(BLKG_RWSTAT_TOTAL, dname, key_str, MAX_KEY_LEN,
|
|
|
- false);
|
|
|
- cb->fill(cb, key_str, disk_total);
|
|
|
- return disk_total;
|
|
|
+ blkcg_print_blkgs(sf, blkcg, blkg_prfill_avg_queue_size,
|
|
|
+ BLKIO_POLICY_PROP, 0, false);
|
|
|
+ return 0;
|
|
|
}
|
|
|
+#endif /* CONFIG_DEBUG_BLK_CGROUP */
|
|
|
|
|
|
static int blkio_policy_parse_and_set(char *buf, enum blkio_policy_id plid,
|
|
|
int fileid, struct blkio_cgroup *blkcg)
|
|
@@ -1074,14 +1115,6 @@ static int blkiocg_file_write(struct cgroup *cgrp, struct cftype *cft,
|
|
|
return ret;
|
|
|
}
|
|
|
|
|
|
-static const char *blkg_dev_name(struct blkio_group *blkg)
|
|
|
-{
|
|
|
- /* some drivers (floppy) instantiate a queue w/o disk registered */
|
|
|
- if (blkg->q->backing_dev_info.dev)
|
|
|
- return dev_name(blkg->q->backing_dev_info.dev);
|
|
|
- return NULL;
|
|
|
-}
|
|
|
-
|
|
|
static void blkio_print_group_conf(struct cftype *cft, struct blkio_group *blkg,
|
|
|
struct seq_file *m)
|
|
|
{
|
|
@@ -1174,116 +1207,6 @@ static int blkiocg_file_read(struct cgroup *cgrp, struct cftype *cft,
|
|
|
return 0;
|
|
|
}
|
|
|
|
|
|
-static int blkio_read_blkg_stats(struct blkio_cgroup *blkcg,
|
|
|
- struct cftype *cft, struct cgroup_map_cb *cb,
|
|
|
- enum stat_type type, bool show_total, bool pcpu)
|
|
|
-{
|
|
|
- struct blkio_group *blkg;
|
|
|
- struct hlist_node *n;
|
|
|
- uint64_t cgroup_total = 0;
|
|
|
-
|
|
|
- spin_lock_irq(&blkcg->lock);
|
|
|
-
|
|
|
- hlist_for_each_entry(blkg, n, &blkcg->blkg_list, blkcg_node) {
|
|
|
- const char *dname = blkg_dev_name(blkg);
|
|
|
- int plid = BLKIOFILE_POLICY(cft->private);
|
|
|
-
|
|
|
- if (!dname)
|
|
|
- continue;
|
|
|
- if (pcpu)
|
|
|
- cgroup_total += blkio_get_stat_cpu(blkg, plid,
|
|
|
- cb, dname, type);
|
|
|
- else
|
|
|
- cgroup_total += blkio_get_stat(blkg, plid,
|
|
|
- cb, dname, type);
|
|
|
- }
|
|
|
- if (show_total)
|
|
|
- cb->fill(cb, "Total", cgroup_total);
|
|
|
-
|
|
|
- spin_unlock_irq(&blkcg->lock);
|
|
|
- return 0;
|
|
|
-}
|
|
|
-
|
|
|
-/* All map kind of cgroup file get serviced by this function */
|
|
|
-static int blkiocg_file_read_map(struct cgroup *cgrp, struct cftype *cft,
|
|
|
- struct cgroup_map_cb *cb)
|
|
|
-{
|
|
|
- struct blkio_cgroup *blkcg;
|
|
|
- enum blkio_policy_id plid = BLKIOFILE_POLICY(cft->private);
|
|
|
- int name = BLKIOFILE_ATTR(cft->private);
|
|
|
-
|
|
|
- blkcg = cgroup_to_blkio_cgroup(cgrp);
|
|
|
-
|
|
|
- switch(plid) {
|
|
|
- case BLKIO_POLICY_PROP:
|
|
|
- switch(name) {
|
|
|
- case BLKIO_PROP_time:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_TIME, 0, 0);
|
|
|
- case BLKIO_PROP_sectors:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_CPU_SECTORS, 0, 1);
|
|
|
- case BLKIO_PROP_io_service_bytes:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_CPU_SERVICE_BYTES, 1, 1);
|
|
|
- case BLKIO_PROP_io_serviced:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_CPU_SERVICED, 1, 1);
|
|
|
- case BLKIO_PROP_io_service_time:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_SERVICE_TIME, 1, 0);
|
|
|
- case BLKIO_PROP_io_wait_time:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_WAIT_TIME, 1, 0);
|
|
|
- case BLKIO_PROP_io_merged:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_MERGED, 1, 0);
|
|
|
- case BLKIO_PROP_io_queued:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_QUEUED, 1, 0);
|
|
|
-#ifdef CONFIG_DEBUG_BLK_CGROUP
|
|
|
- case BLKIO_PROP_unaccounted_time:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_UNACCOUNTED_TIME, 0, 0);
|
|
|
- case BLKIO_PROP_dequeue:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_DEQUEUE, 0, 0);
|
|
|
- case BLKIO_PROP_avg_queue_size:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_AVG_QUEUE_SIZE, 0, 0);
|
|
|
- case BLKIO_PROP_group_wait_time:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_GROUP_WAIT_TIME, 0, 0);
|
|
|
- case BLKIO_PROP_idle_time:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_IDLE_TIME, 0, 0);
|
|
|
- case BLKIO_PROP_empty_time:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_EMPTY_TIME, 0, 0);
|
|
|
-#endif
|
|
|
- default:
|
|
|
- BUG();
|
|
|
- }
|
|
|
- break;
|
|
|
- case BLKIO_POLICY_THROTL:
|
|
|
- switch(name){
|
|
|
- case BLKIO_THROTL_io_service_bytes:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_CPU_SERVICE_BYTES, 1, 1);
|
|
|
- case BLKIO_THROTL_io_serviced:
|
|
|
- return blkio_read_blkg_stats(blkcg, cft, cb,
|
|
|
- BLKIO_STAT_CPU_SERVICED, 1, 1);
|
|
|
- default:
|
|
|
- BUG();
|
|
|
- }
|
|
|
- break;
|
|
|
- default:
|
|
|
- BUG();
|
|
|
- }
|
|
|
-
|
|
|
- return 0;
|
|
|
-}
|
|
|
-
|
|
|
static int blkio_weight_write(struct blkio_cgroup *blkcg, int plid, u64 val)
|
|
|
{
|
|
|
struct blkio_group *blkg;
|
|
@@ -1369,51 +1292,51 @@ struct cftype blkio_files[] = {
|
|
|
},
|
|
|
{
|
|
|
.name = "time",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_time),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_PROP,
|
|
|
+ offsetof(struct blkio_group_stats, time)),
|
|
|
+ .read_seq_string = blkcg_print_stat,
|
|
|
},
|
|
|
{
|
|
|
.name = "sectors",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_sectors),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_PROP,
|
|
|
+ offsetof(struct blkio_group_stats_cpu, sectors)),
|
|
|
+ .read_seq_string = blkcg_print_cpu_stat,
|
|
|
},
|
|
|
{
|
|
|
.name = "io_service_bytes",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_io_service_bytes),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_PROP,
|
|
|
+ offsetof(struct blkio_group_stats_cpu, service_bytes)),
|
|
|
+ .read_seq_string = blkcg_print_cpu_rwstat,
|
|
|
},
|
|
|
{
|
|
|
.name = "io_serviced",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_io_serviced),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_PROP,
|
|
|
+ offsetof(struct blkio_group_stats_cpu, serviced)),
|
|
|
+ .read_seq_string = blkcg_print_cpu_rwstat,
|
|
|
},
|
|
|
{
|
|
|
.name = "io_service_time",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_io_service_time),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_PROP,
|
|
|
+ offsetof(struct blkio_group_stats, service_time)),
|
|
|
+ .read_seq_string = blkcg_print_rwstat,
|
|
|
},
|
|
|
{
|
|
|
.name = "io_wait_time",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_io_wait_time),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_PROP,
|
|
|
+ offsetof(struct blkio_group_stats, wait_time)),
|
|
|
+ .read_seq_string = blkcg_print_rwstat,
|
|
|
},
|
|
|
{
|
|
|
.name = "io_merged",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_io_merged),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_PROP,
|
|
|
+ offsetof(struct blkio_group_stats, merged)),
|
|
|
+ .read_seq_string = blkcg_print_rwstat,
|
|
|
},
|
|
|
{
|
|
|
.name = "io_queued",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_io_queued),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_PROP,
|
|
|
+ offsetof(struct blkio_group_stats, queued)),
|
|
|
+ .read_seq_string = blkcg_print_rwstat,
|
|
|
},
|
|
|
{
|
|
|
.name = "reset_stats",
|
|
@@ -1457,54 +1380,52 @@ struct cftype blkio_files[] = {
|
|
|
},
|
|
|
{
|
|
|
.name = "throttle.io_service_bytes",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_THROTL,
|
|
|
- BLKIO_THROTL_io_service_bytes),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_THROTL,
|
|
|
+ offsetof(struct blkio_group_stats_cpu, service_bytes)),
|
|
|
+ .read_seq_string = blkcg_print_cpu_rwstat,
|
|
|
},
|
|
|
{
|
|
|
.name = "throttle.io_serviced",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_THROTL,
|
|
|
- BLKIO_THROTL_io_serviced),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_THROTL,
|
|
|
+ offsetof(struct blkio_group_stats_cpu, serviced)),
|
|
|
+ .read_seq_string = blkcg_print_cpu_rwstat,
|
|
|
},
|
|
|
#endif /* CONFIG_BLK_DEV_THROTTLING */
|
|
|
|
|
|
#ifdef CONFIG_DEBUG_BLK_CGROUP
|
|
|
{
|
|
|
.name = "avg_queue_size",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_avg_queue_size),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .read_seq_string = blkcg_print_avg_queue_size,
|
|
|
},
|
|
|
{
|
|
|
.name = "group_wait_time",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_group_wait_time),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_PROP,
|
|
|
+ offsetof(struct blkio_group_stats, group_wait_time)),
|
|
|
+ .read_seq_string = blkcg_print_stat,
|
|
|
},
|
|
|
{
|
|
|
.name = "idle_time",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_idle_time),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_PROP,
|
|
|
+ offsetof(struct blkio_group_stats, idle_time)),
|
|
|
+ .read_seq_string = blkcg_print_stat,
|
|
|
},
|
|
|
{
|
|
|
.name = "empty_time",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_empty_time),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_PROP,
|
|
|
+ offsetof(struct blkio_group_stats, empty_time)),
|
|
|
+ .read_seq_string = blkcg_print_stat,
|
|
|
},
|
|
|
{
|
|
|
.name = "dequeue",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_dequeue),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_PROP,
|
|
|
+ offsetof(struct blkio_group_stats, dequeue)),
|
|
|
+ .read_seq_string = blkcg_print_stat,
|
|
|
},
|
|
|
{
|
|
|
.name = "unaccounted_time",
|
|
|
- .private = BLKIOFILE_PRIVATE(BLKIO_POLICY_PROP,
|
|
|
- BLKIO_PROP_unaccounted_time),
|
|
|
- .read_map = blkiocg_file_read_map,
|
|
|
+ .private = BLKCG_STAT_PRIV(BLKIO_POLICY_PROP,
|
|
|
+ offsetof(struct blkio_group_stats, unaccounted_time)),
|
|
|
+ .read_seq_string = blkcg_print_stat,
|
|
|
},
|
|
|
#endif
|
|
|
{ } /* terminate */
|