diff --git a/checkman/checkpoint_raid b/checkman/checkpoint_raid new file mode 100644 index 0000000000000000000000000000000000000000..08ef898bcf6eb7a7979de60090d54f9719bbbc5b --- /dev/null +++ b/checkman/checkpoint_raid @@ -0,0 +1,45 @@ +title: Dummy check man page - used as template for new check manuals +agents: linux, windows, aix, solaris, hpux, vms, freebsd, snmp +catalog: see modules/catalog.py for possible values +license: GPL +distribution: check_mk +description: + Describe here: (1) what the check actually does, (2) under which + circumstances it goes warning/critical, (3) which devices are supported + by the check, (4) if the check requires a separated plugin or + tool or separate configuration on the target host. + +item: + Describe the syntax and meaning of the check's item here. Provide all + information one needs if coding a manual check with {checks +=} in {main.mk}. + Give an example. If the check uses {None} as sole item, + then leave out this section. + +examples: + # Give examples for configuration in {main.mk} here. If the check has + # configuration variable, then give example for them here. + + # set default levels to 40 and 60 percent: + foo_default_values = (40, 60) + + # another configuration variable here: + inventory_foo_filter = [ "superfoo", "superfoo2" ] + +perfdata: + Describe precisely the number and meaning of performance variables + the check sends. If it outputs no performance data, then leave out this + section. + +inventory: + Describe how the inventory for the check works. Which items + will it find? Describe the influence of check specific + configuration parameters to the inventory. + +[parameters] +foofirst(int): describe the first parameter here (if parameters are grouped + as tuple) +fooother(string): describe another parameter here. + +[configuration] +foo_default_levels(int, int): Describe global configuration variable of + foo here. Important: also tell the user how they are preset. diff --git a/checkpoint_raid.mkp b/checkpoint_raid.mkp new file mode 100644 index 0000000000000000000000000000000000000000..7c55592269c286133ae444d39e7616bbdcb05fe4 Binary files /dev/null and b/checkpoint_raid.mkp differ diff --git a/checks/checkpoint_raid b/checks/checkpoint_raid new file mode 100644 index 0000000000000000000000000000000000000000..9293e032cdd888dca1a32ef5d7c972e28d17f729 --- /dev/null +++ b/checks/checkpoint_raid @@ -0,0 +1,320 @@ +#!/usr/bin/python +# -*- encoding: utf-8; py-indent-offset: 4 -*- +# +# License: GNU General Public License v2 +# +# Author: thl-cmk[at]outlook[dot]com +# URL : https://thl-cmk.hopto.org +# +# 2016-05-31 : monitor Check Point appliance soft RAID +# 2018-03-08 : changed snmp scan function +# 2018-03-13 : code cleanup +# 2018-03-15 : more code cleanup +# 2020-06-08 : changed snmp-scan function +# 2020-11-10 : removed perfdata +# added wato option to configure 'ignore disks'. For example on the Smart-1 5150 (Array has 12 Disks, +# but only 6 Disks are in the default hardware +# 2021-04-29 : rename from checkpoint_soft_raid in to checkpoint_raid +# +# sample snmpwalk (one volume / two disks) +# +# .1.3.6.1.4.1.2620.1.6.7.7.1.1.1.1.0 = INTEGER: 1 +# .1.3.6.1.4.1.2620.1.6.7.7.1.1.2.1.0 = INTEGER: 0 +# .1.3.6.1.4.1.2620.1.6.7.7.1.1.3.1.0 = INTEGER: 2 +# .1.3.6.1.4.1.2620.1.6.7.7.1.1.4.1.0 = INTEGER: 2 +# .1.3.6.1.4.1.2620.1.6.7.7.1.1.5.1.0 = INTEGER: 1952448512 +# .1.3.6.1.4.1.2620.1.6.7.7.1.1.6.1.0 = INTEGER: 0 +# .1.3.6.1.4.1.2620.1.6.7.7.1.1.7.1.0 = INTEGER: 1 +# .1.3.6.1.4.1.2620.1.6.7.7.1.1.8.1.0 = Gauge32: 931 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.1.1.0 = INTEGER: 1 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.1.2.0 = INTEGER: 2 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.2.1.0 = INTEGER: 0 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.2.2.0 = INTEGER: 0 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.3.1.0 = INTEGER: 0 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.3.2.0 = INTEGER: 1 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.4.1.0 = INTEGER: 0 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.4.2.0 = INTEGER: 1 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.5.1.0 = STRING: "ATA " +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.5.2.0 = STRING: "ATA " +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.6.1.0 = STRING: "ST1000NM0033-9ZM" +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.6.2.0 = STRING: "ST1000NM0033-9ZM" +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.7.1.0 = STRING: "SN04" +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.7.2.0 = STRING: "SN04" +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.8.1.0 = INTEGER: 1953525168 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.8.2.0 = INTEGER: 1953525168 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.9.1.0 = INTEGER: 0 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.9.2.0 = INTEGER: 0 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.10.1.0 = INTEGER: 0 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.10.2.0 = INTEGER: 0 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.11.1.0 = INTEGER: 100 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.11.2.0 = INTEGER: 100 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.12.1.0 = Gauge32: 931 +# .1.3.6.1.4.1.2620.1.6.7.7.2.1.12.2.0 = Gauge32: 931 +# +# +# sample info +# +# [[[u'1', u'0', u'2', u'2', u'1952448512', u'0', u'1', u'931']], +# [[u'1', u'0', u'0', u'0', u'ATA ', u'ST1000NM0033-9ZM', u'SN04', u'1953525168', u'0', u'0', u'100', u'931'], +# [u'2', u'0', u'1', u'1', u'ATA ', u'ST1000NM0033-9ZM', u'SN04', u'1953525168', u'0', u'0', u'100', u'931']]] +# +# + +factory_settings['checkpoint_raid_defaults'] = { + 'ignore_disks': '', +} + + +def parse_checkpoint_raid(info): + raidvolumetype = { + 0 : 'RAID-0', + 1 : 'RAID-1E', + 2 : 'RAID-1', + 3 : 'RAID_10', + 4 : 'RAID-4', + 5 : 'RAID-5', + 6 : 'RAID-6', + 7 : 'RAID-60', + 8 : 'RAID-50', + } + + raw_volumes, raw_disks = info + volumes = [] + disks = [] + + for volume in raw_volumes: + volumeindex, volumeid, volumetype, numofdisksonraid, volumemaxlba, volumestate, volumeflags, volumesize = volume + + if volumeindex.isdigit(): + volumes.append({'volumeindex' : int(volumeindex), + 'volumeid' : int(volumeid), + 'volumetype' : raidvolumetype.get(int(volumetype)), + 'numofdisksonraid': int(numofdisksonraid), + 'volumemaxlba' : int(volumemaxlba), + 'volumestate' : int(volumestate), + 'volumeflags' : volumeflags, + 'volumesize' : int(volumesize), + }) + + for disk in raw_disks: + diskindex, diskvolumeid, diskid, disknumber, diskvendor, diskproductid, diskrevision, diskmaxlba, diskstate, \ + diskflags, disksyncstate, disksize = disk + + if diskindex.isdigit(): + disks.append({'diskindex' : int(diskindex), + 'diskvolumeid' : int(diskvolumeid), + 'diskid' : int(disknumber), + 'diskvendor' : diskvendor, + 'diskproductid': diskproductid, + 'diskrevision' : diskrevision, + 'diskmaxlba' : int(diskmaxlba), + 'diskstate' : int(diskstate), + 'diskflags' : diskflags, + 'disksyncstate': int(disksyncstate), + 'disksize' : int(disksize) + }) + + parse = [volumes, disks] + return parse + + +def inventory_checkpoint_raid(parse): + volumes, disks = parse + disksonvolume = [] + if len(volumes) != 0: + for volume in volumes: + volumeid = volume.get('volumeid') + item = 'Volume %d' % volumeid + for disk in disks: + if disk.get('diskvolumeid') == volumeid: + disksonvolume.append(disk) + disks.remove(disk) + yield item, None + + +def check_checkpoint_raid(item, params, parse): + raidvolumestate = { + 0: 'OPTIMAL', + 1: 'DEGRADED', + 2: 'FAILED', + } + + raidvolumeflags = { + 0 : 'NONE', + 1 : 'ENABLED', + 2 : 'QUIESCED', + 3 : 'RESYNC IN PROGRESS', + 4 : 'VOLUME INACTIVE', + 5 : 'NOT CONFIGURED', + 6 : 'USING INTERIM RECOVERY MODE', + 7 : 'READY FOR RECOVERY OPERATION', + 8 : 'WRONG PHYSICAL DRIVE WAS REPLACED', + 9 : 'A PHYSICAL DRIVE IS NOT PROPERLY CONNECTED', + 10: 'HARDWARE IS OVER HEATING', + 11: 'HARDWARE WAS OVERHEATED', + 12: 'CURRENTLY EXPENDING', + 13: 'NOT YET AVAILABLE', + 14: 'QUEUED FOR EXPENSION', + 15: 'MIGRATING', + 16: 'IMPACTED', + 17: 'OFFLINE', + 18: 'CLEARING', + } + + raiddiskstate = { + 0 : 'ONLINE', + 1 : 'MISSING', + 2 : 'NOT COMPATIBLE', + 3 : 'DISC FAILED', + 4 : 'INITIALIZING', + 5 : 'OFFLINE REQUESTED', + 6 : 'FAILED REQUESTED', + 7 : 'UNCONFIGURED GOOD SPUN UP', + 8 : 'UNCONFIGURED GOOD SPUN DOWN', + 9 : 'UNCONFIGURED BAD', + 10 : 'HOTSPARE', + 11 : 'DRIVE OFFLINE', + 12 : 'REBUILD', + 13 : 'FAILED', + 14 : 'COPYBACK', + 255: 'OTHER OFFLINE', + } + + raiddiskflags = { + 0: 'NONE', + 1: 'OUT OF SYNC', + 2: 'QUIESCED', + 3: 'VERIFYING', + 4: 'READY', + } + + raiddiskid = { + 0: 'Upper', + 1: 'Lower', + } + + def getflags(flags, flags_description): + description = '' + flags = int(flags) + if flags == 0: + return flags_description.get(0) + else: + for x in range(0, len(flags_description)): + if flags & (1 << x) != 0: + if flags_description.get(x + 1) is not None: + description += '%s,' % flags_description.get(x + 1) + return description + + volumes, disks = parse + infotext = '' + longoutput = '' + perfdata = [] + ignore_disks = [] + + if params: + ignore_disks = params.get('ignore_disks', '').split(',') + + if len(volumes) != 0: + for volume in volumes: + volumeid = volume.get('volumeid') + if item == "Volume %d" % volumeid: + for disk in disks: + if disk.get('diskvolumeid') != volumeid: + disks.remove(disk) + + # volume infos + if volume.get('volumestate') != 0: + yield 2, 'Volume state %s' % raidvolumestate.get(volume.get('volumestate')) + else: + yield 0, 'Volume state: %s' % raidvolumestate.get(volume.get('volumestate')) + + infotext += '%s, ' % volume.get('volumetype') + infotext += '%d disks, ' % volume.get('numofdisksonraid') + infotext += '%d GB, ' % volume.get('volumesize') + + longoutput += '\nVolume state: %s, ' % raidvolumestate.get(volume.get('volumestate')) + longoutput += 'Type: %s, ' % volume.get('volumetype') + longoutput += '# of disks: %d , ' % volume.get('numofdisksonraid') + longoutput += 'Size: %d GB, ' % volume.get('volumesize') + longoutput += 'max LBA: %d, ' % volume.get('volumemaxlba') + longoutput += 'Flags: %s' % getflags(volume.get('volumeflags'), raidvolumeflags) + + # disk infos + disks_in_array = 0 + disks_online = 0 + disks_ignored = 0 + for disk in disks: + diskid = disk.get('diskid') + if not str(diskid) in ignore_disks: + disks_in_array += 1 + syncstate = disk.get('disksyncstate') + if disk.get('diskstate') != 0: + yield 2, 'Disk ID: %d state: %s' % (diskid, raiddiskstate.get(disk.get('diskstate'))) + else: + # yield 0, 'Disk ID %d state %s' % (diskid, raiddiskstate.get(disk.get('diskstate'))) + disks_online += 1 + + longoutput += '\n%s disk (id %d): ' % (raiddiskid.get(diskid), diskid) + longoutput += 'State: %s, ' % raiddiskstate.get(disk.get('diskstate')) + longoutput += 'Sync: %d%s, ' % (syncstate, '%') + longoutput += 'Size: %d GB, ' % disk.get('disksize') + longoutput += 'max LBA: %d, ' % disk.get('diskmaxlba') + longoutput += 'Vendor: %s, ' % disk.get('diskvendor') + longoutput += 'Product id: %s, ' % disk.get('diskproductid') + longoutput += 'Revision: %s, ' % disk.get('diskrevision') + longoutput += 'Flags: %s' % getflags(disk.get('diskflags'), raiddiskflags) + + # perfdata.append(('disk_id_%d' % diskid, syncstate, None, None, 0, 100)) + else: + disks_ignored += 1 + + # remove last ', ' + # infotext = infotext[:-2] + + if disks_in_array == disks_online: + yield 0, '%d/%d Disks online' % (disks_online, disks_in_array) + else: + yield 2, '%d/%d Disks online' % (disks_online, disks_in_array) + + if disks_ignored > 0: + yield 0, '%d Disks ignored' % disks_ignored + + yield 0, infotext + longoutput # , perfdata + + +check_info['checkpoint_raid'] = { + 'check_function' : check_checkpoint_raid, + 'inventory_function' : inventory_checkpoint_raid, + 'parse_function' : parse_checkpoint_raid, + 'default_levels_variable' : 'checkpoint_raid_defaults', + 'service_description' : 'Soft RAID %s', + 'group' : 'checkpoint_raid', + # 'has_perfdata' : True, + 'snmp_scan_function': lambda oid: (oid('.1.3.6.1.2.1.1.2.0').startswith('.1.3.6.1.4.1.2620.1.6.123.1') or + oid('.1.3.6.1.2.1.1.2.0').startswith('.1.3.6.1.4.1.8072.3.2.10')) and + oid('.1.3.6.1.4.1.2620.1.6.1.0', '').lower().startswith('svn foundation'), + 'snmp_info' : [('.1.3.6.1.4.1.2620.1.6.7.7.1.1', [ # CHECKPOINT-MIB::raidVolumeEntry + '1', # raidVolumeIndex + '2', # raidVolumeID + '3', # raidVolumeType + '4', # numOfDisksOnRaid + '5', # raidVolumeMaxLBA + '6', # raidVolumeState + '7', # raidVolumeFlags + '8', # raidVolumeSize + ]), + ('.1.3.6.1.4.1.2620.1.6.7.7.2.1', [ # CHECKPOINT-MIB::raidDiskEntry + '1', # raidDiskIndex + '2', # raidDiskVolumeID + '3', # raidDiskID + '4', # raidDiskNumber + '5', # raidDiskVendor + '6', # raidDiskProductID + '7', # raidDiskRevision + '8', # raidDiskMaxLBA + '9', # raidDiskState + '10', # raidDiskFlags + '11', # raidDiskSyncState + '12', # raidDiskSize + ])], +} \ No newline at end of file diff --git a/packages/checkpoint_raid b/packages/checkpoint_raid new file mode 100644 index 0000000000000000000000000000000000000000..cb964e8b22a726014427303ddc3638de9e3b1764 --- /dev/null +++ b/packages/checkpoint_raid @@ -0,0 +1,14 @@ +{'author': u'Th.L. (thl-cmk[at]outlook[dot]com)', + 'description': u'monitor Check Point appliance RAID\n', + 'download_url': 'http://thl-cmk.hopto.org/', + 'files': {'checkman': ['checkpoint_raid'], + 'checks': ['checkpoint_raid'], + 'web': ['plugins/metrics/checkpoint_raid.py', + 'plugins/wato/checkpoint_raid.py']}, + 'name': 'checkpoint_raid', + 'num_files': 4, + 'title': u'Check Point appliance RAID', + 'version': '20210429.v0.3', + 'version.min_required': '1.2.8b8', + 'version.packaged': '1.6.0p12', + 'version.usable_until': None} \ No newline at end of file diff --git a/web/plugins/metrics/checkpoint_raid.py b/web/plugins/metrics/checkpoint_raid.py new file mode 100644 index 0000000000000000000000000000000000000000..a9482d72393625d4bd68e5a37906d1e0289d631d --- /dev/null +++ b/web/plugins/metrics/checkpoint_raid.py @@ -0,0 +1,82 @@ +#!/usr/bin/python +# -*- encoding: utf-8; py-indent-offset: 4 -*- +# +# License: GNU General Public License v2 +# +# Author: thl-cmk[at]outlook[dot]com +# URL : https://thl-cmk.hopto.org +# Date : 2018-04-11 +# +# Check Point soft RAID metrics plugin +# + +############################################################################## +# +# define units for perfdata +# +############################################################################## + + +############################################################################## +# +# define metrics for perfdata +# +############################################################################## + +metric_info['checkpoint_raid_disk_id_0'] = { + 'title': _('Sync Disk 0'), + 'unit': '%', + 'color': '11/a', +} + + +metric_info['checkpoint_raid_disk_id_1'] = { + 'title': _('Sync Disk 1'), + 'unit': '%', + 'color': '21/a', +} + +############################################################################## +# +# map perfdata to metric +# +############################################################################## + +check_metrics['check_mk-checkpoint_raid'] = { + 'disk_id_0': {'name': 'checkpoint_raid_disk_id_0', }, + 'disk_id_1': {'name': 'checkpoint_raid_disk_id_1', } +} + +############################################################################## +# +# how to graph perdata +# +############################################################################## + +graph_info.append({ + 'title': _('Check Point soft RAID sync status'), + 'metrics': [ + ('checkpoint_raid_disk_id_0', 'area'), + ('checkpoint_raid_disk_id_1', '-area'), + ], +}) + +############################################################################## +# +# define perf-o-meter +# +############################################################################## + + +perfometer_info.append(('stacked', [ + { + 'type': 'linear', + 'segments': ['checkpoint_raid_disk_id_0',], + 'total': 100, + }, + { + 'type': 'linear', + 'segments': ['checkpoint_raid_disk_id_1',], + 'total': 100, + } +])) \ No newline at end of file diff --git a/web/plugins/wato/checkpoint_raid.py b/web/plugins/wato/checkpoint_raid.py new file mode 100644 index 0000000000000000000000000000000000000000..5c07a44a2899231533d91f91bd62db061348b195 --- /dev/null +++ b/web/plugins/wato/checkpoint_raid.py @@ -0,0 +1,33 @@ +#!/usr/bin/python +# -*- encoding: utf-8; py-indent-offset: 4 -*- +# +# License: GNU General Public License v2 +# +# Author: thl-cmk[at]outlook[dot]com +# URL : https://thl-cmk.hopto.org +# +# Check_MK checkpoint_soft_rais WATO plugin +# +# +# + +register_check_parameters( + subgroup_networking, + 'checkpoint_raid', + _('Check Point Soft Raid'), + Dictionary( + help=_(''), + elements=[ + ('ignore_disks', + TextUnicode( + title=_('list of comma separated disk IDs to ignore'), + help=_('This is usefull for RAID Arrays with missing disks like on the Smart-1 5150. There the ' + 'array is configured for 12 Disk but in the default Hardware are only 6 Disks.'), + default_value=None, + allow_empty=False, + )), + ], + ), + None, + match_type='dict', +)