Modernize mempools (#12282)

* mempools to modern module
quick hacky hrstorage port

* port ucd-snmp-mib to Mempools

* Populate DB for ucd
Prep for yaml

* initial yaml attempt

* more complex conversions
fixes to YamlDiscovery, make leading $ optional and allow mib::oid format

* walk full tables and skip values
normalize percentages above 100

* handle precent only ones (specify total as 100)

* Move default polling out of YamlMempoolsDiscovery

* fixes

* Update test data hrstorage should be correct.

* perc_warn for hrstorage

* Host Resources, record buffer, cached, and shared

* Host Resources is always better, don't do both HR and UCD

* fix unix, include warning levels

* variable size

* consolidate skip_values

* define mempools schema

* number instead of integer

* more schema refactor

* one more skip_values reference

* throw error for invalid oid translation
aos6

* a*  and Cisco

* updated test data

* update almost all hrstorage data files

* b*

* c* with test data
use standard cache for hrStorage

* use cache for storage module too

* hand bsnmp properly

* bdcom

* exclude total oid from yaml so it is not polled
May add a way to ignore this behavior and poll it, but I don't know if that is needed.

* automatically handle percent only values

* ciscowlc

* only poll used or free if we have used, free, and total.

* fix skipping

* the dlinkoning
fix find value when value "name" is numeric

* support numeric oids

* dnos/ftos attempt

* I guess we can't filter on total > 0

* edgecos

* e*

* f WIP

* f*

* gwd (aka g*)

* h* + procurve

* i*

* j*

* m*

* support 0% used memory (however unlikely)

* n*

* CISCO-PROCESS-MIB memory, share cache with processors module

* ignore mempools with invalid total

* p*

* quanta

* r*
fix raisecom mibs terribly broken

* s-z

* style fixes

* Move VRP back to PHP and make it actually work

* fix zynos

* update schema

* Update Cisco processor data for description bug fixes

* fix comware processors

* comware mempools with memory size
default precision to 1

* sophos-xg updated data

* hrstorage use ram size for buffers, cache, and shared

* Show memory available instead of free in device overview

* UCD, use same rrd format, store available instead of free in the db.

* Calculate availability for HOST-RESOURCES-MIB

* Convert UCD to standard polling

* rename old rrd files

* initial graph work

* graph WIP

* Graph looking decent

* Graph looking decent for hr

* remove old ucd_graph code

* handle availability mempool
more graph cleanup

* color adjustments

* remove accidental free calculation

* Update test data and fix corner cases

* fis pfsense

* update schema

* add default value for mempool_class

* fix whitespace

* update schema

* update schema correctly

* one more time

* fortigate_1500d-sensors missing oids

* Update docs.

* fix indent

* add implements MempoolsDiscovery explicitly to OS

* remove ucd_memory graph references
remove unused device_memory graph

* remove unused functions

* set devices with mempools to rediscover to prevent/minimize gaps

* use a subquery

* add overview graph

* port health mempools table

* Update device mempool

* only show overview if multiple

* Don't override user set warn percentages in discovery

* fix missed usage

* fix style

* Safety check to not rename rrd files incorrectly if migration has not been run.

* Fix overview percent bar and represent available and used on the bar

* missed an item to convert to mempool_class

* percent on the wrong side
This commit is contained in:
Tony Murray 2020-11-23 15:35:35 -06:00 committed by GitHub
parent b022a30a5b
commit f2f169ae78
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
626 changed files with 27669 additions and 20474 deletions

View File

@ -181,9 +181,10 @@ class Processor extends Model implements DiscoveryModule, PollerModule, Discover
/** @var string $processor_type */
/** @var int $processor_index */
/** @var int $processor_usage */
/** @var string $processor_descr */
if (array_key_exists($processor_id, $data)) {
$usage = round($data[$processor_id], 2);
echo "$usage%\n";
echo "$processor_descr: $usage%\n";
$rrd_name = ['processor', $processor_type, $processor_index];
$fields = compact('usage');

View File

@ -26,6 +26,7 @@ namespace LibreNMS\Device;
use Illuminate\Support\Arr;
use Illuminate\Support\Str;
use LibreNMS\Exceptions\InvalidOidException;
use LibreNMS\Interfaces\Discovery\DiscoveryItem;
use LibreNMS\OS;
@ -107,9 +108,18 @@ class YamlDiscovery
return $items;
}
public static function replaceValues($name, $index, $count, $data, $pre_cache)
/**
* @param string $name Name of the field in yaml
* @param string $index index in the snmp table
* @param int $count current count of snmp table entries
* @param array $def yaml definition
* @param array $pre_cache snmp data fetched from device
* @return mixed|string|string[]|null
*/
public static function replaceValues($name, $index, $count, $def, $pre_cache)
{
$value = static::getValueFromData($name, $index, $data, $pre_cache);
$value = static::getValueFromData($name, $index, $def, $pre_cache);
if (is_null($value)) {
// built in replacements
$search = [
@ -127,11 +137,11 @@ class YamlDiscovery
$replace[] = $subindex;
}
$value = str_replace($search, $replace, $data[$name]);
$value = str_replace($search, $replace, $def[$name]);
// search discovery data for values
$value = preg_replace_callback('/{{ \$([a-zA-Z0-9\-.]+) }}/', function ($matches) use ($index, $data, $pre_cache) {
$replace = static::getValueFromData($matches[1], $index, $data, $pre_cache, null);
$value = preg_replace_callback('/{{ \$?([a-zA-Z0-9\-.:]+) }}/', function ($matches) use ($index, $def, $pre_cache) {
$replace = static::getValueFromData($matches[1], $index, $def, $pre_cache, null);
if (is_null($replace)) {
d_echo('Warning: No variable available to replace ' . $matches[1] . ".\n");
@ -169,12 +179,14 @@ class YamlDiscovery
return $pre_cache[$discovery_data['oid']][$index][$name];
}
if (isset($pre_cache[$name])) {
if (isset($pre_cache[$index][$name])) {
return $pre_cache[$index][$name];
}
if (isset($pre_cache[$name]) && ! is_numeric($name)) {
if (is_array($pre_cache[$name])) {
if (isset($pre_cache[$name][$index][$name])) {
return $pre_cache[$name][$index][$name];
} elseif (isset($pre_cache[$index][$name])) { //probably makes no sense here
return $pre_cache[$index][$name]; //same
} elseif (isset($pre_cache[$name][$index])) {
return $pre_cache[$name][$index];
} elseif (count($pre_cache[$name]) === 1) {
@ -250,7 +262,7 @@ class YamlDiscovery
* @param mixed $value
* @param array $yaml_item_data The data key from this item
* @param array $group_options The options key from this group of items
* @param array $item_snmp_data The pre-cache data array
* @param array $pre_cache The pre-cache data array
* @return bool
*/
public static function canSkipItem($value, $index, $yaml_item_data, $group_options, $pre_cache = [])
@ -291,4 +303,38 @@ class YamlDiscovery
return false;
}
/**
* Translate an oid to numeric format (if already numeric, return as-is)
*
* @param string $oid
* @param array|null $device
* @param string $mib
* @param string|null $mibdir
* @return string numeric oid
* @throws \LibreNMS\Exceptions\InvalidOidException
*/
public static function oidToNumeric($oid, $device = null, $mib = 'ALL', $mibdir = null)
{
if (self::oidIsNumeric($oid)) {
return $oid;
}
foreach (explode(':', $mib) as $mib_name) {
if ($numeric_oid = snmp_translate($oid, $mib_name, $mibdir, null, $device)) {
break;
}
}
if (empty($numeric_oid)) {
throw new InvalidOidException("Unable to translate oid $oid");
}
return $numeric_oid;
}
public static function oidIsNumeric($oid)
{
return (bool) preg_match('/^[.\d]+$/', $oid);
}
}

View File

@ -1,8 +1,8 @@
<?php
/**
* netonix.inc.php
/*
* InvalidOidException.php
*
* LibreNMS mempools module for Netonix
* Exception during Yaml discovery to indicate an invalid oid
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@ -17,13 +17,14 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
* @package LibreNMS
* @link http://librenms.org
* @copyright 2016 Tony Murray
* @copyright 2020 Tony Murray
* @author Tony Murray <murraytony@gmail.com>
*/
$total = snmp_get($device, 'UCD-SNMP-MIB::memTotalReal.0', '-OvQU') * 1024;
$free = snmp_get($device, 'UCD-SNMP-MIB::memAvailReal.0', '-OvQU') * 1024;
$mempool['total'] = $total;
$mempool['free'] = $free;
$mempool['used'] = $total - $free;
namespace LibreNMS\Exceptions;
class InvalidOidException extends YamlException
{
}

View File

@ -1,8 +1,8 @@
<?php
/**
* netonix.inc.php
/*
* YamlException.php
*
* LibreNMS mempools module for Netonix
* Exception generated during Yaml Discovery
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@ -17,16 +17,14 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
* @package LibreNMS
* @link http://librenms.org
* @copyright 2016 Tony Murray
* @copyright 2020 Tony Murray
* @author Tony Murray <murraytony@gmail.com>
*/
if ($device['os'] == 'netonix') {
echo 'NETONIX : ';
$free = snmp_get($device, 'UCD-SNMP-MIB::memTotalFree.0', '-OvQU');
namespace LibreNMS\Exceptions;
if (is_numeric($free)) {
discover_mempool($valid_mempool, $device, 0, 'netonix', 'Memory', 1024);
}
class YamlException extends \Exception
{
}

View File

@ -1,8 +1,8 @@
<?php
/**
* 3com.inc.php
/*
* MempoolsDiscovery.php
*
* LibreNMS mempool discovery module for 3com
* -Description-
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@ -17,16 +17,21 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
* @package LibreNMS
* @link http://librenms.org
* @copyright 2017 Neil Lathwood
* @author Neil Lathwood <neil@lathwood.co.uk>
* @copyright 2020 Tony Murray
* @author Tony Murray <murraytony@gmail.com>
*/
if ($device['os'] === '3com') {
echo '3COM:';
$usage = snmp_get($device, '.1.3.6.1.4.1.43.45.1.6.1.2.1.1.3.65536', '-Ovq');
if (is_numeric($usage)) {
$descr = 'Memory';
discover_mempool($valid_mempool, $device, 0, '3com', $descr, '1', null, null);
}
namespace LibreNMS\Interfaces\Discovery;
interface MempoolsDiscovery
{
/**
* Discover a Collection of Mempool models.
* Will be keyed by mempool_type and mempool_index
*
* @return \Illuminate\Support\Collection \App\Models\Mempool
*/
public function discoverMempools();
}

View File

@ -1,8 +1,8 @@
<?php
/**
* fabos.inc.php
/*
* MempoolsPolling.php
*
* LibreNMS mempool poller module for fabos
* -Description-
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@ -17,14 +17,19 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
* @package LibreNMS
* @link http://librenms.org
* @copyright 2017 Neil Lathwood
* @author Neil Lathwood <neil@lathwood.co.uk>
* @copyright 2020 Tony Murray
* @author Tony Murray <murraytony@gmail.com>
*/
$perc = snmp_get($device, 'swMemUsage.0', '-Ovq', 'SW-MIB');
if (is_numeric($perc)) {
$mempool['total'] = 100;
$mempool['used'] = $perc;
$mempool['free'] = ($mempool['total'] - $mempool['used']);
namespace LibreNMS\Interfaces\Polling;
interface MempoolsPolling
{
/**
* @param \Illuminate\Support\Collection $mempools \App\Models\Mempool
* @return \Illuminate\Support\Collection \App\Models\Mempool
*/
public function pollMempools($mempools);
}

View File

@ -0,0 +1,191 @@
<?php
/*
* Mempools.php
*
* -Description-
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
* @package LibreNMS
* @link http://librenms.org
* @copyright 2020 Tony Murray
* @author Tony Murray <murraytony@gmail.com>
*/
namespace LibreNMS\Modules;
use App\Models\Mempool;
use Illuminate\Support\Collection;
use LibreNMS\DB\SyncsModels;
use LibreNMS\Interfaces\Discovery\MempoolsDiscovery;
use LibreNMS\Interfaces\Module;
use LibreNMS\Interfaces\Polling\MempoolsPolling;
use LibreNMS\OS;
use LibreNMS\RRD\RrdDefinition;
use LibreNMS\Util\ModuleModelObserver;
use Log;
class Mempools implements Module
{
use SyncsModels;
public function discover(OS $os)
{
if ($os instanceof MempoolsDiscovery) {
$mempools = $os->discoverMempools()->filter(function (Mempool $mempool) {
if ($mempool->isValid()) {
return true;
}
Log::debug("Rejecting Mempool $mempool->mempool_index $mempool->mempool_descr: Invalid total value");
return false;
});
$this->calculateAvailable($mempools);
ModuleModelObserver::observe('\App\Models\Mempool');
$this->syncModels($os->getDevice(), 'mempools', $mempools);
echo PHP_EOL;
$mempools->each(function ($mempool) {
$this->printMempool($mempool);
});
}
}
public function poll(OS $os)
{
$mempools = $os->getDevice()->mempools;
if ($mempools->isEmpty()) {
return;
}
$os instanceof MempoolsPolling
? $os->pollMempools($mempools)
: $this->defaultPolling($os, $mempools);
$this->calculateAvailable($mempools)->each(function (Mempool $mempool) use ($os) {
$this->printMempool($mempool);
if (empty($mempool->mempool_class)) {
Log::debug('Mempool skipped. Does not include class.');
}
$mempool->save();
$rrd_name = ['mempool', $mempool->mempool_type, $mempool->mempool_class, $mempool->mempool_index];
$rrd_oldname = ['mempool', $mempool->mempool_type, $mempool->mempool_index];
$rrd_def = RrdDefinition::make()
->addDataset('used', 'GAUGE', 0)
->addDataset('free', 'GAUGE', 0);
$fields = [
'used' => $mempool->mempool_used,
'free' => $mempool->mempool_free,
];
$tags = compact('mempool_type', 'mempool_index', 'rrd_name', 'rrd_def', 'rrd_oldname');
data_update($os->getDeviceArray(), 'mempool', $tags, $fields);
});
}
/**
* @param OS $os
* @param \Illuminate\Support\Collection $mempools
* @return \Illuminate\Support\Collection
*/
private function defaultPolling($os, $mempools)
{
// fetch all data
$oids = $mempools->map->only(['mempool_perc_oid', 'mempool_used_oid', 'mempool_free_oid', 'mempool_total_oid'])
->flatten()->filter()->unique()->values()->all();
$data = snmp_get_multi_oid($os->getDeviceArray(), $oids);
$mempools->each(function (Mempool $mempool) use ($data) {
$mempool->fillUsage(
$data[$mempool->mempool_used_oid] ?? null,
$data[$mempool->mempool_total_oid] ?? null,
$data[$mempool->mempool_free_oid] ?? null,
$data[$mempool->mempool_perc_oid] ?? null
);
});
return $mempools;
}
public function cleanup(OS $os)
{
$os->getDevice()->mempools()->delete();
}
/**
* Calculate available memory. This is free + buffers + cached.
*
* @param \Illuminate\Support\Collection $mempools
* @return \Illuminate\Support\Collection|void
*/
private function calculateAvailable(Collection $mempools)
{
if ($mempools->count() > 2) { // optimization
$system = null;
$buffers = null;
$cached = null;
foreach ($mempools as $mempool) {
/** @var Mempool $mempool */
if ($mempool->mempool_class == 'system') {
if ($system !== null) {
Log::debug('Aborted available calculation, too many system class mempools');
return $mempools; // more than one system, abort
}
$system = $mempool;
} elseif ($mempool->mempool_class == 'buffers') {
if ($buffers !== null) {
Log::debug('Aborted available calculation, too many buffers class mempools');
return $mempools; // more than one buffer, abort
}
$buffers = $mempool->mempool_used;
} elseif ($mempool->mempool_class == 'cached') {
if ($cached !== null) {
Log::debug('Aborted available calculation, too many cached class mempools');
return $mempools; // more than one cache, abort
}
$cached = $mempool->mempool_used;
}
}
if ($system !== null) {
$old = format_bi($system->mempool_free);
$system->fillUsage(($system->mempool_used - $buffers - $cached) / $system->mempool_precision, $system->mempool_total / $system->mempool_precision);
$new = format_bi($system->mempool_free);
Log::debug("Free memory adjusted by availability calculation: {$old}iB -> {$new}iB\n");
}
}
return $mempools;
}
private function printMempool(Mempool $mempool)
{
echo "$mempool->mempool_type [$mempool->mempool_class]: $mempool->mempool_descr: $mempool->mempool_perc%";
if ($mempool->mempool_total != 100) {
$used = format_bi($mempool->mempool_used);
$total = format_bi($mempool->mempool_total);
echo " {$used}iB / {$total}iB";
}
echo PHP_EOL;
}
}

View File

@ -30,22 +30,27 @@ use DeviceCache;
use Illuminate\Support\Str;
use LibreNMS\Device\WirelessSensor;
use LibreNMS\Device\YamlDiscovery;
use LibreNMS\Interfaces\Discovery\MempoolsDiscovery;
use LibreNMS\Interfaces\Discovery\OSDiscovery;
use LibreNMS\Interfaces\Discovery\ProcessorDiscovery;
use LibreNMS\OS\Generic;
use LibreNMS\OS\Traits\HostResources;
use LibreNMS\OS\Traits\UcdResources;
use LibreNMS\OS\Traits\YamlMempoolsDiscovery;
use LibreNMS\OS\Traits\YamlOSDiscovery;
class OS implements ProcessorDiscovery, OSDiscovery
class OS implements ProcessorDiscovery, OSDiscovery, MempoolsDiscovery
{
use HostResources {
HostResources::discoverProcessors as discoverHrProcessors;
HostResources::discoverMempools as discoverHrMempools;
}
use UcdResources {
UcdResources::discoverProcessors as discoverUcdProcessors;
UcdResources::discoverMempools as discoverUcdMempools;
}
use YamlOSDiscovery;
use YamlMempoolsDiscovery;
private $device; // annoying use of references to make sure this is in sync with global $device variable
private $graphs; // stores device graphs
@ -285,7 +290,21 @@ class OS implements ProcessorDiscovery, OSDiscovery
return $processors;
}
public function getDiscovery()
public function discoverMempools()
{
if ($this->hasYamlDiscovery('mempools')) {
return $this->discoverYamlMempools();
}
$mempools = $this->discoverHrMempools();
if ($mempools->isNotEmpty()) {
return $mempools;
}
return $this->discoverUcdMempools();
}
public function getDiscovery($module = null)
{
if (! array_key_exists('dynamic_discovery', $this->device)) {
$file = base_path('/includes/definitions/discovery/' . $this->getName() . '.yaml');
@ -294,6 +313,10 @@ class OS implements ProcessorDiscovery, OSDiscovery
}
}
if ($module) {
return $this->device['dynamic_discovery']['modules'][$module] ?? [];
}
return $this->device['dynamic_discovery'] ?? [];
}

View File

@ -25,11 +25,13 @@
namespace LibreNMS\OS;
use App\Models\Device;
use App\Models\Mempool;
use LibreNMS\Device\Processor;
use LibreNMS\Interfaces\Discovery\MempoolsDiscovery;
use LibreNMS\Interfaces\Discovery\ProcessorDiscovery;
use LibreNMS\OS;
class Comware extends OS implements ProcessorDiscovery
class Comware extends OS implements MempoolsDiscovery, ProcessorDiscovery
{
public function discoverOS(Device $device): void
{
@ -48,16 +50,16 @@ class Comware extends OS implements ProcessorDiscovery
*/
public function discoverProcessors()
{
$procdata = $this->getCacheByIndex('hh3cEntityExtCpuUsage', 'HH3C-ENTITY-EXT-MIB');
if (! empty($procdata)) {
$entity_data = $this->getCacheByIndex('entPhysicalName', 'ENTITY-MIB');
}
$processors = [];
$procdata = snmpwalk_group($this->getDeviceArray(), 'hh3cEntityExtCpuUsage', 'HH3C-ENTITY-EXT-MIB');
if (empty($procdata)) {
return $processors;
}
$entity_data = $this->getCacheByIndex('entPhysicalName', 'ENTITY-MIB');
foreach ($procdata as $index => $usage) {
if ($usage != 0) {
if ($usage['hh3cEntityExtCpuUsage'] != 0) {
$processors[] = Processor::discover(
$this->getName(),
$this->getDeviceId(),
@ -65,7 +67,7 @@ class Comware extends OS implements ProcessorDiscovery
$index,
$entity_data[$index],
1,
$usage,
$usage['hh3cEntityExtCpuUsage'],
null,
$index
);
@ -74,4 +76,33 @@ class Comware extends OS implements ProcessorDiscovery
return $processors;
}
public function discoverMempools()
{
$mempools = collect();
$data = snmpwalk_group($this->getDeviceArray(), 'hh3cEntityExtMemUsage', 'HH3C-ENTITY-EXT-MIB');
if (empty($data)) {
return $mempools; // avoid additional walks
}
$data = snmpwalk_group($this->getDeviceArray(), 'hh3cEntityExtMemSize', 'HH3C-ENTITY-EXT-MIB', 1, $data);
$entity_name = $this->getCacheByIndex('entPhysicalName', 'ENTITY-MIB');
$entity_class = $this->getCacheByIndex('entPhysicalClass', 'ENTITY-MIB');
foreach ($data as $index => $entry) {
if ($entity_class[$index] == 'module' && $entry['hh3cEntityExtMemUsage'] > 0) {
$mempools->push((new Mempool([
'mempool_index' => $index,
'mempool_type' => 'comware',
'mempool_class' =>'system',
'mempool_descr' => $entity_name[$index],
'mempool_precision' => 1,
'mempool_perc_oid' => ".1.3.6.1.4.1.25506.2.6.1.1.1.1.8.$index",
]))->fillUsage(null, $entry['hh3cEntityExtMemSize'], null, $entry['hh3cEntityExtMemUsage']));
}
}
return $mempools;
}
}

View File

@ -25,11 +25,13 @@
namespace LibreNMS\OS;
use App\Models\Device;
use App\Models\Mempool;
use LibreNMS\Device\Processor;
use LibreNMS\Interfaces\Discovery\MempoolsDiscovery;
use LibreNMS\Interfaces\Discovery\ProcessorDiscovery;
use LibreNMS\OS;
class Dlinkap extends OS implements ProcessorDiscovery
class Dlinkap extends OS implements MempoolsDiscovery, ProcessorDiscovery
{
public function discoverOS(Device $device): void
{
@ -52,11 +54,29 @@ class Dlinkap extends OS implements ProcessorDiscovery
Processor::discover(
'dlinkap-cpu',
$this->getDeviceId(),
$this->getDeviceArray()['sysObjectID'] . '.5.1.3.0', // different OID for each model
$this->getDevice()->sysObjectID . '.5.1.3.0', // different OID for each model
0,
'Processor',
100
),
];
}
public function discoverMempools()
{
$oid = $this->getDevice()->sysObjectID . '.5.1.4.0';
$memory = snmp_get($this->getDeviceArray(), $oid, '-OQv');
if ($memory === false) {
return collect();
}
return collect()->push((new Mempool([
'mempool_index' => 0,
'mempool_type' => 'dlinkap',
'mempool_class' => 'system',
'mempool_descr' => 'Memory',
'mempool_perc_oid' => $oid,
]))->fillUsage(null, null, null, $memory));
}
}

View File

@ -25,38 +25,49 @@
namespace LibreNMS\OS;
use App\Models\Device;
use App\Models\Mempool;
use Illuminate\Support\Str;
use LibreNMS\Device\Processor;
use LibreNMS\Device\YamlDiscovery;
use LibreNMS\Interfaces\Discovery\MempoolsDiscovery;
use LibreNMS\Interfaces\Discovery\ProcessorDiscovery;
use LibreNMS\OS;
class Edgecos extends OS implements ProcessorDiscovery
class Edgecos extends OS implements MempoolsDiscovery, ProcessorDiscovery
{
public function discoverOS(Device $device): void
public function discoverMempools()
{
if (Str::startsWith($device->sysObjectID, '.1.3.6.1.4.1.259.6.')) { //ES3528M0
$tmp_mib = 'ES3528MO-MIB';
} elseif (Str::startsWith($device->sysObjectID, '.1.3.6.1.4.1.259.10.1.22.')) { //ES3528MV2
$tmp_mib = 'ES3528MV2-MIB';
} elseif (Str::startsWith($device->sysObjectID, '.1.3.6.1.4.1.259.10.1.24.')) { //ECS4510
$tmp_mib = 'ECS4510-MIB';
} elseif (Str::startsWith($device->sysObjectID, '.1.3.6.1.4.1.259.10.1.39.')) { //ECS4110
$tmp_mib = 'ECS4110-MIB';
} elseif (Str::startsWith($device->sysObjectID, '.1.3.6.1.4.1.259.10.1.42.')) { //ECS4210
$tmp_mib = 'ECS4210-MIB';
} elseif (Str::startsWith($device->sysObjectID, '.1.3.6.1.4.1.259.10.1.27.')) { //ECS3510
$tmp_mib = 'ECS3510-MIB';
} elseif (Str::startsWith($device->sysObjectID, '.1.3.6.1.4.1.259.10.1.45.')) { //ECS4120
$tmp_mib = 'ECS4120-MIB';
} elseif (Str::startsWith($device->sysObjectID, '.1.3.6.1.4.1.259.8.1.11')) { //ES3510MA
$tmp_mib = 'ES3510MA-MIB';
} elseif (Str::startsWith($device->sysObjectID, '.1.3.6.1.4.1.259.10.1.43.')) { //ECS2100
$tmp_mib = 'ECS2100-MIB';
} else {
return;
$mib = $this->findMib();
$data = snmp_get_multi_oid($this->getDeviceArray(), ['memoryTotal.0', 'memoryFreed.0', 'memoryAllocated.0'], '-OUQs', $mib);
if (empty($data)) {
return collect();
}
$data = snmp_get_multi($this->getDeviceArray(), ['swOpCodeVer.1', 'swProdName.0', 'swSerialNumber.1', 'swHardwareVer.1'], '-OQUs', $tmp_mib);
$mempool = new Mempool([
'mempool_index' => 0,
'mempool_type' => 'edgecos',
'mempool_class' => 'system',
'mempool_precision' => 1,
'mempool_descr' => 'Memory',
'mempool_perc_warn' => 90,
]);
if ($data['memoryAllocated.0']) {
$mempool->mempool_used_oid = YamlDiscovery::oidToNumeric('memoryAllocated.0', $this->getDeviceArray(), $mib);
} else {
$mempool->mempool_free_oid = YamlDiscovery::oidToNumeric('memoryFreed.0', $this->getDeviceArray(), $mib);
}
$mempool->fillUsage($data['memoryAllocated.0'], $data['memoryTotal.0'], $data['memoryFreed.0']);
return collect([$mempool]);
}
public function discoverOS(Device $device): void
{
$mib = $this->findMib();
$data = snmp_get_multi($this->getDeviceArray(), ['swOpCodeVer.1', 'swProdName.0', 'swSerialNumber.1', 'swHardwareVer.1'], '-OQUs', $mib);
$device->version = trim($data[1]['swHardwareVer'] . ' ' . $data[1]['swOpCodeVer']) ?: null;
$device->hardware = $data[0]['swProdName'] ?? null;
@ -102,4 +113,31 @@ class Edgecos extends OS implements ProcessorDiscovery
return [];
}
/**
* Find the MIB based on sysObjectID
* @return string
*/
protected function findMib(): ?string
{
$table = [
'.1.3.6.1.4.1.259.6.' => 'ES3528MO-MIB',
'.1.3.6.1.4.1.259.10.1.22.' => 'ES3528MV2-MIB',
'.1.3.6.1.4.1.259.10.1.24.' => 'ECS4510-MIB',
'.1.3.6.1.4.1.259.10.1.39.' => 'ECS4110-MIB',
'.1.3.6.1.4.1.259.10.1.42.' => 'ECS4210-MIB',
'.1.3.6.1.4.1.259.10.1.27.' => 'ECS3510-MIB',
'.1.3.6.1.4.1.259.10.1.45.' => 'ECS4120-MIB',
'.1.3.6.1.4.1.259.8.1.11' => 'ES3510MA-MIB',
'.1.3.6.1.4.1.259.10.1.43.' => 'ECS2100-MIB',
];
foreach ($table as $prefix => $mib) {
if (Str::startsWith($this->getDevice()->sysObjectID, $prefix)) {
return $mib;
}
}
return null;
}
}

59
LibreNMS/OS/Enterasys.php Normal file
View File

@ -0,0 +1,59 @@
<?php
/*
* Enterasys.php
*
* -Description-
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
* @package LibreNMS
* @link http://librenms.org
* @copyright 2020 Tony Murray
* @author Tony Murray <murraytony@gmail.com>
*/
namespace LibreNMS\OS;
use App\Models\Mempool;
use LibreNMS\Interfaces\Discovery\MempoolsDiscovery;
class Enterasys extends \LibreNMS\OS implements MempoolsDiscovery
{
public function discoverMempools()
{
$mempools = collect();
$mem = snmpwalk_group($this->getDeviceArray(), 'etsysResourceStorageTable', 'ENTERASYS-RESOURCE-UTILIZATION-MIB', 3);
foreach ($mem as $index => $mem_data) {
foreach ($mem_data['ram'] as $mem_id => $ram) {
$descr = $ram['etsysResourceStorageDescr'];
if ($index > 1000) {
$descr = 'Slot #' . substr($index, -1) . " $descr";
}
$mempools->push((new Mempool([
'mempool_index' => $index,
'mempool_type' => 'enterasys',
'mempool_class' => 'system',
'mempool_descr' => $descr,
'mempool_precision' => 1024,
'mempool_free_oid' => ".1.3.6.1.4.1.5624.1.2.49.1.3.1.1.5.$index.2.$mem_id",
'mempool_perc_warn' => 90,
]))->fillUsage(null, $ram['etsysResourceStorageSize'], $ram['etsysResourceStorageAvailable']));
}
}
return $mempools;
}
}

View File

@ -26,8 +26,11 @@
namespace LibreNMS\OS\Shared;
use App\Models\Device;
use App\Models\Mempool;
use App\Models\PortsNac;
use Illuminate\Support\Arr;
use LibreNMS\Device\Processor;
use LibreNMS\Interfaces\Discovery\MempoolsDiscovery;
use LibreNMS\Interfaces\Discovery\OSDiscovery;
use LibreNMS\Interfaces\Discovery\ProcessorDiscovery;
use LibreNMS\Interfaces\Polling\NacPolling;
@ -35,7 +38,7 @@ use LibreNMS\OS;
use LibreNMS\OS\Traits\YamlOSDiscovery;
use LibreNMS\Util\IP;
class Cisco extends OS implements OSDiscovery, ProcessorDiscovery, NacPolling
class Cisco extends OS implements OSDiscovery, ProcessorDiscovery, MempoolsDiscovery, NacPolling
{
use YamlOSDiscovery {
YamlOSDiscovery::discoverOS as discoverYamlOS;
@ -110,6 +113,92 @@ class Cisco extends OS implements OSDiscovery, ProcessorDiscovery, NacPolling
$device->hardware = $hardware ?: snmp_translate($device->sysObjectID, 'SNMPv2-MIB:CISCO-PRODUCTS-MIB', 'cisco');
}
public function discoverMempools()
{
if ($this->hasYamlDiscovery('mempools')) {
return parent::discoverMempools(); // yaml
}
$mempools = collect();
$cemp = snmpwalk_cache_multi_oid($this->getDeviceArray(), 'cempMemPoolTable', [], 'CISCO-ENHANCED-MEMPOOL-MIB');
foreach (Arr::wrap($cemp) as $index => $entry) {
if (is_numeric($entry['cempMemPoolUsed']) && $entry['cempMemPoolValid'] == 'true') {
[$entPhysicalIndex] = explode('.', $index);
$entPhysicalName = $this->getCacheByIndex('entPhysicalName', 'ENTITY-MIB')[$entPhysicalIndex];
$descr = ucwords($entPhysicalName . ' - ' . $entry['cempMemPoolName']);
$descr = trim(str_replace(['Cisco ', 'Network Processing Engine'], '', $descr), ' -');
$mempools->push((new Mempool([
'mempool_index' => $index,
'entPhysicalIndex' => $entPhysicalIndex,
'mempool_type' => 'cemp',
'mempool_class' => 'system',
'mempool_precision' => 1,
'mempool_descr' => $descr,
'mempool_used_oid' => isset($entry['cempMemPoolHCUsed']) ? ".1.3.6.1.4.1.9.9.221.1.1.1.1.18.$index" : ".1.3.6.1.4.1.9.9.221.1.1.1.1.7.$index",
'mempool_free_oid' => isset($entry['cempMemPoolHCFree']) ? ".1.3.6.1.4.1.9.9.221.1.1.1.1.20.$index" : ".1.3.6.1.4.1.9.9.221.1.1.1.1.8.$index",
'mempool_perc_warn' => 90,
'mempool_largestfree' => $entry['cempMemPoolHCLargestFree'] ?? $entry['cempMemPoolLargestFree'] ?? null,
'mempool_lowestfree' => $entry['cempMemPoolHCLowestFree'] ?? $entry['cempMemPoolLowestFree'] ?? null,
]))->fillUsage($entry['cempMemPoolHCUsed'] ?? $entry['cempMemPoolUsed'], null, $entry['cempMemPoolHCFree'] ?? $entry['cempMemPoolFree']));
}
}
if ($mempools->isNotEmpty()) {
return $mempools;
}
$cmp = snmpwalk_cache_oid($this->getDeviceArray(), 'ciscoMemoryPool', [], 'CISCO-MEMORY-POOL-MIB');
foreach (Arr::wrap($cmp) as $index => $entry) {
if (is_numeric($entry['ciscoMemoryPoolUsed']) && is_numeric($index)) {
$mempools->push((new Mempool([
'mempool_index' => $index,
'mempool_type' => 'cmp',
'mempool_class' => 'system',
'mempool_precision' => 1,
'mempool_descr' => $entry['ciscoMemoryPoolName'],
'mempool_used_oid' => ".1.3.6.1.4.1.9.9.48.1.1.1.5.$index",
'mempool_free_oid' => ".1.3.6.1.4.1.9.9.48.1.1.1.6.$index",
'mempool_perc_warn' => 90,
'mempool_largestfree' => $entry['ciscoMemoryPoolLargestFree'] ?? null,
]))->fillUsage($entry['ciscoMemoryPoolUsed'], null, $entry['ciscoMemoryPoolFree']));
}
}
if ($mempools->isNotEmpty()) {
return $mempools;
}
$cpm = $this->getCacheTable('cpmCPUTotalTable', 'CISCO-PROCESS-MIB');
$count = 0;
foreach (Arr::wrap($cpm) as $index => $entry) {
$count++;
if (is_numeric($entry['cpmCPUMemoryFree']) && is_numeric($entry['cpmCPUMemoryFree'])) {
$cpu = $this->getCacheByIndex('entPhysicalName', 'ENTITY-MIB')[$entry['cpmCPUTotalPhysicalIndex'] ?? 'none'] ?? "Processor $index";
$mempools->push((new Mempool([
'mempool_index' => $index,
'mempool_type' => 'cpm',
'mempool_class' => 'system',
'mempool_precision' => 1024,
'mempool_descr' => "$cpu Memory",
'mempool_used_oid' => empty($entry['cpmCPUMemoryHCUsed']) ? ".1.3.6.1.4.1.9.9.109.1.1.1.1.12.$index" : ".1.3.6.1.4.1.9.9.109.1.1.1.1.17.$index",
'mempool_free_oid' => empty($entry['cpmCPUMemoryHCFree']) ? ".1.3.6.1.4.1.9.9.109.1.1.1.1.13.$index" : ".1.3.6.1.4.1.9.9.109.1.1.1.1.19.$index",
'mempool_perc_warn' => 90,
'mempool_lowestfree' => $entry['cpmCPUMemoryHCLowest'] ?? $entry['cpmCPUMemoryLowest'] ?? null,
]))->fillUsage(
empty($entry['cpmCPUMemoryHCUsed']) ? $entry['cpmCPUMemoryUsed'] : $entry['cpmCPUMemoryHCUsed'],
null,
empty($entry['cpmCPUMemoryHCFree']) ? $entry['cpmCPUMemoryFree'] : $entry['cpmCPUMemoryHCFree']
));
}
}
return $mempools;
}
/**
* Discover processors.
* Returns an array of LibreNMS\Device\Processor objects that have been discovered
@ -118,7 +207,8 @@ class Cisco extends OS implements OSDiscovery, ProcessorDiscovery, NacPolling
*/
public function discoverProcessors()
{
$processors_data = snmpwalk_group($this->getDeviceArray(), 'cpmCPU', 'CISCO-PROCESS-MIB');
$processors_data = $this->getCacheTable('cpmCPUTotalTable', 'CISCO-PROCESS-MIB');
$processors_data = snmpwalk_group($this->getDeviceArray(), 'cpmCoreTable', 'CISCO-PROCESS-MIB', 1, $processors_data);
$processors = [];
foreach ($processors_data as $index => $entry) {
@ -132,17 +222,8 @@ class Cisco extends OS implements OSDiscovery, ProcessorDiscovery, NacPolling
continue; // skip bad data
}
$entPhysicalIndex = $entry['cpmCPUTotalPhysicalIndex'];
if ($entPhysicalIndex) {
if ($this->isCached('entPhysicalName')) {
$entPhysicalName_array = $this->getCacheByIndex('entPhysicalName', 'ENTITY-MIB');
$descr = $entPhysicalName_array[$entPhysicalIndex];
}
if (empty($descr)) {
$descr = snmp_get($this->getDeviceArray(), 'entPhysicalName.' . $entPhysicalIndex, '-Oqv', 'ENTITY-MIB');
}
if (isset($entry['cpmCPUTotalPhysicalIndex'])) {
$descr = $this->getCacheByIndex('entPhysicalName', 'ENTITY-MIB')[$entry['cpmCPUTotalPhysicalIndex']];
}
if (empty($descr)) {
@ -161,7 +242,7 @@ class Cisco extends OS implements OSDiscovery, ProcessorDiscovery, NacPolling
1,
$core_usage,
null,
$entPhysicalIndex
$entry['cpmCPUTotalPhysicalIndex']
);
}
} else {
@ -174,7 +255,7 @@ class Cisco extends OS implements OSDiscovery, ProcessorDiscovery, NacPolling
1,
$usage,
null,
$entPhysicalIndex
$entry['cpmCPUTotalPhysicalIndex']
);
}
}
@ -202,17 +283,7 @@ class Cisco extends OS implements OSDiscovery, ProcessorDiscovery, NacPolling
$qfp_usage = $entry['fiveMinute'];
if ($entQfpPhysicalIndex) {
if ($this->isCached('entPhysicalName')) {
$entPhysicalName_array = $this->getCacheByIndex('entPhysicalName', 'ENTITY-MIB');
$qfp_descr = $entPhysicalName_array[$entQfpPhysicalIndex];
}
if (empty($qfp_descr)) {
$qfp_descr = snmp_get($this->getDeviceArray(), 'entPhysicalName.' . $entQfpPhysicalIndex, '-Oqv', 'ENTITY-MIB');
}
}
if (empty($qfp_descr)) {
$qfp_desc = "QFP $entQfpPhysicalIndex";
$qfp_descr = $this->getCacheByIndex('entPhysicalName', 'ENTITY-MIB')[$entQfpPhysicalIndex];
}
$processors[] = Processor::discover(
@ -220,7 +291,7 @@ class Cisco extends OS implements OSDiscovery, ProcessorDiscovery, NacPolling
$this->getDeviceId(),
$qfp_usage_oid,
$entQfpPhysicalIndex . '.3',
$qfp_descr,
$qfp_descr ?? "QFP $entQfpPhysicalIndex",
1,
$qfp_usage,
null,

View File

@ -27,10 +27,11 @@ namespace LibreNMS\OS\Shared;
use App\Models\Device;
use Illuminate\Support\Str;
use LibreNMS\Interfaces\Discovery\MempoolsDiscovery;
use LibreNMS\OS\Traits\ServerHardware;
use LibreNMS\OS\Traits\YamlOSDiscovery;
class Unix extends \LibreNMS\OS
class Unix extends \LibreNMS\OS implements MempoolsDiscovery
{
use ServerHardware;
use YamlOSDiscovery {

View File

@ -24,10 +24,41 @@
namespace LibreNMS\OS\Traits;
use App\Models\Mempool;
use Closure;
use Exception;
use Illuminate\Support\Str;
use LibreNMS\Device\Processor;
trait HostResources
{
private $hrStorage;
private $memoryStorageTypes = [
'hrStorageVirtualMemory',
'hrStorageRam',
'hrStorageOther',
];
private $ignoreMemoryDescr = [
'MALLOC',
'UMA',
'procfs',
'/proc',
];
private $validOtherMemory = [
'Memory buffers',
'Cached memory',
'Shared memory',
];
private $memoryDescrWarn = [
'Cached memory' => 0,
'Memory buffers' => 0,
'Physical memory' => 99,
'Real memory' => 90,
'Shared memory' => 0,
'Swap space' => 10,
'Virtual memory' => 95,
];
/**
* Discover processors.
* Returns an array of LibreNMS\Device\Processor objects that have been discovered
@ -48,7 +79,7 @@ trait HostResources
}
$hrDeviceDescr = $this->getCacheByIndex('hrDeviceDescr', 'HOST-RESOURCES-MIB');
} catch (\Exception $e) {
} catch (Exception $e) {
return [];
}
@ -107,4 +138,52 @@ trait HostResources
return $processors;
}
public function discoverMempools()
{
$hr_storage = $this->getCacheTable('hrStorageTable', 'HOST-RESOURCES-MIB:HOST-RESOURCES-TYPES');
if (! is_array($hr_storage)) {
return collect();
}
$ram_bytes = snmp_get($this->getDeviceArray(), 'hrMemorySize.0', '-OQUv', 'HOST-RESOURCES-MIB') * 1024
?: (isset($hr_storage[1]['hrStorageSize']) ? $hr_storage[1]['hrStorageSize'] * $hr_storage[1]['hrStorageAllocationUnits'] : 0);
return collect($hr_storage)->filter(Closure::fromCallable([$this, 'memValid']))
->map(function ($storage, $index) use ($ram_bytes) {
$total = $storage['hrStorageSize'];
if (Str::contains($storage['hrStorageDescr'], 'Real Memory Metrics') || ($storage['hrStorageType'] == 'hrStorageOther' && $total != 0)) {
// use total RAM for buffers, cached, and shared
// bsnmp does not report the same as net-snmp, total RAM is stored in hrMemorySize
if ($ram_bytes) {
$total = $ram_bytes / $storage['hrStorageAllocationUnits']; // will be calculated with this entries allocation units later
}
}
return (new Mempool([
'mempool_index' => $index,
'mempool_type' => 'hrstorage',
'mempool_precision' => $storage['hrStorageAllocationUnits'],
'mempool_descr' => $storage['hrStorageDescr'],
'mempool_perc_warn' => $this->memoryDescrWarn[$storage['hrStorageDescr']] ?? 90,
'mempool_used_oid' => ".1.3.6.1.2.1.25.2.3.1.6.$index",
'mempool_total_oid' => null,
]))->setClass($storage['hrStorageType'] == 'hrStorageVirtualMemory' ? 'virtual' : null)
->fillUsage($storage['hrStorageUsed'], $total);
});
}
protected function memValid($storage)
{
if (! in_array($storage['hrStorageType'], $this->memoryStorageTypes)) {
return false;
}
if ($storage['hrStorageType'] == 'hrStorageOther' && ! in_array($storage['hrStorageDescr'], $this->validOtherMemory)) {
return false;
}
return ! Str::contains($storage['hrStorageDescr'], $this->ignoreMemoryDescr);
}
}

View File

@ -24,6 +24,7 @@
namespace LibreNMS\OS\Traits;
use App\Models\Mempool;
use LibreNMS\Device\Processor;
trait UcdResources
@ -49,4 +50,80 @@ trait UcdResources
),
];
}
public function discoverMempools()
{
$mempools = collect();
$data = snmp_get_multi($this->getDeviceArray(), [
'memTotalSwap.0',
'memAvailSwap.0',
'memTotalReal.0',
'memAvailReal.0',
'memBuffer.0',
'memCached.0',
'memSysAvail.0',
], '-OQUs', 'UCD-SNMP-MIB');
if ($this->oidValid($data, 'memTotalReal') && ($this->oidValid($data, 'memAvailReal') || $this->oidValid($data, 'memSysAvail'))) {
$mempools->push((new Mempool([
'mempool_index' => 1,
'mempool_type' => 'ucd',
'mempool_class' => 'system',
'mempool_precision' => 1024,
'mempool_descr' => 'Physical memory',
'mempool_free_oid' => '.1.3.6.1.4.1.2021.4.6.0',
]))->fillUsage(null, $data[0]['memTotalReal'], $data[0]['memAvailReal'] + $data[0]['memBuffer'] + $data[0]['memCached']));
}
if ($this->oidValid($data, 'memTotalSwap') && $this->oidValid($data, 'memAvailSwap')) {
$mempools->push((new Mempool([
'mempool_index' => 2,
'mempool_type' => 'ucd',
'mempool_class' => 'swap',
'mempool_precision' => 1024,
'mempool_descr' => 'Swap space',
'mempool_free_oid' => '.1.3.6.1.4.1.2021.4.4.0',
]))->fillUsage(null, $data[0]['memTotalSwap'], $data[0]['memAvailSwap']));
}
if ($this->oidValid($data, 'memBuffer')) {
$mempools->push((new Mempool([
'mempool_index' => 3,
'mempool_type' => 'ucd',
'mempool_class' => 'buffers',
'mempool_precision' => 1024,
'mempool_descr' => 'Memory buffers',
'mempool_used_oid' => '.1.3.6.1.4.1.2021.4.14.0',
]))->fillUsage(null, $data[0]['memTotalReal'], $data[0]['memBuffer']));
}
if ($this->oidValid($data, 'memCached')) {
$mempools->push((new Mempool([
'mempool_index' => 4,
'mempool_type' => 'ucd',
'mempool_class' => 'cached',
'mempool_precision' => 1024,
'mempool_descr' => 'Cached memory',
'mempool_used_oid' => '.1.3.6.1.4.1.2021.4.15.0',
]))->fillUsage(null, $data[0]['memTotalReal'], $data[0]['memCached']));
}
if ($this->oidValid($data, 'memSysAvail')) {
$mempools->push((new Mempool([
'mempool_index' => 5,
'mempool_type' => 'ucd',
'mempool_class' => 'available',
'mempool_precision' => 1024,
'mempool_descr' => 'Available memory',
'mempool_free_oid' => '.1.3.6.1.4.1.2021.4.27.0',
]))->fillUsage(null, $data[0]['memTotalReal'], $data[0]['memSysAvail']));
}
return $mempools;
}
private function oidValid($data, $oid)
{
return isset($data[0][$oid]) && $data[0][$oid] !== 'NULL';
}
}

View File

@ -0,0 +1,150 @@
<?php
/*
* YamlMempoolsDiscovery.php
*
* -Description-
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
* @package LibreNMS
* @link http://librenms.org
* @copyright 2020 Tony Murray
* @author Tony Murray <murraytony@gmail.com>
*/
namespace LibreNMS\OS\Traits;
use App\Models\Mempool;
use LibreNMS\Device\YamlDiscovery;
trait YamlMempoolsDiscovery
{
private $mempoolsData = [];
private $mempoolsOids = [];
private $mempoolsFields = [
'total',
'free',
'used',
'percent_used',
];
private $mempoolsPrefetch = [];
public function discoverYamlMempools()
{
$mempools = collect();
$mempools_yaml = $this->getDiscovery('mempools');
foreach ($mempools_yaml['pre-cache']['oids'] ?? [] as $oid) {
$options = $mempools_yaml['pre-cache']['snmp_flags'] ?? '-OQUb';
$this->mempoolsPrefetch = snmpwalk_cache_oid($this->getDeviceArray(), $oid, $this->mempoolsPrefetch, null, null, $options);
}
foreach ($mempools_yaml['data'] as $yaml) {
$this->fetchData($yaml, $this->getDiscovery()['mib'] ?? 'ALL');
$snmp_data = array_replace_recursive($this->mempoolsPrefetch, $this->mempoolsData);
$count = 1;
foreach ($this->mempoolsData as $index => $data) {
if (YamlDiscovery::canSkipItem(null, $index, $yaml, [], $data)) {
echo 's';
continue;
}
$used = $this->getData('used', $index, $yaml);
$total = $this->getData('total', $index, $yaml);
$mempool = (new Mempool([
'mempool_index' => isset($yaml['index']) ? YamlDiscovery::replaceValues('index', $index, $count, $yaml, $snmp_data) : $index,
'mempool_type' => $yaml['type'] ?? $this->getName(),
'mempool_class' =>$yaml['class'] ?? 'system',
'mempool_precision' => $yaml['precision'] ?? 1,
'mempool_descr' => isset($yaml['descr']) ? ucwords(YamlDiscovery::replaceValues('descr', $index, $count, $yaml, $snmp_data)) : 'Memory',
'mempool_used_oid' => $this->getOid('used', $index, $yaml),
'mempool_free_oid' => ($used === null || $total === null) ? $this->getOid('free', $index, $yaml) : null, // only use "free" if we have both used and total
'mempool_perc_oid' => $this->getOid('percent_used', $index, $yaml),
'mempool_perc_warn' => isset($yaml['warn_percent']) ? YamlDiscovery::replaceValues('warn_percent', $index, $count, $yaml, $snmp_data) : 90,
]))->fillUsage(
$used,
$total,
$this->getData('free', $index, $yaml),
$this->getData('percent_used', $index, $yaml)
);
if ($mempool->mempool_total) {
$mempools->push($mempool);
$count++;
}
}
}
return $mempools;
}
private function getData($field, $index, $yaml)
{
$oid = $yaml[$field];
if (isset($this->mempoolsData[$index][$oid])) {
return $this->mempoolsData[$index][$oid];
}
if (isset($this->mempoolsPrefetch[$index][$oid])) {
return $this->mempoolsPrefetch[$index][$oid];
}
return is_numeric($yaml[$field]) ? $yaml[$field] : null; // hard coded number
}
private function getOid($field, $index, $yaml)
{
if (YamlDiscovery::oidIsNumeric($yaml[$field])) {
return $yaml[$field];
}
if (isset($this->mempoolsOids[$field])) {
return YamlDiscovery::oidToNumeric("{$this->mempoolsOids[$field]}.$index", $this->getDeviceArray());
}
return null;
}
/**
* @param array $yaml item yaml definition
* @param string $mib
* @throws \LibreNMS\Exceptions\InvalidOidException
*/
private function fetchData($yaml, $mib)
{
$this->mempoolsOids = [];
$this->mempoolsData = []; // clear data from previous mempools
$options = $yaml['snmp_flags'] ?? '-OQUb';
if (isset($yaml['oid'])) {
$this->mempoolsData = snmpwalk_cache_oid($this->getDeviceArray(), $yaml['oid'], $this->mempoolsData, null, null, $options);
}
foreach ($this->mempoolsFields as $field) {
$oid = $yaml[$field];
if (isset($oid) && ! is_numeric($oid)) { // allow for hard-coded values
if (YamlDiscovery::oidIsNumeric($oid)) { // if numeric oid, it is not a table, just fetch it
$this->mempoolsData[0][$oid] = snmp_get($this->getDeviceArray(), $oid, '-Oqv');
continue;
}
if (empty($yaml['oid'])) { // if table given, skip individual oids
$this->mempoolsData = snmpwalk_cache_oid($this->getDeviceArray(), $oid, $this->mempoolsData, null, null, $options);
}
$this->mempoolsOids[$field] = YamlDiscovery::oidToNumeric($oid, $this->getDeviceArray(), $mib);
}
}
}
}

View File

@ -31,14 +31,14 @@ use Log;
trait YamlOSDiscovery
{
private $dbFields = [
private $osDbFields = [
'version',
'hardware',
'features',
'serial',
];
private $fields = [
private $osFields = [
'version',
'hardware',
'features',
@ -48,8 +48,7 @@ trait YamlOSDiscovery
public function discoverOS(Device $device): void
{
$yaml = $this->getDiscovery();
$os_yaml = $yaml['modules']['os'] ?? [];
$os_yaml = $this->getDiscovery('os');
if (isset($os_yaml['sysDescr_regex'])) {
$this->parseRegex($os_yaml['sysDescr_regex'], $device->sysDescr);
@ -59,7 +58,7 @@ trait YamlOSDiscovery
$this->translateSysObjectID($os_yaml['hardware_mib'], $os_yaml['hardware_regex'] ?? null);
}
$oids = Arr::only($os_yaml, $this->fields);
$oids = Arr::only($os_yaml, $this->osFields);
$fetch_oids = array_unique(Arr::flatten($oids));
$numeric = $this->isNumeric($fetch_oids);
$flags = $numeric ? '-OUQn' : '-OUQ';
@ -106,7 +105,7 @@ trait YamlOSDiscovery
foreach (Arr::wrap($regexes) as $regex) {
if (preg_match($regex, $subject, $matches)) {
foreach ($this->dbFields as $field) {
foreach ($this->osDbFields as $field) {
if (isset($matches[$field])) {
$device->$field = $matches[$field];
}

View File

@ -25,10 +25,13 @@
namespace LibreNMS\OS;
use App\Models\Device;
use App\Models\Mempool;
use App\Models\PortsNac;
use Illuminate\Support\Arr;
use Illuminate\Support\Str;
use LibreNMS\Device\Processor;
use LibreNMS\Device\WirelessSensor;
use LibreNMS\Interfaces\Discovery\MempoolsDiscovery;
use LibreNMS\Interfaces\Discovery\OSDiscovery;
use LibreNMS\Interfaces\Discovery\ProcessorDiscovery;
use LibreNMS\Interfaces\Discovery\Sensors\WirelessApCountDiscovery;
@ -39,6 +42,7 @@ use LibreNMS\OS;
use LibreNMS\RRD\RrdDefinition;
class Vrp extends OS implements
MempoolsDiscovery,
OSPolling,
ProcessorDiscovery,
NacPolling,
@ -46,6 +50,35 @@ class Vrp extends OS implements
WirelessClientsDiscovery,
OSDiscovery
{
public function discoverMempools()
{
$mempools = collect();
$mempools_array = snmpwalk_cache_multi_oid($this->getDeviceArray(), 'hwEntityMemUsage', [], 'HUAWEI-ENTITY-EXTENT-MIB', 'huawei');
$mempools_array = snmpwalk_cache_multi_oid($this->getDeviceArray(), 'hwEntityMemSize', $mempools_array, 'HUAWEI-ENTITY-EXTENT-MIB', 'huawei');
$mempools_array = snmpwalk_cache_multi_oid($this->getDeviceArray(), 'hwEntityBomEnDesc', $mempools_array, 'HUAWEI-ENTITY-EXTENT-MIB', 'huawei');
$mempools_array = snmpwalk_cache_multi_oid($this->getDeviceArray(), 'hwEntityMemSizeMega', $mempools_array, 'HUAWEI-ENTITY-EXTENT-MIB', 'huawei');
$mempools_array = snmpwalk_cache_multi_oid($this->getDeviceArray(), 'entPhysicalName', $mempools_array, 'HUAWEI-ENTITY-EXTENT-MIB', 'huawei');
foreach (Arr::wrap($mempools_array) as $index => $entry) {
$size = empty($entry['hwEntityMemSizeMega']) ? $entry['hwEntityMemSize'] : $entry['hwEntityMemSizeMega'];
$descr = empty($entry['entPhysicalName']) ? $entry['hwEntityBomEnDesc'] : $entry['entPhysicalName'];
if ($size != 0 && $descr && ! Str::contains($descr, 'No') && ! Str::contains($entry['hwEntityMemUsage'], 'No')) {
$mempools->push((new Mempool([
'mempool_index' => $index,
'mempool_type' => 'vrp',
'mempool_class' => 'system',
'mempool_precision' => empty($entry['hwEntityMemSizeMega']) ? 1 : 1048576,
'mempool_descr' => substr("$descr Memory", 0, 64),
'mempool_perc_oid' => ".1.3.6.1.4.1.2011.5.25.31.1.1.1.1.7.$index",
'mempool_perc_warn' => 90,
]))->fillUsage(null, $size, null, $entry['hwEntityMemUsage']));
}
}
return $mempools;
}
public function discoverOS(Device $device): void
{
parent::discoverOS($device); // yaml

View File

@ -38,6 +38,7 @@ class Colors
return [
'left' => 'c4323f',
'right' => 'c96a73',
'middle' => 'c75862',
];
}
@ -45,6 +46,7 @@ class Colors
return [
'left' => 'bf5d5b',
'right' => 'd39392',
'middle' => 'c97e7d',
];
}
@ -52,6 +54,7 @@ class Colors
return [
'left' => 'bf875b',
'right' => 'd3ae92',
'middle' => 'cca07e',
];
}
@ -59,12 +62,14 @@ class Colors
return [
'left' => '5b93bf',
'right' => '92b7d3',
'middle' => '7da8c9',
];
}
return [
'left' => '9abf5b',
'right' => 'bbd392',
'middle' => 'afcc7c',
];
}
}

View File

@ -134,24 +134,32 @@ class Html
return $graph_data;
}
public static function percentageBar($width, $height, $percent, $left_text, $left_colour, $left_background, $right_text, $right_colour, $right_background)
public static function percentageBar($width, $height, $percent, $left_text = '', $right_text = '', $warn = null, $shadow = null, $colors = null)
{
if ($percent > '100') {
$size_percent = '100';
} else {
$size_percent = $percent;
$percent = min($percent, 100);
if ($colors === null) {
$colors = Colors::percentage($percent, $warn ?: null);
}
$default = Colors::percentage(0);
$left_text_color = $colors['left_text'] ?? 'ffffff';
$right_text_color = $colors['right_text'] ?? 'ffffff';
$left_color = $colors['left'] ?? $default['left'];
$right_color = $colors['right'] ?? $default['right'];
$output = '<div style="width:' . $width . 'px; height:' . $height . 'px; position: relative;">
<div class="progress" style="min-width: 2em; background-color:#' . $right_color . '; height:' . $height . 'px;margin-bottom:-' . $height . 'px;">';
if ($shadow !== null) {
$shadow = min($shadow, 100);
$middle_color = $colors['middle'] ?? $default['middle'];
$output .= '<div class="progress-bar" role="progressbar" aria-valuenow="' . $shadow . '" aria-valuemin="0" aria-valuemax="100" style="min-width: 2em; width:' . $shadow . '%; background-color: #' . $middle_color . ';">';
}
$output = '
<div style="width:' . $width . 'px; height:' . $height . 'px; position: relative;">
<div class="progress" style="min-width: 2em; background-color:#' . $right_background . '; height:' . $height . 'px;margin-bottom:-' . $height . 'px;">
<div class="progress-bar" role="progressbar" aria-valuenow="' . $size_percent . '" aria-valuemin="0" aria-valuemax="100" style="min-width: 2em; width:' . $size_percent . '%; background-color: #' . $left_background . ';">
</div>
</div>
<b style="padding-left: 2%; position: absolute; top: 0; left: 0;color:#' . $left_colour . ';">' . $left_text . '</b>
<b style="padding-right: 2%; position: absolute; top: 0; right: 0;color:#' . $right_colour . ';">' . $right_text . '</b>
</div>
';
$output .= '<div class="progress-bar" role="progressbar" aria-valuenow="' . $percent . '" aria-valuemin="0" aria-valuemax="100" style="min-width: 2em; width:' . $percent . '%; background-color: #' . $left_color . ';">
</div></div>
<b style="padding-left: 2%; position: absolute; top: 0; left: 0;color:#' . $left_text_color . ';">' . $left_text . '</b>
<b style="padding-right: 2%; position: absolute; top: 0; right: 0;color:#' . $right_text_color . ';">' . $right_text . '</b>
</div>';
return $output;
}

86
LibreNMS/Util/Number.php Normal file
View File

@ -0,0 +1,86 @@
<?php
/*
* Number.php
*
* -Description-
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
* @package LibreNMS
* @link http://librenms.org
* @copyright 2020 Tony Murray
* @author Tony Murray <murraytony@gmail.com>
*/
namespace LibreNMS\Util;
class Number
{
public static function formatBase($value, $base = 1000, $round = 2, $sf = 3, $suffix = 'B')
{
return $base == 1000
? self::formatSi($value, $round, $sf, $suffix)
: self::formatBi($value, $round, $sf, $suffix);
}
public static function formatSi($value, $round = 2, $sf = 3, $suffix = 'B')
{
$neg = $value < 0;
if ($neg) {
$value = $value * -1;
}
if ($value >= '0.1') {
$sizes = ['', 'K', 'M', 'G', 'T', 'P', 'E', 'Z', 'Y'];
$ext = $sizes[0];
for ($i = 1; (($i < count($sizes)) && ($value >= 1000)); $i++) {
$value = $value / 1000;
$ext = $sizes[$i];
}
} else {
$sizes = ['', 'm', 'u', 'n', 'p'];
$ext = $sizes[0];
for ($i = 1; (($i < count($sizes)) && ($value != 0) && ($value <= 0.1)); $i++) {
$value = $value * 1000;
$ext = $sizes[$i];
}
}
if ($neg) {
$value = $value * -1;
}
return (number_format(round($value, $round), $sf, '.', '') + 0) . " $ext$suffix";
}
public static function formatBi($value, $round = 2, $sf = 3, $suffix = 'B')
{
$neg = $value < 0;
if ($neg) {
$value = $value * -1;
}
$sizes = ['', 'Ki', 'Mi', 'Gi', 'Ti', 'Pi', 'Ei', 'Zi', 'Yi'];
$ext = $sizes[0];
for ($i = 1; (($i < count($sizes)) && ($value >= 1024)); $i++) {
$value = $value / 1024;
$ext = $sizes[$i];
}
if ($neg) {
$value = $value * -1;
}
return (number_format(round($value, $round), $sf, '.', '') + 0) . " $ext$suffix";
}
}

View File

@ -410,34 +410,4 @@ class Rewrite
{
return str_pad($num, $length, '0', STR_PAD_LEFT);
}
public static function formatStorage($value, int $round = 2, int $sf = 3): string
{
$value = self::format_bi($value, $round, $sf) . 'B';
return $value;
}
public static function format_bi($value, int $round = 2, int $sf = 3): string
{
$neg = false;
$sizes = ['', 'k', 'M', 'G', 'T', 'P', 'E'];
$ext = $sizes[0];
if ($value < 0) {
$neg = true;
$value = $value * -1;
}
for ($i = 1; (($i < count($sizes)) && ($value >= 1024)); $i++) {
$value = $value / 1024;
$ext = $sizes[$i];
}
if ($neg) {
$value = $value * -1;
}
return (number_format(round($value, $round), $sf, '.', '') + 0) . ' ' . $ext;
}
}

View File

@ -315,33 +315,33 @@ class Url
return '<img src="' . url('graph.php') . '?' . implode('&amp;', $urlargs) . '" style="border:0;" />';
}
public static function graphPopup($args)
public static function graphPopup($args, $content = null, $link = null)
{
// Take $args and print day,week,month,year graphs in overlib, hovered over graph
$original_from = $args['from'];
$now = CarbonImmutable::now();
$graph = self::graphTag($args);
$content = '<div class=list-large>' . $args['popup_title'] . '</div>';
$content .= '<div style="width: 850px">';
$graph = $content ?: self::graphTag($args);
$popup = '<div class=list-large>' . $args['popup_title'] . '</div>';
$popup .= '<div style="width: 850px">';
$args['width'] = 340;
$args['height'] = 100;
$args['legend'] = 'yes';
$args['from'] = $now->subDay()->timestamp;
$content .= self::graphTag($args);
$popup .= self::graphTag($args);
$args['from'] = $now->subWeek()->timestamp;
$content .= self::graphTag($args);
$popup .= self::graphTag($args);
$args['from'] = $now->subMonth()->timestamp;
$content .= self::graphTag($args);
$popup .= self::graphTag($args);
$args['from'] = $now->subYear()->timestamp;
$content .= self::graphTag($args);
$content .= '</div>';
$popup .= self::graphTag($args);
$popup .= '</div>';
$args['from'] = $original_from;
$args['link'] = self::generate($args, ['page' => 'graphs', 'height' => null, 'width' => null, 'bg' => null]);
$args['link'] = $link ?: self::generate($args, ['page' => 'graphs', 'height' => null, 'width' => null, 'bg' => null]);
return self::overlibLink($args['link'], $graph, $content, null);
return self::overlibLink($args['link'], $graph, $popup, null);
}
public static function lazyGraphTag($args)

View File

@ -26,6 +26,7 @@ namespace App\Http\Controllers\Device\Tabs;
use App\Models\Device;
use LibreNMS\Interfaces\UI\DeviceTab;
use Session;
class OverviewController implements DeviceTab
{
@ -53,4 +54,24 @@ class OverviewController implements DeviceTab
{
return [];
}
public static function setGraphWidth($graph = [])
{
// possibly the wrong spot for this
if ($screen_width = Session::get('screen_width')) {
if ($screen_width > 970) {
$graph['width'] = round(($screen_width - 390) / 2, 0);
$graph['height'] = round($graph['width'] / 3);
$graph['lazy_w'] = $graph['width'] + 80;
return $graph;
}
$graph['width'] = $screen_width - 190;
$graph['height'] = round($graph['width'] / 3);
$graph['lazy_w'] = $graph['width'] + 80;
}
return $graph;
}
}

View File

@ -0,0 +1,133 @@
<?php
/*
* MempoolsController.php
*
* -Description-
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
* @package LibreNMS
* @link http://librenms.org
* @copyright 2020 Tony Murray
* @author Tony Murray <murraytony@gmail.com>
*/
namespace App\Http\Controllers\Table;
use App\Models\Device;
use App\Models\Mempool;
use Illuminate\Support\Arr;
use LibreNMS\Config;
use LibreNMS\Util\Html;
use LibreNMS\Util\Number;
use LibreNMS\Util\Url;
class MempoolsController extends TableController
{
protected function searchFields($request)
{
return ['hostname', 'mempool_descr'];
}
protected function sortFields($request)
{
return ['mempool_descr', 'mempool_perc', 'mempool_used', 'hostname'];
}
/**
* {@inheritdoc}
*/
protected function baseQuery($request)
{
if ($request->get('view') == 'graphs') {
return Device::query()->has('mempools')->with('mempools');
}
$query = Mempool::query()->with('device');
// join devices table to sort by hostname or search
if (array_key_exists('hostname', $request->get('sort', $this->default_sort)) || $request->get('searchPhrase')) {
$query->join('devices', 'mempools.device_id', 'devices.device_id')
->select('mempools.*');
}
return $query;
}
public function formatItem($mempool)
{
if ($mempool instanceof Device) {
$device = $mempool;
$graphs = \LibreNMS\Util\Html::graphRow([
'device' => $device->device_id,
'type' => 'device_mempool',
'height' => 100,
'width' => 216,
]);
return [
'hostname' => Url::deviceLink($device),
'mempool_descr' => $graphs[0],
'graph' => $graphs[1],
'mempool_used' => $graphs[2],
'mempool_perc' => $graphs[3],
];
}
/** @var Mempool $mempool */
return [
'hostname' => Url::deviceLink($mempool->device),
'mempool_descr' => $mempool->mempool_descr,
'graph' => $this->miniGraph($mempool),
'mempool_used' => $this->barLink($mempool),
'mempool_perc' => $mempool->mempool_perc . '%',
];
}
private function miniGraph(Mempool $mempool)
{
$graph = [
'type' => 'mempool_usage',
'id' => $mempool->mempool_id,
'from' => Config::get('time.day'),
'height' => 20,
'width' => 80,
];
$link = Url::generate(['page' => 'graphs'], Arr::only($graph, ['id', 'type', 'from']));
return Url::overlibLink($link, Url::lazyGraphTag($graph), Url::graphTag(['height' => 150, 'width' => 400] + $graph));
}
private function barLink(Mempool $mempool)
{
$graph = [
'type' => 'mempool_usage',
'id' => $mempool->mempool_id,
'from' => Config::get('time.day'),
'height' => 150,
'width' => 400,
];
$is_percent = $mempool->mempool_total == 100;
$free = $is_percent ? $mempool->mempool_free : Number::formatBi($mempool->mempool_free);
$used = $is_percent ? $mempool->mempool_used : Number::formatBi($mempool->mempool_used);
$total = $is_percent ? $mempool->mempool_total : Number::formatBi($mempool->mempool_total);
$percent = Html::percentageBar(400, 20, $mempool->mempool_perc, "$used / $total", $free, $mempool->mempool_perc_warn);
$link = Url::generate(['page' => 'graphs'], Arr::only($graph, ['id', 'type', 'from']));
return Url::overlibLink($link, $percent, Url::graphTag($graph));
}
}

View File

@ -35,7 +35,6 @@ use Illuminate\Database\Eloquent\Builder;
use Illuminate\Http\Request;
use Illuminate\Support\Collection;
use Illuminate\View\View;
use LibreNMS\Util\Colors;
use LibreNMS\Util\Html;
use LibreNMS\Util\StringHelpers;
use LibreNMS\Util\Url;
@ -311,15 +310,12 @@ class TopDevicesController extends WidgetController
unset($link_array['height'], $link_array['width'], $link_array['legend']);
$link = Url::generate($link_array);
$percent = $storage->storage_perc;
$background = Colors::percentage($percent, $storage->storage_perc_warn);
return [
Url::deviceLink($device, $device->shortDisplayName()),
StringHelpers::shortenText($storage->storage_descr, 50),
Url::overlibLink(
$link,
Html::percentageBar(150, 20, $percent, null, 'ffffff', $background['left'], $percent . '%', 'ffffff', $background['right']),
Html::percentageBar(150, 20, $storage->storage_perc, '', $storage->storage_perc . '%', $storage->storage_perc_warn),
$overlib_content
),
];

View File

@ -2,9 +2,176 @@
namespace App\Models;
class Mempool extends DeviceRelatedModel
use Illuminate\Support\Str;
use LibreNMS\Interfaces\Models\Keyable;
class Mempool extends DeviceRelatedModel implements Keyable
{
protected $table = 'mempools';
protected $primaryKey = 'mempool_id';
public $timestamps = false;
protected $fillable = [
'mempool_perc_warn',
'mempool_index',
'entPhysicalIndex',
'mempool_type',
'mempool_class',
'mempool_precision',
'mempool_descr',
'mempool_perc',
'mempool_perc_oid',
'mempool_used',
'mempool_used_oid',
'mempool_free',
'mempool_free_oid',
'mempool_total',
'mempool_total_oid',
'mempool_largestfree',
'mempool_lowestfree',
];
protected $attributes = [
'mempool_precision' => 1,
];
public function __construct(array $attributes = [])
{
parent::__construct($attributes);
if (! $this->exists) {
// only allow mempool_perc_warn to be filled for new mempools
unset($this->fillable[array_search('mempool_perc_warn', $this->fillable)]);
}
}
public function isValid()
{
return $this->mempool_total > 0;
}
public function fillUsage($used = null, $total = null, $free = null, $percent = null)
{
try {
$total = $this->correctNegative($total);
$used = $this->correctNegative($used, $total);
$free = $this->correctNegative($free, $total);
} catch (\Exception $e) {
d_echo($e->getMessage());
return $this; // unhandled negative
}
$this->mempool_total = $this->calculateTotal($total, $used, $free);
$this->mempool_used = $used * $this->mempool_precision;
$this->mempool_free = $free * $this->mempool_precision;
$percent = $this->normalizePercent($percent); // don't assign to model or it loses precision
$this->mempool_perc = $percent;
if (! $this->mempool_total) {
if (! $percent && $percent !== '0') {
// could not calculate total, can't calculate other values
return $this;
}
$this->mempool_total = 100; // only have percent, mark total as 100
}
if ($used === null) {
$this->mempool_used = $free !== null
? $this->mempool_total - $this->mempool_free
: round($this->mempool_total * ($percent ? ($percent / 100) : 0));
}
if ($free === null) {
$this->mempool_free = $used !== null
? $this->mempool_total - $this->mempool_used
: round($this->mempool_total * ($percent ? (1 - ($percent / 100)) : 1));
}
if ($percent == null) {
$this->mempool_perc = $this->mempool_used / $this->mempool_total * 100;
}
return $this;
}
/**
* Set the mempool class. If no class is given, try to detect it from available data.
*
* @param null $class
* @return \App\Models\Mempool
*/
public function setClass($class = null)
{
if ($class) {
$this->mempool_class = $class;
return $this;
}
$memoryClasses = [
'virtual' => ['virtual'],
'swap' => ['swap'],
'buffers' => ['buffers'],
'cached' => ['cache'],
'system' => ['shared real memory metrics'],
'shared' => ['shared'],
];
$descr = strtolower($this->mempool_descr);
foreach ($memoryClasses as $class => $search) {
if (Str::contains($descr, $search)) {
$this->mempool_class = $class;
return $this;
}
}
$this->mempool_class = 'system'; // just call everything else system
return $this;
}
public function setMempoolPercAttribute($percent)
{
$this->attributes['mempool_perc'] = round($percent);
}
public function getCompositeKey()
{
return "$this->mempool_type-$this->mempool_index";
}
private function correctNegative($value, $max = null)
{
$int_max = 4294967296;
if ($value < 0) {
// assume unsigned/signed issue
$value = $int_max + $value;
if (($max && $value > $max) || $value > $int_max) {
throw new \Exception('Uncorrectable negative value');
}
}
return $value;
}
private function calculateTotal($total, $used, $free)
{
if ($total !== null) {
return $total * $this->mempool_precision;
}
if ($used !== null && $free !== null) {
return ($used + $free) * $this->mempool_precision;
}
return $this->mempool_total; // don't change the value it may have been set in discovery
}
private function normalizePercent($percent)
{
while ($percent > 100) {
$percent = $percent / 10;
}
return $percent;
}
}

View File

@ -8,6 +8,7 @@ use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Relations\HasOne;
use Illuminate\Support\Str;
use LibreNMS\Util\Html;
use LibreNMS\Util\Number;
use LibreNMS\Util\Rewrite;
class Vminfo extends DeviceRelatedModel
@ -24,7 +25,7 @@ class Vminfo extends DeviceRelatedModel
public function getMemoryFormattedAttribute(): string
{
return Rewrite::formatStorage($this->vmwVmMemSize * 1024 * 1024);
return Number::formatBi($this->vmwVmMemSize * 1024 * 1024);
}
public function getOperatingSystemAttribute(): string

View File

@ -13,9 +13,6 @@ class RemoveConfigDefinitionFromDb extends Migration
*/
public function up()
{
// $schema = new \Thedevsaddam\LaravelSchema\Schema\Schema();
// dd($schema->databaseWrapper->getColumns('config'));
Schema::table('config', function (Blueprint $table) {
$table->dropColumn([
'config_default',

View File

@ -28,7 +28,6 @@ class DeviceGroupsRewrite extends Migration
*/
public function down()
{
// dd(Schema::getColumnListing('device_groups'), \LibreNMS\DB\Eloquent::getDriver());
// Schema::table('device_groups', function (Blueprint $table) {
// $table->string('desc')->change();
// $table->dropColumn(['type', 'rules']);

View File

@ -0,0 +1,45 @@
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class MempoolsAddOids extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::table('mempools', function (Blueprint $table) {
$table->dropColumn('hrDeviceIndex');
$table->string('mempool_class', 32)->default('system')->after('mempool_type');
$table->string('mempool_descr', 128)->change();
$table->string('mempool_perc_oid')->after('mempool_perc')->nullable();
$table->string('mempool_used_oid')->after('mempool_used')->nullable();
$table->string('mempool_free_oid')->after('mempool_free')->nullable();
$table->string('mempool_total_oid')->after('mempool_total')->nullable();
});
// rediscover mempools to fill empty columns and prevent gaps
DB::table('devices')->whereIn('device_id', function ($query) {
$query->from('mempools')->distinct()->select('device_id');
})->update(['last_discovered' => null]);
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
Schema::table('mempools', function (Blueprint $table) {
$table->string('mempool_descr', 64)->change();
$table->integer('hrDeviceIndex')->nullable()->after('entPhysicalIndex');
$table->dropColumn(['mempool_class', 'mempool_perc_oid', 'mempool_used_oid', 'mempool_free_oid', 'mempool_total_oid']);
});
}
}

View File

@ -6,31 +6,87 @@ Processor for your new device.
#### Memory
Detection for memory is done via two php scripts, one for discovery
and the other for polling:
LibreNMS will attempt to detect memory statistics using the standard HOST-RESOURCES-MIB and UCD-SNMP-MIB MIBs.
To detect non-standard MIBs, they can be defined via Yaml.
`includes/discovery/mempools/pulse.inc.php`
##### YAML
```php
<?php
echo 'PULSE-MEMORY-POOL: ';
$usage = str_replace('"', "", snmp_get($device, 'iveMemoryUtil.0', '-OvQ', 'PULSESECURE-PSG-MIB'));
if (is_numeric($usage)) {
discover_mempool($valid_mempool, $device, 0, 'pulse-mem', 'Main Memory', '100', null, null);
}
In order to successfully detect memory amount and usage, two of the for keys below are required. Some OS only
provide a usage percentage, which will work, but a total RAM amount will not be displayed.
- total
- used
- free
- percent_used
`includes/definitions/discovery/mempools/arubaos.yaml`
```yaml
mempools:
data:
-
total: WLSX-SWITCH-MIB::sysXMemorySize
used: WLSX-SWITCH-MIB::sysXMemoryUsed
precision: 1024
```
`includes/polling/mempools/pulse.inc.php`
The code can also interpret table based OIDs and supports many of the same features as Health Sensors
including {{ }} parsing, skip_values, and precache.
Valid data entry keys:
- `oid` oid to walk to collect processor data
- `total` oid or integer total memory size in bytes (or precision),
- `used` oid memory used in bytes (or precision)
- `free` oid memory free in bytes (or precision)
- `percent_used` oid of percentage of used memory
- `descr` A visible description of the memory measurement defaults to "Memory"
- `warn_percent` Usage percentage to used for alert purposes
- `precision` precision for all byte values, typically a power of 2 (1024 for example)
- `class`used to generate rrd filename, defaults to system. If system, buffers, and cached exist they
will be combined to calculate available memory.
- `type` used to generate rrd filename, defaults to the os name
- `index` used to generate rrd filename, defaults to the oid index
- `skip_values` skip values see [Health Sensors](../Developing/os/Health-Information.md) for specification
- `snmp_flags` additional net-snmp flags
##### Custom Processor Discovery and Polling
If you need to implement custom discovery or polling you can implement
the MempoolsDiscovery interface and the MempoolsPolling interface in the OS class.
MempoolsPolling is optional, standard polling will be used based on OIDs stored in the database.
OS Class files reside under `LibreNMS\OS`
```php
<?php
echo 'Pulse Secure MemPool\n';
$perc = str_replace('"', "", snmp_get($device, "iveMemoryUtil.0", '-OvQ', 'PULSESECURE-PSG-MIB'));
if (is_numeric($perc)) {
$memory_available = str_replace('"', "", snmp_get($device, "memTotalReal.0", '-OvQ', 'UCD-SNMP-MIB'));
$mempool['total'] = $memory_available;
$mempool['used'] = ($memory_available / 100 * $perc);
$mempool['free'] = ($memory_available - $mempool['used']);
namespace LibreNMS\OS;
use LibreNMS\Interfaces\Discovery\MempoolsDiscovery;
use LibreNMS\Interfaces\Polling\MempoolsPolling;
class Example extends \LibreNMS\OS implements MempoolsDiscovery, MempoolsPolling
{
/**
* Discover a Collection of Mempool models.
* Will be keyed by mempool_type and mempool_index
*
* @return \Illuminate\Support\Collection \App\Models\Mempool
*/
public function discoverMempools()
{
// TODO: Implement discoverMempools() method.
}
/**
* @param \Illuminate\Support\Collection $mempools \App\Models\Mempool
* @return \Illuminate\Support\Collection \App\Models\Mempool
*/
public function pollMempools($mempools)
{
// TODO: Implement pollMempools() method.
}
}
```
@ -75,7 +131,7 @@ Accessing values within yaml:
| {{ $count }} | The count of entries (starting with 1) |
| {{ $`oid` }} | Any oid in the table or pre-fetched |
##### Custom Discovery and Polling
##### Custom Processor Discovery and Polling
If you need to implement custom discovery or polling you can implement
the ProcessorDiscovery interface and the ProcessorPolling interface in the OS class.

View File

@ -489,52 +489,22 @@ function formatRates($value, $round = '2', $sf = '3')
function formatStorage($value, $round = '2', $sf = '3')
{
return \LibreNMS\Util\Rewrite::formatStorage($value, $round, $sf);
return \LibreNMS\Util\Number::formatBi($value, $round, $sf);
}
function format_si($value, $round = '2', $sf = '3')
function format_si($value, $round = 2, $sf = 3)
{
$neg = 0;
if ($value < '0') {
$neg = 1;
$value = $value * -1;
}
if ($value >= '0.1') {
$sizes = ['', 'k', 'M', 'G', 'T', 'P', 'E'];
$ext = $sizes[0];
for ($i = 1; (($i < count($sizes)) && ($value >= 1000)); $i++) {
$value = $value / 1000;
$ext = $sizes[$i];
}
} else {
$sizes = ['', 'm', 'u', 'n', 'p'];
$ext = $sizes[0];
for ($i = 1; (($i < count($sizes)) && ($value != 0) && ($value <= 0.1)); $i++) {
$value = $value * 1000;
$ext = $sizes[$i];
}
}
if ($neg == 1) {
$value = $value * -1;
}
return (number_format(round($value, $round), $sf, '.', '') + 0) . ' ' . $ext;
return \LibreNMS\Util\Number::formatSi($value, $round, $sf, '');
}
function format_bi($value, $round = '2', $sf = '3')
function format_bi($value, $round = 2, $sf = 3)
{
return \LibreNMS\Util\Rewrite::format_bi($value, $round, $sf);
return \LibreNMS\Util\Number::formatBi($value, $round, $sf, '');
}
function format_number($value, $base = '1000', $round = 2, $sf = 3)
function format_number($value, $base = 1000, $round = 2, $sf = 3)
{
if ($base == '1000') {
return format_si($value, $round, $sf);
} else {
return format_bi($value, $round, $sf);
}
return \LibreNMS\Util\Number::formatBase($value, $base, $round, $sf, '');
}
function is_valid_hostname($hostname)

View File

@ -7,7 +7,7 @@ ifXmcbc: true
ifname: true
over:
- { graph: device_processor, text: 'Processor Usage' }
- { graph: device_ucd_memory, text: 'Memory Usage' }
- { graph: device_mempool, text: 'Memory Usage' }
- { graph: device_storage, text: 'Storage Usage' }
poller_modules:
bgp-peers: false

View File

@ -6,7 +6,7 @@ icon: coreos
processor_stacked: true
over:
- { graph: device_processor, text: 'Processor Usage' }
- { graph: device_ucd_memory, text: 'Memory Usage' }
- { graph: device_mempool, text: 'Memory Usage' }
discovery:
-
sysDescr_regex: '/^Linux.*coreos/'

View File

@ -6,7 +6,7 @@ icon: dell
processor_stacked: true
over:
- { graph: device_processor, text: 'Processor Usage' }
- { graph: device_ucd_memory, text: 'Memory Usage' }
- { graph: device_mempool, text: 'Memory Usage' }
- { graph: device_storage, text: 'Storage Usage' }
poller_modules:
applications: false

View File

@ -6,7 +6,7 @@ ifXmcbc: true
ifname: true
over:
- { graph: device_processor, text: 'Processor Usage' }
- { graph: device_ucd_memory, text: 'Memory Usage' }
- { graph: device_mempool, text: 'Memory Usage' }
- { graph: device_storage, text: 'Storage Usage' }
discovery:
-

View File

@ -1,5 +1,11 @@
mib: A3COM-HUAWEI-LswDEVM-MIB
modules:
mempools:
data:
-
free: A3COM-HUAWEI-LswDEVM-MIB::hwMemFree
total: A3COM-HUAWEI-LswDEVM-MIB::hwMemSize
index: 0
processors:
data:
-

View File

@ -1,5 +1,12 @@
mib: A10-AX-MIB
modules:
mempools:
data:
-
total: A10-AX-MIB::axSysMemoryTotal
used: A10-AX-MIB::axSysMemoryUsage
precision: 1024
descr: 'System Memory'
os:
sysDescr_regex: '/(?<hardware>\S+( TPS)?), ACOS (?<version>[^,]+)/'
serial: A10-AX-MIB::axSysSerialNumber.0

View File

@ -1,5 +1,10 @@
mib: ADTRAN-AOSCPU
modules:
mempools:
data:
-
total: ADTRAN-AOSCPU::adGenAOSMemPool
free: ADTRAN-AOSCPU::adGenAOSHeapFree
os:
hardware: ADTRAN-AOSUNIT::adAOSDeviceProductName.0
serial: ADTRAN-AOSUNIT::adAOSDeviceSerialNumber.0

View File

@ -1,5 +1,11 @@
mib: ALTEON-CHEETAH-SWITCH-MIB
modules:
mempools:
data:
-
total: ALTEON-CHEETAH-SWITCH-MIB::mpMemStatsTotal
free: ALTEON-CHEETAH-SWITCH-MIB::mpMemStatsFree
descr: 'Main Memory'
os:
features: ALTEON-CHEETAH-SWITCH-MIB::agEnabledSwFeatures.0
hardware:

View File

@ -1,5 +1,12 @@
mib: ALCATEL-IND1-CHASSIS-MIB:ALCATEL-IND1-HEALTH-MIB:ALCATEL-IND1-PORT-MIB
modules:
mempools:
data:
-
total: ALCATEL-IND1-SYSTEM-MIB::systemHardwareMemorySize
percent_used: ALCATEL-IND1-HEALTH-MIB::healthDeviceMemoryLatest
descr: 'Device Memory'
os:
sysDescr_regex: '/(?<hardware>OS\S*)? ?(?<version>\d+\.\d+\.\S*)/'
processors:

View File

@ -1,5 +1,17 @@
mib: ALCATEL-IND1-CHASSIS-MIB:ALCATEL-IND1-HEALTH-MIB:ALCATEL-IND1-PORT-MIB
modules:
mempools:
data:
-
total: ALCATEL-IND1-SYSTEM-MIB::systemHardwareMemorySize
percent_used: ALCATEL-IND1-HEALTH-MIB::healthModuleMemory1MinAvg
precision: 1024
descr: 'Device Memory'
skip_values:
-
oid: ALCATEL-IND1-SYSTEM-MIB::systemHardwareMemorySize
op: '<='
value: 0
os:
sysDescr_regex: '/(?<hardware>OS\S+)? ?(?<version>\d+\.\d+\.\S+)/'
processors:

View File

@ -1,3 +1,14 @@
modules:
mempools:
pre-cache:
oids:
- AI-AP-MIB::aiAPSerialNum
- AI-AP-MIB::aiAPName
data:
-
total: AI-AP-MIB::aiAPTotalMemory
free: AI-AP-MIB::aiAPMemoryFree
index: '{{ AI-AP-MIB::aiAPSerialNum }}'
descr: '{{ AI-AP-MIB::aiAPName }} [{{ AI-AP-MIB::aiAPSerialNum }}]'
os:
sysDescr_regex: '/\(MODEL: (?<hardware>\S+)\), Version (?<version>\S+)/'

View File

@ -2,6 +2,15 @@ mib: ARUBA-MIB:WLSX-SYSTEMEXT-MIB
modules:
os:
sysDescr_regex: '/(\(MODEL: (?<hardware>.+)\),)? Version (?<version>\S+)/'
mempools:
data:
-
total: WLSX-SWITCH-MIB::sysXMemorySize
used: WLSX-SWITCH-MIB::sysXMemoryUsed
free: WLSX-SWITCH-MIB::sysXMemoryFree
precision: 1024
type: arubaos
index: 0
processors:
data:
-

View File

@ -1,5 +1,10 @@
mib: BDCOM-PROCESS-MIB
modules:
mempools:
data:
-
used: BDCOM-MEMORY-POOL-MIB::bdcomMemoryPoolUsed
free: BDCOM-MEMORY-POOL-MIB::bdcomMemoryPoolFree
processors:
data:
-

View File

@ -1,5 +1,11 @@
mib: BENU-HOST-MIB
modules:
mempools:
data:
-
total: BENU-HOST-MIB::bSysTotalMem
used: BENU-HOST-MIB::bSysMemUsed
precision: 1024
processors:
data:
-

View File

@ -1,5 +1,10 @@
mib: PRVT-SYS-MON-MIB
modules:
mempools:
data:
-
used: PRVT-SYS-INFO-MIB::numBytesAlloc
free: PRVT-SYS-INFO-MIB::numBytesFree
processors:
data:
-

View File

@ -1,5 +1,9 @@
mib: PRVT-INTERWORKING-OS-MIB:PRVT-SYS-MON-MIB
modules:
mempools:
data:
-
percent_used: PRVT-SYS-MON-MIB::prvtSysMonCurrentRamUsage
os:
hardware: PRVT-SWITCH-MIB::sysPartNumber.0
serial: PRVT-SWITCH-MIB::sysSerialNumber.0

View File

@ -0,0 +1,10 @@
modules:
mempools:
data:
-
total: S5-CHASSIS-MIB::s5ChasUtilMemoryTotalMB
free: S5-CHASSIS-MIB::s5ChasUtilMemoryAvailableMB
descr: 'Unit {{ $count }} Memory'
precision: 1048576
index: '.{{ $index }}'
type: avaya-ers

View File

@ -1,5 +1,10 @@
mib: FD-SYSTEM-MIB:CDATA-EPON-MIB:NSCRTV-FTTX-EPON-MIB:NSCRTV-PON-TREE-EXT-MIB
modules:
mempools:
data:
-
total: NSCRTV-PON-TREE-EXT-MIB::memTotalSize
free: NSCRTV-PON-TREE-EXT-MIB::memFreeSize
os:
hardware:
- .1.3.6.1.4.1.17409.2.3.1.3.1.1.7.1.0

View File

@ -1,5 +1,11 @@
mib: AIRESPACE-SWITCHING-MIB
modules:
mempools:
data:
-
free: AIRESPACE-SWITCHING-MIB::agentFreeMemory
total: AIRESPACE-SWITCHING-MIB::agentTotalMemory
precision: 1024
processors:
data:
-

View File

@ -1,5 +1,18 @@
mib: CYBEROAM-MIB
modules:
mempools:
data:
-
total: CYBEROAM-MIB::memoryCapacity
percent_used: CYBEROAM-MIB::memoryPercentUsage
precision: 1048576
index: 0
-
total: CYBEROAM-MIB::swapCapacity
percent_used: CYBEROAM-MIB::swapPercentUsage
precision: 1048576
descr: Swap
index: 1
os:
hardware: CYBEROAM-MIB::applianceModel.0
version: CYBEROAM-MIB::cyberoamVersion.0

View File

@ -1,5 +1,12 @@
mib: DASAN-SWITCH-MIB
modules:
mempools:
data:
-
total: DASAN-SWITCH-MIB::dsTotalMem
used: DASAN-SWITCH-MIB::dsUsedMem
free: DASAN-SWITCH-MIB::dsFreeMem
descr: 'Memory Utilization'
os:
sysDescr_regex: '#(?<hardware>.+) NOS (?<version>[^/]+)#'
serial: DASAN-SWITCH-MIB::dsSerialNumber.0

View File

@ -1,5 +1,11 @@
mib: DCN-MIB
modules:
mempools:
data:
-
total: DCN-MIB::switchMemorySize
used: DCN-MIB::switchMemoryBusy
descr: 'Memory Usage'
os:
hardware:
- DCN-MIB::ntpEntSoftwareName.0

View File

@ -1,5 +1,18 @@
mib: EQUIPMENT-MIB:DLINKSW-ENTITY-EXT-MIB
modules:
mempools:
data:
-
percent_used: AGENT-GENERAL-MIB::agentDRAMutilization
index: 0
-
oid: DLINKSW-ENTITY-EXT-MIB::dEntityExtMemoryUtilTable
total: dEntityExtMemUtilTotal
used: dEntityExtMemUtilUsed
free: dEntityExtMemUtilFree
descr: '{{ $subindex1 }} Memory'
snmp_flags: '-OQUs'
os:
sysDescr_regex: '/(D-Link )?(?<hardware>\S+) (?<version>[0-9.]+)?/'
version:

View File

@ -1,5 +1,20 @@
mib: DELL-NETWORKING-CHASSIS-MIB:DELL-NETWORKING-IF-EXTENSION-MIB
modules:
mempools:
pre-cache:
snmp_flags: '-OQUs'
oids:
- DELL-NETWORKING-CHASSIS-MIB::dellNetProcessorTable
data:
-
snmp_flags: '-OQUs'
oid: DELL-NETWORKING-CHASSIS-MIB::dellNetCpuUtilTable
total: dellNetProcessorMemSize
percent_used: dellNetCpuUtilMemUsage
precision: 1048576
type: dell-net
descr: 'Memory Usage'
os:
sysDescr_regex:
- '/Software Version: (?<version>\S+)/'

View File

@ -1,7 +0,0 @@
mib: ECS4510-MIB
modules:
processors:
data:
-
oid: cpuCurrentUti
num_oid: '.1.3.6.1.4.1.259.10.1.24.1.39.2.1.{{ $index }}'

View File

@ -1,5 +1,11 @@
mib: EdgeSwitch-BOXSERVICES-PRIVATE-MIB
modules:
mempools:
data:
-
total: EdgeSwitch-SWITCHING-MIB::agentSwitchCpuProcessMemAvailable
free: EdgeSwitch-SWITCHING-MIB::agentSwitchCpuProcessMemFree
precision: 1024
os:
sysDescr_regex: '/^(?<hardware>EdgeSwitch .*|EdgePoint Switch .*|USW-.*), (?<version>.*), Linux .*$/'
serial: ENTITY-MIB::entPhysicalSerialNum.1

View File

@ -0,0 +1,7 @@
modules:
mempools:
data:
-
used: F5-BIGIP-SYSTEM-MIB::sysStatMemoryUsed
total: F5-BIGIP-SYSTEM-MIB::sysStatMemoryTotal
descr: 'TMM Memory'

View File

@ -1,5 +1,9 @@
mib: SW-MIB
modules:
mempools:
data:
-
percent_used: SW-MIB::swMemUsage
processors:
data:
-

View File

@ -1,5 +1,12 @@
mib: WRI-CPU-MIB:WRI-TEMPERATURE-MIB:WRI-VOLTAGE-MIB:FAN-MIB:WRI-POWER-MIB:WRI-DEVICE-MIB
modules:
mempools:
data:
-
oid: WRI-MEMORY-MIB::memoryPoolTable
total: WRI-MEMORY-MIB::memoryPoolTotalBytes
used: WRI-MEMORY-MIB::memoryPoolAllocBytesNum
descr: WRI-MEMORY-MIB::memoryPoolIndexDescr
os:
sysDescr_regex: '/(?<hardware>.*) \(R\) Software, Version (?<version>[^ ,]+),Hw Version (?<features>[^ ,]+)/'
# version: WRI-DEVICE-MIB::msppDevSwVersion.0

View File

@ -1,5 +1,17 @@
mib: GEPON-OLT-COMMON-MIB
modules:
mempools:
data:
-
oid: GEPON-OLT-COMMON-MIB::mgrCardInfoTable
percent_used: GEPON-OLT-COMMON-MIB::mgrCardMemUtil
total: 268435456
descr: 'Hswa {{ $index }} Memory'
skip_values:
-
oid: GEPON-OLT-COMMON-MIB::mgrCardWorkStatus
op: '!='
value: 1
os:
sysDescr_regex: '/(?<hardware>.*)/'
version: GEPON-OLT-COMMON-MIB::sysSoftVersion.0

View File

@ -1,5 +1,12 @@
mib: FORTINET-FORTIGATE-MIB
modules:
mempools:
data:
-
total: FORTINET-FORTIGATE-MIB::fgSysMemCapacity
percent_used: FORTINET-FORTIGATE-MIB::fgSysMemUsage
precision: 1024
descr: 'Main Memory'
os:
version: FORTINET-FORTIGATE-MIB::fgSysVersion.0
serial: ENTITY-MIB::entPhysicalSerialNum.1

View File

@ -1,5 +1,10 @@
mib: FORTINET-FORTIMAIL-MIB
modules:
mempools:
data:
-
percent_used: FORTINET-FORTIMAIL-MIB::fmlSysMemUsage
descr: 'Physical Memory'
os:
hardware: FORTINET-FORTIMAIL-MIB::fmlSysModel.0
version: FORTINET-FORTIMAIL-MIB::fmlSysVersion.0

View File

@ -1,4 +1,11 @@
modules:
mempools:
data:
-
total: FORTINET-FORTIMANAGER-FORTIANALYZER-MIB::fmSysMemCapacity
used: FORTINET-FORTIMANAGER-FORTIANALYZER-MIB::fmSysMemUsed
precision: 1024
descr: 'Main Memory'
os:
version: FORTINET-FORTIMANAGER-FORTIANALYZER-MIB::fmSysVersion.0
serial:

View File

@ -1,5 +1,12 @@
mib: FORTINET-FORTISANDBOX-MIB
modules:
mempools:
data:
-
total: FORTINET-FORTISANDBOX-MIB::fsaSysMemCapacity
percent_used: FORTINET-FORTISANDBOX-MIB::fsaSysMemUsage
precision: 1024
descr: 'Physical Memory'
os:
version: FORTINET-FORTISANDBOX-MIB::fsaSysVersion.0
hardware: ENTITY-MIB::entPhysicalModelName.1

View File

@ -1,5 +1,12 @@
mib: FORTINET-FORTISWITCH-MIB
modules:
mempools:
data:
-
total: FORTINET-FORTISWITCH-MIB::fsSysMemCapacity
used: FORTINET-FORTISWITCH-MIB::fsSysMemUsage
descr: 'Main Memory'
precision: 1024
os:
serial:
- FORTINET-CORE-MIB::fnSysSerial.0

View File

@ -1,5 +1,12 @@
mib: FORTINET-FORTIWEB-MIB
modules:
mempools:
data:
-
total: FORTINET-FORTIWEB-MIB::fwSysMemCapacity
percent_used: FORTINET-FORTIWEB-MIB::fwSysMemUsage
precision: 1048576
descr: 'Physical Memory'
os:
serial:
- FORTINET-CORE-MIB::fnSysSerial.0

View File

@ -1,4 +1,14 @@
modules:
mempools:
pre-cache:
oids:
- GBNPlatformOAM-MIB::cpuDescription
data:
-
total: GBNPlatformOAM-MIB::memorySize
free: GBNPlatformOAM-MIB::memoryIdle
precision: 1048576
descr: '{{ GBNPlatformOAM-MIB::cpuDescription }} Memory'
os:
hardware: GBNPlatformOAM-MIB::productName.0
version: GBNPlatformOAM-MIB::softwareVersion.0

View File

@ -1,5 +1,13 @@
mib: FS-MIB
modules:
mempools:
data:
-
total: SWITCH::memTotalReal
free: SWITCH::memTotalFree
used: SWITCH::memTotalUsed
precision: 1024
descr: 'Chassis Memory'
os:
hardware:
- SWITCH::lswSlotCurrentType.1.1

View File

@ -1,3 +1,20 @@
modules:
mempools:
data:
-
total: F10-CHASSIS-MIB::chSysProcessorMemSize
percent_used: F10-CHASSIS-MIB::chRpmMemUsageUtil
-
total: F10-S-SERIES-CHASSIS-MIB::chSysProcessorMemSize
percent_used: F10-S-SERIES-CHASSIS-MIB::chStackUnitMemUsageUtil
-
total: F10-C-SERIES-CHASSIS-MIB::chSysProcessorMemSize
percent_used: F10-C-SERIES-CHASSIS-MIB::chSysProcessorMemSize
-
total: F10-M-SERIES-CHASSIS-MIB::chSysProcessorMemSize
percent_used: F10-M-SERIES-CHASSIS-MIB::chSysProcessorMemSize
-
total: F10-Z-SERIES-CHASSIS-MIB::chSysProcessorMemSize
percent_used: F10-Z-SERIES-CHASSIS-MIB::chSysCpuUtilMemUsage
os:
sysDescr_regex: '/Application Software Version: (?<version>[\d.]+\d)/'

View File

@ -1,5 +1,12 @@
mib: GW-EPON-DEV-MIB:GWTT-SMI:GW-EPON-MIB
modules:
mempools:
data:
-
total: .1.3.6.1.4.1.10072.2.20.1.1.2.1.1.28.1.1
used: .1.3.6.1.4.1.10072.2.20.1.1.2.1.1.20.1.1
index: 0
precision: 1048576
os:
hardware: .1.3.6.1.4.1.10072.2.20.1.1.1.1.1.9.1
serial: .1.3.6.1.4.1.10072.2.20.1.1.2.1.1.18.1.1

View File

@ -1,5 +1,11 @@
mib: HIK-DEVICE-MIB:HIKVISION-MIB
modules:
mempools:
data:
-
total: HIK-DEVICE-MIB::memSize
percent_used: HIK-DEVICE-MIB::memUsed
precision: 1048576
os:
hardware: HIK-DEVICE-MIB::deviceType.0
version: HIK-DEVICE-MIB::softwVersion.0

View File

@ -1,4 +1,10 @@
modules:
mempools:
data:
-
total: HIKVISION-MIB::hikMemoryCapability
percent_used: HIKVISION-MIB::hikMemoryUsage
precision: 1048576
os:
hardware: HIKVISION-MIB::hikEntityType.0
serial: HIKVISION-MIB::hikEntityIndex.0

View File

@ -1,5 +1,16 @@
mib: HMPRIV-MGMT-SNMP-MIB
modules:
mempools:
data:
-
used: HMPRIV-MGMT-SNMP-MIB::hmMemoryAllocated
free: HMPRIV-MGMT-SNMP-MIB::hmMemoryFree
descr: 'Main Memory'
precision: 1024
os:
hardware: HMPRIV-MGMT-SNMP-MIB::hmPNIOOrderID.0
version: HMPRIV-MGMT-SNMP-MIB::hmPNIOSoftwareRelease.0
serial: HMPRIV-MGMT-SNMP-MIB::hmSysGroupSerialNum.1
processors:
data:
-

View File

@ -1,5 +1,9 @@
mib: AH-SYSTEM-MIB
modules:
mempools:
data:
-
percent_used: AH-SYSTEM-MIB::ahMemUtilization
os:
sysDescr_regex: '/^(?<hardware>.*), HiveOS (?<version>.*)$/'
hardware: AH-SYSTEM-MIB::ahDeviceMode.0

View File

@ -1,5 +1,20 @@
mib: CPQHLTH-MIB:CPQIDA-MIB:CPQSTDEQ-MIB:CPQHOST-MIB
modules:
mempools:
data:
-
total: CPQHOST-MIB::cpqHoPhysicalMemorySize
free: CPQHOST-MIB::cpqHoPhysicalMemoryFree
index: 0
precision: 1048576
descr: 'Physical Memory'
-
total: CPQHOST-MIB::cpqHoPagingMemorySize
free: CPQHOST-MIB::cpqHoPagingMemoryFree
index: 1
precision: 1048576
descr: 'Paging Memory'
os:
sysDescr_regex: '/Integrated Lights-Out \d (?<version>[\d.]+)/'
hardware: CPQSINFO-MIB::cpqSiProductName.0

View File

@ -1,5 +1,12 @@
mib: COLUBRIS-USAGE-INFORMATION-MIB
modules:
mempools:
data:
-
total: COLUBRIS-USAGE-INFORMATION-MIB::coUsInfoRamTotal
free: COLUBRIS-USAGE-INFORMATION-MIB::coUsInfoRamFree
precision: 1024
descr: 'Memory Utilization'
os:
sysDescr_regex: '/(?<hardware>MSM\S+) .* Serial number (?<serial>\S+) - Firmware version (?<version>\S+)/'
processors:

View File

@ -1,5 +1,12 @@
mib: ZYXEL-IES5000-MIB
modules:
mempools:
data:
-
oid: ZYXEL-IES5000-MIB::memoryUsageTable
percent_used: ZYXEL-IES5000-MIB::memoryCurValue
descr: ZYXEL-IES5000-MIB::memoryDescr
warn_percent: ZYXEL-IES5000-MIB::memoryHighThresh
os:
serial: .1.3.6.1.4.1.890.1.5.13.5.6.2.1.3.0
version:

View File

@ -1,5 +1,13 @@
mib: IES5206-MIB
modules:
mempools:
data:
-
oid: IES5206-MIB::memStatsTable
percent_used: IES5206-MIB::memStatsCurrent
descr: 'Memory {{ $index }}'
type: ies52xxM-mem
warn_percent: IES5206-MIB::memStatsHighThreshold
os:
hardware: IES5206-MIB::sysProductDescr.0
serial: IES5206-MIB::sysSerialNumber.0

View File

@ -1,3 +1,9 @@
modules:
mempools:
data:
-
total: FROGFOOT-RESOURCES-MIB::memTotal
free: FROGFOOT-RESOURCES-MIB::memFree
precision: 1024
os:
sysDescr_regex: '/(?<hardware>NFT \S+)( (?<version>.*))?/'

View File

@ -1,5 +1,10 @@
mib: IONODES-IONSERIES-MIB
modules:
mempools:
data:
-
percent_used: IONODES-IONSERIES-MIB::ionSysMemUsage
descr: 'System Memory'
processors:
data:
-

View File

@ -1,5 +1,25 @@
mib: FOUNDRY-SN-AGENT-MIB:FOUNDRY-SN-SWITCH-GROUP-MIB:FOUNDRY-SN-STACKING-MIB
modules:
mempools:
pre-cache:
oids:
- FOUNDRY-SN-AGENT-MIB::snAgentBrdMainBrdDescription
data:
# -
# total: FOUNDRY-SN-AGENT-MIB::snAgGblDynMemTotal
# free: FOUNDRY-SN-AGENT-MIB::snAgGblDynMemFree
# type: ironware-dyn
# descr: 'Dynamic Memory'
-
total: FOUNDRY-SN-AGENT-MIB::snAgSystemDRAMTotal
free: FOUNDRY-SN-AGENT-MIB::snAgSystemDRAMFree
descr: 'System Memory'
type: ironware-system
-
total: FOUNDRY-SN-AGENT-MIB::snAgentBrdMemoryTotal
percent_used: FOUNDRY-SN-AGENT-MIB::snAgentBrdMemoryUtil100thPercent
type: ironware-dyn
descr: '{{ FOUNDRY-SN-AGENT-MIB::snAgentBrdMainBrdDescription }}'
os:
hardware_mib: FOUNDRY-SN-ROOT-MIB
sysDescr_regex: '/IronWare Version V(?<version>.*) Compiled on/'

View File

@ -1,5 +1,10 @@
mib: TPLINK-SYSMONITOR-MIB
modules:
mempools:
data:
-
percent_used: TPLINK-SYSMONITOR-MIB::tpSysMonitorMemoryUtilization
descr: 'Memory #{{ $index }}'
processors:
data:
-

View File

@ -1,5 +1,11 @@
mib: TRAPEZE-NETWORKS-SYSTEM-MIB
modules:
mempools:
data:
-
total: TRAPEZE-NETWORKS-SYSTEM-MIB::trpzSysCpuMemorySize
used: TRAPEZE-NETWORKS-SYSTEM-MIB::trpzSysCpuMemoryInstantUsage
precision: 1024
os:
sysDescr_regex: '/Juniper Networks, Inc (?<hardware>\S+) (?<version>\S+)/'
processors:

View File

@ -1,9 +1,21 @@
mib: JUNIPER-IFOPTICS-MIB:JNX-OPT-IF-EXT-MIB:IF-MIB:JUNIPER-MIB:JUNIPER-SRX5000-SPU-MONITORING-MIB:JUNIPER-ALARM-MIB:JUNIPER-VIRTUALCHASSIS-MIB:JUNIPER-VIRTUALCHASSIS-MIB:JUNIPER-RPM-MIB
modules:
mempools:
data:
-
oid: JUNIPER-MIB::jnxOperatingTable
total: JUNIPER-MIB::jnxOperatingDRAMSize
percent_used: JUNIPER-MIB::jnxOperatingBuffer
descr: '{{ JUNIPER-MIB::jnxOperatingDescr }}'
skip_values:
-
oid: JUNIPER-MIB::jnxOperatingDRAMSize
op: '='
value: 0
processors:
data:
-
oid: jnxOperatingEntry
oid: jnxOperatingTable
value: jnxOperatingCPU
num_oid: '.1.3.6.1.4.1.2636.3.1.13.1.8.{{ $index }}'
descr: jnxOperatingDescr

View File

@ -1,5 +1,39 @@
mib: IF-MIB
modules:
mempools:
data:
-
total: MOXA-IKS6726A-MIB::totalMemory
used: MOXA-IKS6726A-MIB::usedMemory
free: MOXA-IKS6726A-MIB::freeMemory
-
total: MOXA-EDSG508E-MIB::totalMemory
used: MOXA-EDSG508E-MIB::usedMemory
free: MOXA-EDSG508E-MIB::freeMemory
-
total: MOXA-EDSP510A8POE-MIB::totalMemory
used: MOXA-EDSP510A8POE-MIB::usedMemory
free: MOXA-EDSP510A8POE-MIB::freeMemory
-
total: MOXA-EDSG512E8POE-MIB::totalMemory
used: MOXA-EDSG512E8POE-MIB::usedMemory
free: MOXA-EDSG512E8POE-MIB::freeMemory
os:
hardware:
- MOXA-IKS6726A-MIB::switchModel
- MOXA-EDSG508E-MIB::switchModel
- MOXA-EDSP510A8POE-MIB::switchModel
- MOXA-EDSG512E8POE-MIB::switchModel
version:
- MOXA-IKS6726A-MIB::firmwareVersion
- MOXA-EDSG508E-MIB::firmwareVersion
- MOXA-EDSP510A8POE-MIB::firmwareVersion
- MOXA-EDSG512E8POE-MIB::firmwareVersion
serial:
- MOXA-IKS6726A-MIB::serialNumber
- MOXA-EDSG508E-MIB::serialNumber
- MOXA-EDSP510A8POE-MIB::serialNumber
- MOXA-EDSG512E8POE-MIB::serialNumber
sensors:
pre-cache:
data:

View File

@ -1,5 +1,12 @@
mib: MPIOS-MIB
modules:
mempools:
data:
-
total: MPIOS-MIB::memoryTotalBytes
used: MPIOS-MIB::numBytesAlloc
free: MPIOS-MIB::numBytesFree
os:
sysDescr_regex: '/MyPower (?<hardware>.*) version (?<version>[\d.]+)/'
processors:

View File

@ -1,5 +1,11 @@
mib: NETGEAR-BOXSERVICES-PRIVATE-MIB
modules:
mempools:
data:
-
total: NETGEAR-SWITCHING-MIB::agentSwitchCpuProcessMemAvailable
free: NETGEAR-SWITCHING-MIB::agentSwitchCpuProcessMemFree
precision: 1024
os:
sysDescr_regex: '/^(?<hardware>\S+) .*, (?<version>[\d.]+),/'
serial: ENTITY-MIB::entPhysicalSerialNum.1

View File

@ -1,5 +1,11 @@
mib: NS-ROOT-MIB
modules:
mempools:
data:
-
total: NS-ROOT-MIB::memSizeMB
percent_used: NS-ROOT-MIB::resMemUsage
precision: 1048576
os:
hardware: NS-ROOT-MIB::sysHardwareVersionDesc.0
serial: NS-ROOT-MIB::sysHardwareSerialNumber.0

View File

@ -1,5 +1,10 @@
mib: OACOMMON-MIB
modules:
mempools:
data:
-
percent_used: OACOMMON-MIB::netSpireDeviceStorageUsed
descr: 'Storage'
os:
hardware: OACOMMON-MIB::netspireDeviceModelName.0
serial: OACOMMON-MIB::netSpireDeviceDeviceSerialNo.0

View File

@ -1,5 +1,16 @@
mib: ASAM-SYSTEM-MIB:ASAM-EQUIP-MIB
modules:
mempools:
pre-cache:
oids:
- ASAM-EQUIP-MIB::eqptBoardTable
data:
-
total: ASAM-SYSTEM-MIB::totalMemSize
used: ASAM-SYSTEM-MIB::memAbsoluteUsage
precision: 1048576
descr: '{{ ASAM-EQUIP-MIB::eqptBoardInventoryTypeName }}: {{ ASAM-EQUIP-MIB::eqptBoardIfSlotId }} Memory ({{ $index }})'
warn_percent: 98
os:
hardware: ASAM-EQUIP-MIB::eqptHolderActualType.17
serial: ASAM-EQUIP-MIB::eqptHolderSerialNumber.17

View File

@ -1,5 +1,9 @@
mib: SW-MIB
modules:
mempools:
data:
-
percent_used: .1.3.6.1.4.1.1588.2.1.1.1.26.6.0
processors:
data:
-

View File

@ -1,5 +1,14 @@
mib: SMARTNODE-MIB
modules:
mempools:
pre-cache:
oids:
- SMARTNODE-MIB::memDescr
data:
-
used: SMARTNODE-MIB::memAllocatedBytes
free: SMARTNODE-MIB::memFreeBytes
descr: '{{ SMARTNODE-MIB::memDescr }} Memory'
os:
hardware:
- SMARTNODE-MIB::hwRelease.0

View File

@ -0,0 +1,8 @@
modules:
mempools:
data:
-
total: NMS-MEMORY-POOL-MIB::nmsMemoryPoolTotalMemorySize
percent_used: NMS-MEMORY-POOL-MIB::nmsMemoryPoolUtilization
type: pbn-mem
descr: 'Main Memory'

View File

@ -1,4 +1,11 @@
modules:
mempools:
data:
-
total: .1.3.6.1.4.1.674.10895.5000.2.6132.1.1.1.1.4.2.0
free: .1.3.6.1.4.1.674.10895.5000.2.6132.1.1.1.1.4.1.0
descr: 'CPU Memory'
type: powerconnect-cpu
os:
sysDescr_regex: '/(?<hardware>(Power[Cc]onnect |Dell Networking |Dell EMC Networking )?[A-Z]?\d{2,}[A-Z\-]*)(, (?<version>\d+\.[\d.]+))?/'
features: Dell-Vendor-MIB::productIdentificationDescription.0

View File

@ -1,5 +1,19 @@
mib: POWERSUPPLY-MIB:FAN-MIB:STATISTICS-MIB
modules:
mempools:
data:
-
total: NETSWITCH-MIB::hpLocalMemTotalBytes
free: NETSWITCH-MIB::hpLocalMemFreeBytes
used: NETSWITCH-MIB::hpLocalMemAllocBytes
descr: 'Local Memory {{ $index }}'
type: hpLocal
-
total: NETSWITCH-MIB::hpGlobalMemTotalBytes
free: NETSWITCH-MIB::hpGlobalMemFreeBytes
used: NETSWITCH-MIB::hpGlobalMemAllocBytes
descr: 'Global Memory {{ $index }}'
type: hpGlobal
os:
sysDescr_regex:
- '/( (?<hardware>\d{4,}\S*)[^,]*)?, revision (?<version>[^ ,]+)/'

View File

@ -1,5 +1,13 @@
mib: PULSESECURE-PSG-MIB
modules:
mempools:
data:
-
total: UCD-SNMP-MIB::memTotalReal
percent_used: PULSESECURE-PSG-MIB::iveMemoryUtil
precision: 1024
descr: 'Main Memory'
type: 'pulse-mem'
os:
hardware: PULSESECURE-PSG-MIB::productName.0
version: PULSESECURE-PSG-MIB::productVersion.0

Some files were not shown because too many files have changed in this diff Show More