1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://www.opensolaris.org/os/licensing. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21 /* 22 * Copyright 2006 Sun Microsystems, Inc. All rights reserved. 23 * Copyright 2012 David Hoeppner. All rights reserved. 24 */ 25 26 #ifndef _STAT_KSTAT_H 27 #define _STAT_KSTAT_H 28 29 /* 30 * Structures needed by the kstat reader functions. 31 */ 32 #include <sys/var.h> 33 #include <sys/utsname.h> 34 #include <sys/sysinfo.h> 35 #include <sys/flock.h> 36 #include <sys/dnlc.h> 37 #include <nfs/nfs.h> 38 #include <nfs/nfs_clnt.h> 39 40 #ifdef __sparc 41 #include <vm/hat_sfmmu.h> 42 #include <sys/simmstat.h> 43 #include <sys/sysctrl.h> 44 #include <sys/fhc.h> 45 #endif 46 47 #define KSTAT_DATA_HRTIME (KSTAT_DATA_STRING + 1) 48 49 typedef union ks_value { 50 char c[16]; 51 int32_t i32; 52 uint32_t ui32; 53 struct { 54 union { 55 char *ptr; 56 char __pad[8]; 57 } addr; 58 uint32_t len; 59 } str; 60 61 int64_t i64; 62 uint64_t ui64; 63 } ks_value_t; 64 65 #define SAVE_HRTIME(I, S, N) \ 66 { \ 67 ks_value_t v; \ 68 v.ui64 = S->N; \ 69 nvpair_insert(I, #N, &v, KSTAT_DATA_UINT64); \ 70 } 71 72 #define SAVE_INT32(I, S, N) \ 73 { \ 74 ks_value_t v; \ 75 v.i32 = S->N; \ 76 nvpair_insert(I, #N, &v, KSTAT_DATA_INT32); \ 77 } 78 79 #define SAVE_UINT32(I, S, N) \ 80 { \ 81 ks_value_t v; \ 82 v.ui32 = S->N; \ 83 nvpair_insert(I, #N, &v, KSTAT_DATA_UINT32); \ 84 } 85 86 #define SAVE_INT64(I, S, N) \ 87 { \ 88 ks_value_t v; \ 89 v.i64 = S->N; \ 90 nvpair_insert(I, #N, &v, KSTAT_DATA_INT64); \ 91 } 92 93 #define SAVE_UINT64(I, S, N) \ 94 { \ 95 ks_value_t v; \ 96 v.ui64 = S->N; \ 97 nvpair_insert(I, #N, &v, KSTAT_DATA_UINT64); \ 98 } 99 100 /* 101 * We dont want const "strings" because we free 102 * the instances later. 103 */ 104 #define SAVE_STRING(I, S, N) \ 105 { \ 106 ks_value_t v; \ 107 v.str.addr.ptr = safe_strdup(S->N); \ 108 v.str.len = strlen(S->N); \ 109 nvpair_insert(I, #N, &v, KSTAT_DATA_STRING); \ 110 } 111 112 #define SAVE_HRTIME_X(I, N, V) \ 113 { \ 114 ks_value_t v; \ 115 v.ui64 = V; \ 116 nvpair_insert(I, N, &v, KSTAT_DATA_HRTIME); \ 117 } 118 119 #define SAVE_INT32_X(I, N, V) \ 120 { \ 121 ks_value_t v; \ 122 v.i32 = V; \ 123 nvpair_insert(I, N, &v, KSTAT_DATA_INT32); \ 124 } 125 126 #define SAVE_UINT32_X(I, N, V) \ 127 { \ 128 ks_value_t v; \ 129 v.ui32 = V; \ 130 nvpair_insert(I, N, &v, KSTAT_DATA_UINT32); \ 131 } 132 133 #define SAVE_UINT64_X(I, N, V) \ 134 { \ 135 ks_value_t v; \ 136 v.ui64 = V; \ 137 nvpair_insert(I, N, &v, KSTAT_DATA_UINT64); \ 138 } 139 140 #define SAVE_STRING_X(I, N, V) \ 141 { \ 142 ks_value_t v; \ 143 v.str.addr.ptr = safe_strdup(V); \ 144 v.str.len = strlen(V); \ 145 nvpair_insert(I, N, &v, KSTAT_DATA_STRING); \ 146 } 147 148 #define SAVE_CHAR_X(I, N, V) \ 149 { \ 150 ks_value_t v; \ 151 asprintf(&v.str.addr.ptr, "%c", V); \ 152 v.str.len = 1; \ 153 nvpair_insert(I, N, &v, KSTAT_DATA_STRING); \ 154 } 155 156 #define DFLT_FMT \ 157 "module: %-30.30s instance: %-6d\n" \ 158 "name: %-30.30s class: %-.30s\n" 159 160 #define JSON_FMT \ 161 "{\n\t\"module\": \"%s\",\n" \ 162 "\t\"instance\": %d,\n" \ 163 "\t\"name\": \"%s\",\n" \ 164 "\t\"class\": \"%s\",\n" \ 165 "\t\"type\": %d,\n" 166 167 #define KS_DFMT "\t%-30s " 168 #define KS_JFMT "\t\t\"%s\": " 169 #define KS_PFMT "%s:%d:%s:%s" 170 171 typedef struct ks_instance { 172 list_node_t ks_next; 173 char ks_name[KSTAT_STRLEN]; 174 char ks_module[KSTAT_STRLEN]; 175 char ks_class[KSTAT_STRLEN]; 176 int ks_instance; 177 uchar_t ks_type; 178 hrtime_t ks_snaptime; 179 list_t ks_nvlist; 180 } ks_instance_t; 181 182 typedef struct ks_nvpair { 183 list_node_t nv_next; 184 char name[KSTAT_STRLEN]; 185 uchar_t data_type; 186 ks_value_t value; 187 } ks_nvpair_t; 188 189 typedef struct ks_selector { 190 list_node_t ks_next; 191 char *ks_module; 192 char *ks_instance; 193 char *ks_name; 194 char *ks_statistic; 195 } ks_selector_t; 196 197 static void usage(void); 198 static int compare_instances(ks_instance_t *, ks_instance_t *); 199 static void nvpair_insert(ks_instance_t *, char *, ks_value_t *, uchar_t); 200 static ks_selector_t *new_selector(void); 201 static void ks_instances_read(kstat_ctl_t *); 202 static void ks_value_print(ks_nvpair_t *); 203 static void ks_instance_print(ks_instance_t *, ks_nvpair_t *); 204 static void ks_instances_print(void); 205 static char *ks_safe_strdup(char *); 206 static void ks_sleep_until(hrtime_t *, hrtime_t, int, int *); 207 208 /* Raw kstat readers */ 209 static void save_cpu_stat(kstat_t *, ks_instance_t *); 210 static void save_var(kstat_t *, ks_instance_t *); 211 static void save_ncstats(kstat_t *, ks_instance_t *); 212 static void save_sysinfo(kstat_t *, ks_instance_t *); 213 static void save_vminfo(kstat_t *, ks_instance_t *); 214 static void save_nfs(kstat_t *, ks_instance_t *); 215 #ifdef __sparc 216 static void save_sfmmu_global_stat(kstat_t *, ks_instance_t *); 217 static void save_sfmmu_tsbsize_stat(kstat_t *, ks_instance_t *); 218 static void save_simmstat(kstat_t *, ks_instance_t *); 219 /* Helper function for save_temperature() */ 220 static char *short_array_to_string(short *, int); 221 static void save_temperature(kstat_t *, ks_instance_t *); 222 static void save_temp_over(kstat_t *, ks_instance_t *); 223 static void save_ps_shadow(kstat_t *, ks_instance_t *); 224 static void save_fault_list(kstat_t *, ks_instance_t *); 225 #endif 226 227 /* Named kstat readers */ 228 static void save_named(kstat_t *, ks_instance_t *); 229 static void save_intr(kstat_t *, ks_instance_t *); 230 static void save_io(kstat_t *, ks_instance_t *); 231 static void save_timer(kstat_t *, ks_instance_t *); 232 233 /* Typedef for raw kstat reader functions */ 234 typedef void (*kstat_raw_reader_t)(kstat_t *, ks_instance_t *); 235 236 static struct { 237 kstat_raw_reader_t fn; 238 char *name; 239 } ks_raw_lookup[] = { 240 /* Function name kstat name */ 241 {save_cpu_stat, "cpu_stat:cpu_stat"}, 242 {save_var, "unix:var"}, 243 {save_ncstats, "unix:ncstats"}, 244 {save_sysinfo, "unix:sysinfo"}, 245 {save_vminfo, "unix:vminfo"}, 246 {save_nfs, "nfs:mntinfo"}, 247 #ifdef __sparc 248 {save_sfmmu_global_stat, "unix:sfmmu_global_stat"}, 249 {save_sfmmu_tsbsize_stat, "unix:sfmmu_tsbsize_stat"}, 250 {save_simmstat, "unix:simm-status"}, 251 {save_temperature, "unix:temperature"}, 252 {save_temp_over, "unix:temperature override"}, 253 {save_ps_shadow, "unix:ps_shadow"}, 254 {save_fault_list, "unix:fault_list"}, 255 #endif 256 {NULL, NULL}, 257 }; 258 259 static kstat_raw_reader_t lookup_raw_kstat_fn(char *, char *); 260 261 #endif /* _STAT_KSTAT_H */