Skip to content

Commit 6460516

Browse files
committed
de-prometheus the stats, add more metaclasses
1 parent 1b4e463 commit 6460516

File tree

2 files changed

+82
-46
lines changed

2 files changed

+82
-46
lines changed

include/sys/spa.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -940,7 +940,7 @@ typedef struct spa_stats {
940940
spa_history_kstat_t state; /* pool state */
941941
spa_history_kstat_t guid; /* pool guid */
942942
spa_history_kstat_t iostats;
943-
spa_history_kstat_t fragmentation;
943+
spa_history_kstat_t fragmentation[5];
944944
} spa_stats_t;
945945

946946
typedef enum txg_state {

module/zfs/spa_stats.c

Lines changed: 81 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -304,67 +304,103 @@ spa_txg_history_init(spa_t *spa)
304304
offsetof(spa_txg_history_t, sth_node));
305305
}
306306

307+
typedef struct {
308+
spa_t *spa;
309+
int metaclass;
310+
} freespace_histogram_stat_t;
311+
307312
static void *
308313
spa_frag_addr(kstat_t *ksp, loff_t n)
309314
{
310-
if (n == 0)
311-
return ksp->ks_private;
312-
return NULL;
315+
if (n == 0) {
316+
freespace_histogram_stat_t *stat = ksp->ks_private;
317+
switch (stat->metaclass) {
318+
case 0:
319+
return (spa_normal_class(stat->spa));
320+
case 1:
321+
return (spa_log_class(stat->spa));
322+
case 2:
323+
return (spa_embedded_log_class(stat->spa));
324+
case 3:
325+
return (spa_special_class(stat->spa));
326+
case 4:
327+
return (spa_dedup_class(stat->spa));
328+
}
329+
}
330+
return (NULL);
313331
}
314332

315333
static int
316-
spa_frag_data(char *buf, size_t size, void *data) {
317-
spa_t *spa = (spa_t *)data;
318-
size_t offset = 0;
319-
const char *name = spa_name(spa);
320-
321-
metaslab_class_t *mc = spa_normal_class(spa);
322-
for (int i=0; i<RANGE_TREE_HISTOGRAM_SIZE; i++) {
323-
if (mc->mc_histogram[i] > 0) {
324-
int res = snprintf(buf + offset, size, "zfs_fragmentation_normal{power=\"%d\",pool=\"%s\"} %llu\n", i, name, (u_longlong_t)mc->mc_histogram[i]);
325-
offset += res;
326-
size -= res;
327-
}
328-
}
329-
330-
metaslab_class_t *smc = spa_special_class(spa);
331-
for (int i=0; i<RANGE_TREE_HISTOGRAM_SIZE; i++) {
332-
if (smc->mc_histogram[i] > 0) {
333-
int res = snprintf(buf + offset, size, "zfs_fragmentation_special{power=\"%d\",pool=\"%s\"} %llu\n", i, name, (u_longlong_t)smc->mc_histogram[i]);
334-
offset += res;
335-
size -= res;
336-
}
337-
}
338-
return 0;
334+
spa_frag_data(char *buf, size_t size, void *data)
335+
{
336+
metaslab_class_t *mc = data;
337+
size_t offset = 0;
338+
int res;
339+
// without this, it becomes a data-leak, and un-initialized strings
340+
// can be returned if all buckets are 0
341+
buf[0] = 0;
342+
343+
for (int i = 0; i < RANGE_TREE_HISTOGRAM_SIZE; i++) {
344+
if (mc->mc_histogram[i] > 0) {
345+
res = snprintf(buf + offset, size, "%d %llu\n", i,
346+
(u_longlong_t)mc->mc_histogram[i]);
347+
offset += res;
348+
size -= res;
349+
}
350+
}
351+
352+
return (0);
339353
}
340354

341355
static void
342356
spa_fragmentation_init(spa_t *spa)
343357
{
344-
char *name;
345-
spa_history_kstat_t *shk = &spa->spa_stats.fragmentation;
346-
kstat_t *ksp;
347-
348-
name = kmem_asprintf("zfs/%s", spa_name(spa));
349-
ksp = kstat_create(name, 0, "fragmentation", "misc", KSTAT_TYPE_RAW, 0, KSTAT_FLAG_VIRTUAL);
350-
351-
shk->kstat = ksp;
352-
if (ksp) {
353-
ksp->ks_private = spa;
354-
ksp->ks_flags |= KSTAT_FLAG_NO_HEADERS;
355-
kstat_set_raw_ops(ksp, NULL, spa_frag_data, spa_frag_addr);
356-
kstat_install(ksp);
357-
}
358-
kmem_strfree(name);
358+
char *dirname;
359+
const char *statnames[] = {
360+
"fragmentation_normal",
361+
"fragmentation_log",
362+
"fragmentation_embedded_log",
363+
"fragmentation_special",
364+
"fragmentation_dedup"
365+
};
366+
for (int i = 0; i < 5; i++) {
367+
spa_history_kstat_t *shk = &spa->spa_stats.fragmentation[i];
368+
kstat_t *ksp;
369+
370+
dirname = kmem_asprintf("zfs/%s", spa_name(spa));
371+
ksp = kstat_create(dirname, 0, statnames[i], "misc",
372+
KSTAT_TYPE_RAW, 0, KSTAT_FLAG_VIRTUAL);
373+
kmem_strfree(dirname);
374+
375+
shk->kstat = ksp;
376+
if (ksp) {
377+
freespace_histogram_stat_t *stat = kmem_zalloc(
378+
sizeof (freespace_histogram_stat_t), KM_SLEEP);
379+
stat->spa = spa;
380+
stat->metaclass = i;
381+
ksp->ks_private = stat;
382+
ksp->ks_flags |= KSTAT_FLAG_NO_HEADERS;
383+
kstat_set_raw_ops(ksp, NULL, spa_frag_data,
384+
spa_frag_addr);
385+
kstat_install(ksp);
386+
}
387+
}
359388
}
360389

361390
static void
362391
spa_fragmentation_destroy(spa_t *spa)
363392
{
364-
spa_history_kstat_t *shk = &spa->spa_stats.fragmentation;
365-
kstat_t *ksp = shk->kstat;
366-
if (ksp)
367-
kstat_delete(ksp);
393+
for (int i = 0; i < 5; i++) {
394+
spa_history_kstat_t *shk = &spa->spa_stats.fragmentation[i];
395+
kstat_t *ksp = shk->kstat;
396+
if (ksp) {
397+
if (ksp->ks_private) {
398+
kmem_free(ksp->ks_private,
399+
sizeof (freespace_histogram_stat_t));
400+
}
401+
kstat_delete(ksp);
402+
}
403+
}
368404
}
369405

370406
static void

0 commit comments

Comments
 (0)