Refactoring: Changed all check parameters starting with an 'o' to the new rulespec...
[check_mk.git] / checks / zfs_arc_cache
blobbd5de5ca21ddec35cdff18567b879d756ffa7d60
1 #!/usr/bin/python
2 # -*- encoding: utf-8; py-indent-offset: 4 -*-
3 # +------------------------------------------------------------------+
4 # | ____ _ _ __ __ _ __ |
5 # | / ___| |__ ___ ___| | __ | \/ | |/ / |
6 # | | | | '_ \ / _ \/ __| |/ / | |\/| | ' / |
7 # | | |___| | | | __/ (__| < | | | | . \ |
8 # | \____|_| |_|\___|\___|_|\_\___|_| |_|_|\_\ |
9 # | |
10 # | Copyright Mathias Kettner 2014 mk@mathias-kettner.de |
11 # +------------------------------------------------------------------+
13 # This file is part of Check_MK.
14 # The official homepage is at http://mathias-kettner.de/check_mk.
16 # check_mk is free software; you can redistribute it and/or modify it
17 # under the terms of the GNU General Public License as published by
18 # the Free Software Foundation in version 2. check_mk is distributed
19 # in the hope that it will be useful, but WITHOUT ANY WARRANTY; with-
20 # out even the implied warranty of MERCHANTABILITY or FITNESS FOR A
21 # PARTICULAR PURPOSE. See the GNU General Public License for more de-
22 # tails. You should have received a copy of the GNU General Public
23 # License along with GNU Make; see the file COPYING. If not, write
24 # to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
25 # Boston, MA 02110-1301 USA.
27 # .--output--------------------------------------------------------------.
28 # | _ _ |
29 # | ___ _ _| |_ _ __ _ _| |_ |
30 # | / _ \| | | | __| '_ \| | | | __| |
31 # | | (_) | |_| | |_| |_) | |_| | |_ |
32 # | \___/ \__,_|\__| .__/ \__,_|\__| |
33 # | |_| |
34 # '----------------------------------------------------------------------'
36 # Example output from agent:
37 # <<<zfs_arc_cache>>>
38 # hits = 106259988004
39 # misses = 27664604758
40 # demand_data_hits = 23694052185
41 # demand_data_misses = 2806853416
42 # demand_metadata_hits = 73187550363
43 # demand_metadata_misses = 1557349557
44 # prefetch_data_hits = 3100882779
45 # prefetch_data_misses = 21062611239
46 # prefetch_metadata_hits = 6277502677
47 # prefetch_metadata_misses = 2237790546
48 # mru_hits = 44007947284
49 # mru_ghost_hits = 2418664836
50 # mfu_hits = 52875478045
51 # mfu_ghost_hits = 1458768458
52 # deleted = 25139978315
53 # recycle_miss = 3965481664
54 # mutex_miss = 323199589
55 # evict_skip = 2543918629307
56 # evict_l2_cached = 0
57 # evict_l2_eligible = 253548767148544
58 # evict_l2_ineligible = 36185885241856
59 # hash_elements = 182514
60 # hash_elements_max = 388216
61 # hash_collisions = 6825894732
62 # hash_chains = 14194
63 # hash_chain_max = 8
64 # p = 914 MB
65 # c = 2010 MB
66 # c_min = 2010 MB
67 # c_max = 320 MB
68 # size = 1554 MB
69 # hdr_size = 36128904
70 # data_size = 951095808
71 # other_size = 642656472
72 # l2_hits = 0
73 # l2_misses = 0
74 # l2_feeds = 0
75 # l2_rw_clash = 0
76 # l2_read_bytes = 0
77 # l2_write_bytes = 0
78 # l2_writes_sent = 0
79 # l2_writes_done = 0
80 # l2_writes_error = 0
81 # l2_writes_hdr_miss = 0
82 # l2_evict_lock_retry = 0
83 # l2_evict_reading = 0
84 # l2_free_on_write = 0
85 # l2_abort_lowmem = 0
86 # l2_cksum_bad = 0
87 # l2_io_error = 0
88 # l2_size = 0
89 # l2_hdr_size = 0
90 # memory_throttle_count = 439874
91 # arc_no_grow = 1
92 # arc_tempreserve = 0 MB
93 # arc_meta_used = 1322 MB
94 # arc_meta_limit = 80 MB
95 # arc_meta_max = 2077 MB
97 # newer output under solaris 11.3 with old agent
98 # <<<zfs_arc_cache>>>
99 # size = 46751 MB
100 # target size (c) = 1027788 MB
101 # target mru_size (p) = 64236 MB
102 # c_min = 4018 MB
103 # c_max = 1027788 MB
104 # buf_size = 605 MB
105 # data_size = 43123 MB
106 # other_size = 2988 MB
107 # rawdata_size = 0 MB
108 # meta_used = 3628 MB
109 # meta_max = 3628 MB
110 # meta_limit = 0 MB
111 # memory_throttle_count = 0
112 # arc_no_grow = 0
113 # arc_tempreserve = 0 MB
114 # mfu_size = 30605 MB
115 # mru_size = 11601 MB
117 # newer output under solaris 11.3 with updated agent
118 # <<<zfs_arc_cache>>>
119 # buf_size = 742832600
120 # c = 48841615704
121 # c_max = 1077714329600
122 # c_min = 4214015904
123 # class = misc
124 # crtime = 6389056,11403263
125 # data_freed = 2633453157248
126 # data_size = 45014421888
127 # deleted = 9360622
128 # demand_data_hits = 645028929
129 # demand_data_misses = 9656913
130 # demand_metadata_hits = 3819285336
131 # demand_metadata_misses = 1934895
132 # evict_l2_cached = 0
133 # evict_l2_eligible = 0
134 # evict_l2_ineligible = 607708484608
135 # evict_prefetch = 977715200
136 # evicted_mfu = 44603686912
137 # evicted_mru = 563104797696
138 # hash_chain_max = 5
139 # hash_chains = 70415
140 # hash_collisions = 2812966
141 # hash_elements = 1585475
142 # hash_elements_max = 1810662
143 # hits = 4467022475
144 # l2_abort_lowmem = 0
145 # l2_cksum_bad = 0
146 # l2_feeds = 0
147 # l2_hdr_size = 0
148 # l2_hits = 0
149 # l2_imports = 0
150 # l2_io_error = 0
151 # l2_misses = 7259729
152 # l2_persistence_hits = 0
153 # l2_read_bytes = 0
154 # l2_rw_clash = 0
155 # l2_size = 0
156 # l2_write_bytes = 0
157 # l2_writes_done = 0
158 # l2_writes_error = 0
159 # l2_writes_sent = 0
160 # memory_throttle_count = 0
161 # meta_limit = 0
162 # meta_max = 4519225600
163 # meta_used = 3836680704
164 # mfu_ghost_hits = 27965
165 # mfu_hits = 4444241817
166 # misses = 11591808
167 # mru_ghost_hits = 499269
168 # mru_hits = 47780363
169 # mutex_miss = 46709
170 # other_size = 3058023880
171 # p = 15479322529
172 # prefetch_behind_prefetch = 429897
173 # prefetch_data_hits = 1849310
174 # prefetch_joins = 1305700
175 # prefetch_meta_size = 35824224
176 # prefetch_metadata_hits = 858900
177 # prefetch_reads = 3616694
178 # prefetch_size = 9486336
179 # rawdata_size = 0
180 # size = 48851102592
181 # snaptime = 6646791,81811455
183 #<<<zfs_arc_cache>>>
184 #hits = 97798158981
185 #misses = 29159034052
186 #demand_data_hits = 21894170403
187 #demand_data_misses = 6555284601
188 #demand_metadata_hits = 67915356653
189 #demand_metadata_misses = 2138181167
190 #prefetch_data_hits = 6162208911
191 #prefetch_data_misses = 19200459846
192 #prefetch_metadata_hits = 1826423014
193 #prefetch_metadata_misses = 1265108438
194 #mru_hits = 32456530155
195 #mru_ghost_hits = 2084134895
196 #mfu_hits = 57357428725
197 #mfu_ghost_hits = 1416265946
198 #deleted = 26434603017
199 #recycle_miss = 2014989945
200 #mutex_miss = 548212067
201 #evict_skip = 1758367956525
202 #evict_l2_cached = 0
203 #evict_l2_eligible = 236579643061760
204 #evict_l2_ineligible = 68829096635392
205 #hash_elements = 235200
206 #hash_elements_max = 441047
207 #hash_collisions = 5893650106
208 #hash_chains = 22800
209 #hash_chain_max = 8
210 #p = 242 MB
211 #c = 2048 MB
212 #c_min = 2010 MB
213 #c_max = 2048 MB
214 #size = 1658 MB
215 #hdr_size = 76639184
216 #data_size = 998181888
217 #other_size = 664157400
218 #l2_hits = 0
219 #l2_misses = 0
220 #l2_feeds = 0
221 #l2_rw_clash = 0
222 #l2_read_bytes = 0
223 #l2_write_bytes = 0
224 #l2_writes_sent = 0
225 #l2_writes_done = 0
226 #l2_writes_error = 0
227 #l2_writes_hdr_miss = 0
228 #l2_evict_lock_retry = 0
229 #l2_evict_reading = 0
230 #l2_free_on_write = 0
231 #l2_abort_lowmem = 0
232 #l2_cksum_bad = 0
233 #l2_io_error = 0
234 #l2_size = 0
235 #l2_hdr_size = 0
236 #memory_throttle_count = 1014537
237 #arc_no_grow = 0
238 #arc_tempreserve = 0 MB
239 #arc_meta_used = 1196 MB
240 #arc_meta_limit = 512 MB
241 #arc_meta_max = 2132 MB
245 # parses agent output in a structure like
246 # {'arc_meta_limit': 80,
247 # 'arc_meta_max': 2077,
248 # 'arc_meta_used': 1322,
249 # [...]
253 def parse_zfs_arc_cache(info):
254 parsed = {}
255 for line in info:
256 if not (len(line) >= 3 and line[1] == "=" and line[2].isdigit()):
257 continue
259 factor = 1
260 if len(line) == 4:
261 if line[3].lower() == "mb":
262 factor = 1024**2
263 elif line[3].lower() == "kb":
264 factor = 1024
265 parsed[line[0]] = int(line[2]) * factor
266 return parsed
269 # .--cache---------------------------------------------------------------.
270 # | _ |
271 # | ___ __ _ ___| |__ ___ |
272 # | / __/ _` |/ __| '_ \ / _ \ |
273 # | | (_| (_| | (__| | | | __/ |
274 # | \___\__,_|\___|_| |_|\___| |
275 # | |
276 # '----------------------------------------------------------------------'
279 def inventory_zfs_arc_cache(parsed):
280 if parsed.get("hits") and parsed.get("misses"):
281 return [(None, None)]
282 return []
285 def check_zfs_arc_cache(_no_item, _no_params, parsed):
286 # Solaris >= 11.3 do not provide these data pretech_*data
287 for key in ["", "prefetch_data_", "prefetch_metadata_"]:
288 if "%shits" % key in parsed and "%smisses" % key in parsed:
289 total_hits_misses = parsed["%shits" % key] + parsed["%smisses" % key]
290 human_key = key.replace("_", " ")
292 if total_hits_misses:
293 hit_ratio = float(parsed["%shits" % key]) / total_hits_misses * 100
294 yield 0, "%sHit Ratio: %0.2f%%" % (human_key.title(), hit_ratio), \
295 [("%shit_ratio" % key, hit_ratio, None, None, 0, 100)]
297 else:
298 yield 0, "No %sHits or Misses" % human_key, \
299 [("%shit_ratio" % key, 0, None, None, 0, 100)]
301 # size
302 if "size" in parsed.keys():
303 size_bytes = parsed["size"]
304 size_readable = get_bytes_human_readable(size_bytes)
305 yield 0, "Cache size: %s" % size_readable, \
306 [("size", float(size_bytes), None, None, 0)]
308 # arc_meta
309 # these values may be missing, this is ok too
310 # in this case just do not report these values
311 if "arc_meta_used" in parsed.keys() and "arc_meta_limit" in parsed.keys() and \
312 "arc_meta_max" in parsed.keys():
313 yield 0, "Arc Meta %s used, Limit %s, Max %s" % \
314 (get_bytes_human_readable(parsed["arc_meta_used"]),
315 get_bytes_human_readable(parsed["arc_meta_limit"]),
316 get_bytes_human_readable(parsed["arc_meta_max"])), \
317 [("arc_meta_used", float(parsed["arc_meta_used"]), None, None, 0),
318 ("arc_meta_limit", float(parsed["arc_meta_limit"]), None, None, 0),
319 ("arc_meta_max", float(parsed["arc_meta_max"]), None, None, 0)]
322 check_info["zfs_arc_cache"] = {
323 "parse_function": parse_zfs_arc_cache,
324 "check_function": check_zfs_arc_cache,
325 "inventory_function": inventory_zfs_arc_cache,
326 "service_description": "ZFS arc cache",
327 "has_perfdata": True,
331 # .--L2 cache------------------------------------------------------------.
332 # | _ ____ _ |
333 # | | | |___ \ ___ __ _ ___| |__ ___ |
334 # | | | __) | / __/ _` |/ __| '_ \ / _ \ |
335 # | | |___ / __/ | (_| (_| | (__| | | | __/ |
336 # | |_____|_____| \___\__,_|\___|_| |_|\___| |
337 # | |
338 # '----------------------------------------------------------------------'
341 def inventory_zfs_arc_cache_l2(parsed):
342 # if l2_size == 0 there is no l2 cache available at all
343 if "l2_size" in parsed.keys() and parsed["l2_size"] > 0:
344 return [(None, None)]
345 return []
348 def check_zfs_arc_cache_l2(_no_item, _no_params, parsed):
349 status = 0
350 perfdata = []
351 message = "ZFS arc cache L2:"
353 # hit ratio
354 if "l2_hits" in parsed.keys() and "l2_misses" in parsed.keys():
355 l2_hit_ratio = float(parsed["l2_hits"]) / (parsed["l2_hits"] + parsed["l2_misses"]) * 100
356 message += " L2 hit ratio: %0.2f%%" % l2_hit_ratio
357 perfdata.append(("l2_hit_ratio", l2_hit_ratio, None, None, 0, 100))
359 else:
360 message += " no info about L2 hit ratio available"
361 perfdata.append(("l2_hit_ratio", 0, None, None, 0, 100))
362 status = 3
364 # size
365 if "l2_size" in parsed.keys():
366 message += ", L2 size: %s" % get_bytes_human_readable(parsed["l2_size"])
367 perfdata.append(("l2_size", float(parsed["l2_size"]), None, None, 0))
368 else:
369 message += ", no info about L2 size available"
370 perfdata.append(("l2_size", 0, None, None, 0))
371 status = 3
373 return status, message, perfdata
376 check_info["zfs_arc_cache.l2"] = {
377 "check_function": check_zfs_arc_cache_l2,
378 "inventory_function": inventory_zfs_arc_cache_l2,
379 "service_description": "ZFS arc cache L2",
380 "has_perfdata": True,