SNMP Client - Geräte-Status von NAS (QNAP, Synology) oder SNMP Servern allg. auslesen

Hallo,

mit nachfolgendem Skript (Idee basiert auf dem Beitrag von Hardlog Status der Synology DS per Script auslesen?) könnt ihr von einem SNMP Server Daten auslesen und im weiterverarbeiten.

In meinem Fall habe ich Daten wie Festplattenkapazität, Arbeitsspeicher, Temperaturen, etc. meiner QNAP ausgelesen.

Das Skript legt für jeden ausgelesenen Wert eine Variable an und aktualisiert diese. Dadurch könnt ihr mit IPS-Ereignissen arbeiten und die Variablen angenehm im Webfront verarbeiten.

Benötigt wird das Kommandozeilenprogramm „ssmnpq.exe“ (nur unter Windows lauffähig). Das Programm gibt’s hier: Simple SNMP Query Tool - Digi Grupp

Die Konfiguration ist in den Script-Kommentaren erläutert.

Skript:


<?
// *****************************************************************************
// ** Script zum Auslesen der MIB von SNMP Server
// ** Die Idee stammt von hardlog aus dem Symcon Forum (https://www.symcon.de/forum/threads/26977-Status-der-Synology-DS-per-Script-auslesen?p=247930#post247930)
// ** läuft so nur unter Windows, da das Komandozeilenprogramm "ssmnpq.exe"
// ** benötig: genanntes Programm hier http://www.digigrupp.com/ssnmpq/ downloaden
// ** in einen beliebigen Ornder entpacken und den Ornder in diesem Script
// ** entsprechend anpassen
// ** Bei NAS-Servern wie Synology / QNAP muss der SNMP-Dienst aktiviert werden.
// ** Den Standardport am SNMP Server bitte nicht ändern.
// **
// ** Dieses Skript funktioniert folgendermaßen:
// ** Du konfigurierst, welche Werte deines SNMP Servers du gerne auslesen,
// ** möchtest (siehe "registerSNMPObj" weiter unten).
// ** Das Skript wird den Datentyp der SNMP Daten ermitteln und als IPS-Variablen
// ** unterhalb des Skriptes anlegen (sofern diese nicht bereits existieren.)
// ** Der Name der Variable entspricht der von dir benannten "Beschreibung" für
// ** den SNMP-Wert.
// ** Die Werte der Variablen werden mit jeder Ausführung des Skripts aktualisiert.
// *****************************************************************************


/**
	KONFIGURATION der SNMP Verbindung
	~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
**/
$host          = "192.168.2.253"; 										// IP Adresse deines SNMP Servers (QNAP, Synology, etc.)
$community     = "public"; 												// SNMP Community
$binary 			= "C:\IP-Symcon\IPStools\ssnmpq\ssnmpq.exe";    // Pfad zur ssnmpq.exe
$debug         = false; 													// Bei true werden Debuginformationen (echo) ausgegeben

$snmp = new SNMP($host, $community, $binary, $debug);          //DIESE ZEILE NICHT VERÄNDERN!

/**
 KONFIGURATION abzurufender Werte
 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
 mit $snmp->registerSNMPObj($oid, $desc, $convertType) kannst du angeben,
 welche Daten per SNMP abgerufen werden sollen.
 Die Funktion benötigt drei Parameter:
 
 Parameter1 ($oid):
 ------------------
 die ID des Wertes am SNMP Server (Mit dem iReasoning MIB Browser kannst du mit
 einem Windowsprogramm angenehm nach gültigen ID's in deinem System suchen.
 http://www.ireasoning.com
 
 Die vorbelegten OIDs basieren auf den Werten meiner QNAP und müssen evtl.
 angepasst werden.
 
 Parameter2 ($desc):
 -------------------
 Die Bezeichnung legt fest, wie die IPS-Variable genannt werden soll.
 
 Bitte berücksichtige, dass jede OID und jede Bezeichnung eindeutig sein müssen
 (keine doppelten Einträge). Ausserdem löscht das Skript keine einmal erstellten
 Variablen. D.h. wenn du eine Bezeichnung umbenennst, denn musst du die "alte"
 Variable manuell löschen.
 
 Parameter 3 (convertType)
 -------------------------
 dieser Parameter ist optional. Wird er nicht gesetzt oder als "none" übergeben,
 werden die Daten "wie empfangen" in der zugehörigen IPS-Variable gespeichert.
 
 In einigen Fällen ist dies jedoch nicht erwünscht. Beispielsweise liefert eine
 QNAP als freie Festplattenkapazität den Wert inkl. der Mengeneinheit als Text:
 3.96 TB. Damit ist eine geeignete Weiterverarbeitung in IPS sowie ein Logging
 der Variable ausgeschlossen.
 
 Um das zu ändern beinhaltet das Skript einige "Converter". In diesem Fall auf
 die Rohdaten der QNAP abgestimmt. Der Converter "Capacity" wandelt MB/GB/TB
 (Megabyte, Gigabyte, Terrabyte)-Strings in Megabyte Zahlen um.
 Aus "3.96 TB" werden "3960000".
 
 Derzeit verfügbare Converter:
 Capacity (Speichergrößen in Megabyte als Float)
 Temperature (Celsius Temperatur als Integer)
 FanSpeed (RPM als Integer)
 
**/

$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.12.0", "ModelName");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.2.0", "SystemTotalMem", "Capacity");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.3.0", "SystemFreeMem", "Capacity");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.17.1.4.1", "SysVolumeTotalSize", "Capacity");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.17.1.5.1", "SysVolumeFreeSize", "Capacity");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.4.0", "SystemUptime");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.5.0", "CPU-Temperature", "Temperature");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.6.0", "System-Temperature", "Temperature");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.15.1.3.1", "System-FanSpeed", "FanSpeed");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.3.1", "HDTemperature1", "Temperature");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.3.2", "HDTemperature2", "Temperature");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.3.3", "HDTemperature3", "Temperature");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.3.4", "HDTemperature4", "Temperature");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.7.1", "HDSmartInfo1");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.7.2", "HDSmartInfo2");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.7.3", "HDSmartInfo3");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.7.4", "HDSmartInfo4");

// ***** ab hier nichts mehr ändern
$snmp->update();

class SNMP
{
	//Objekteigenschaften
	protected $host;       			//SNMP Serveradresse
  	protected $community;  			//SNMP Community
  	protected $binary;     			//Dateipfad zur ssnmpq.exe
  	public $debug = false; 			//Bei true werden Debuginformationen ausgegeben
  	protected $snmpobj=array();	//array registrierter snmp objekte welche beim server abgefragt werden
  	

	public function __construct($host, $community, $binary, $debug){
		$this->host 		= $host;
		$this->community 	= $community;
		$this->binary 		= $binary;
		$this->debug 		= $debug;
	}
	
	public function registerSNMPObj($oid, $desc, $convertType = "none"){
	
	   //prüfe auf doppelte Einträge beim Registrieren neuer SNMP Objekte
	   foreach($this->snmpobj as $obj){
	      if($desc==$obj->desc){
	      	if($this->debug) echo "ERROR - registerSNMPObj: Variable description '$desc' already exists, it must be unique!";
				exit;
			}
			if($oid==$obj->OID){
	      	if($this->debug) echo "ERROR - registerSNMPObj: Variable OID '$oid' already exists, it must be unique!";
				exit;
			}
	   }
	   
	   //prüfe ob IPS Variablen für SNMP Objekt existiert (Variablenname entspricht description)
	   $parentID = $_IPS['SELF'];
		$ips_var = @IPS_GetVariableIDByName($desc, $parentID);
	   if($ips_var == false){
	      if($this->debug) echo "Variable '$desc' not found - create IPSVariable
";

			if($convertType == "none") $type = $this->getSNMPType($oid);
			if($convertType == "Capacity") $type = 2; //float
			if($convertType == "Temperature") $type = 1; //integer
			if($convertType == "FanSpeed") $type = 1; //integer
	      if($this->debug) echo "Type of OID '$oid' is $type 
";
	      
	      $ips_var = IPS_CreateVariable($type);
	      IPS_SetName($ips_var, $desc);
	      IPS_SetParent($ips_var, $parentID);
	   }
	   
		$count = count($this->snmpobj);
	   array_push($this->snmpobj, new SNMPObj($oid, $desc, $convertType, $ips_var));
	   $count = count($this->snmpobj);
	   if($this->debug) echo "New SNMPObj registered, now monitoring '$count' snmp variables
";
	}
	
	//startet eine Abfrage am SNMP Server und aktualisiert die IPS-Variablen der registrierten
	//SNMP Objekte
	public function update(){
		if($this->debug) echo "Updating ". count($this->snmpobj) ." variable(s)
";
		
	   foreach($this->snmpobj as $obj){
	      $oid = ltrim($obj->OID,".");
	      $exec_param =" /h:". $this->host ." /c:". $this->community ." /o:". $oid ." /v";
	      if($this->debug) echo "Execute SNMP-Query: ". $this->binary, "$exec_param
";
	      $obj->value = trim(IPS_Execute($this->binary, $exec_param, false, true));
	      if($this->debug) echo "Result of ". $obj->desc .": ". $obj->value ."
";
	      
	      if($obj->convertType=="Capacity") $obj->value = $this->convertCapacity($obj->value);
	      if($obj->convertType=="Temperature") $obj->value = $this->convertTemperature($obj->value);
	      if($obj->convertType=="FanSpeed") $obj->value = $this->convertFanSpeed($obj->value);
	      
			SetValue($obj->ips_var, $obj->value);
	   }
	}
	
	//prüfe um welchen SNMP Rückgabetyp es sich handelt
	//returns 3 => String / 1 => Integer / 2 => Float
	private function getSNMPType($oid){
		$oid = ltrim($oid,".");
	 	$exec_param =" /h:". $this->host ." /c:". $this->community ." /o:". $oid;
		$result = IPS_Execute($this->binary, $exec_param, false, true);
	   $pos_start = stripos ($result, "Type=");
	   $pos_end = stripos ($result, "Value=");
		$type = substr($result, $pos_start + strlen("Type="), $pos_end - $pos_start);

		switch($type){
		case "OctetString":
			return 3;
		case "Integer":
			return 1;
		case "TimeTicks":
		   return 2;
		default:
		   return 3;
		}
	}
	
	//returns -1 on error
	private function convertCapacity($input){
		$result = -1;
	   $pos = stripos($input, "MB");
	   if($pos != false){
	      $result = substr($input, 0, $pos);
	      $result = round(trim($result));
	   }
	   $pos = stripos($input, "GB");
	   if($pos != false){
	      $result = substr($input, 0, $pos);
	      $result = trim($result)*1000;
	   }
	   $pos = stripos($input, "TB");
	   if($pos != false){
	      $result = substr($input, 0, $pos);
	      $result = trim($result)*1000*1000;
	   }
		return $result;
	}
	
	//returns -1 on error
	private function convertTemperature($input){
		$result = -1;
	   $pos = stripos($input, "C");
	   if($pos != false){
	      $result = substr($input, 0, $pos);
	      $result = round(trim($result));
	   }
	   return $result;
	}
	
	//returns -1 on error
	private function convertFanSpeed($input){
		$result = -1;
	   $pos = stripos($input, "RPM");
	   if($pos != false){
	      $result = substr($input, 0, $pos);
	      $result = round(trim($result));
	   }
	   return $result;
	}
	
}

class SNMPObj
{
	//Objekteigenschaften
	public $OID;         			//SNMP Message ID
	public $desc;        			//Beschreibung
	public $value;       			//Wert
	public $convertType;          //Typ-Converter
	public $ips_var;   				//ID der IPS-Variable welche den SNMP Wert speichert

	public function __construct($OID, $desc, $convertType, $ips_var){
		$this->OID				= $OID;
	   $this->desc				= $desc;
		$this->convertType	= $convertType;
	   $this->ips_var 		= $ips_var;
   }
}
?>

Das Skript ist um ein paar Verbesserungen erweitert:

  • automatisches Anlegen von Variablenprofilen mit dem Präfix „SNMP_“. Dadurch werden Temperaturen, RPMs, etc im Webfront formatiert ausgegeben.
  • Auswerten vom Festplattenstatus „S.M.A.R.T“ in Boolean (gut / defekt)
  • Ausgabe von Speicherkapazitäten wahlweise in MB / GB / TB

Wie bisher werden Variablen und Variablenprofile, sofern Sie bereits angelegt sind, nicht nachträglich aktualisiert. D.h. zum Ändern am besten alle erstellten Variablen löschen und vom Skript neu anlegen lassen.


<?
// *****************************************************************************
// ** Script zum Auslesen der MIB von SNMP Server
// ** Die Idee stammt von hardlog aus dem Symcon Forum (https://www.symcon.de/forum/threads/26977-Status-der-Synology-DS-per-Script-auslesen?p=247930#post247930)
// ** läuft so nur unter Windows, da das Komandozeilenprogramm "ssmnpq.exe"
// ** benötig: genanntes Programm hier http://www.digigrupp.com/ssnmpq/ downloaden
// ** in einen beliebigen Ornder entpacken und den Ornder in diesem Script
// ** entsprechend anpassen
// ** Bei NAS-Servern wie Synology / QNAP muss der SNMP-Dienst aktiviert werden.
// ** Den Standardport am SNMP Server bitte nicht ändern.
// **
// ** Dieses Skript funktioniert folgendermaßen:
// ** Du konfigurierst, welche Werte deines SNMP Servers du gerne auslesen,
// ** möchtest (siehe "registerSNMPObj" weiter unten).
// ** Das Skript wird den Datentyp der SNMP Daten ermitteln und als IPS-Variablen
// ** unterhalb des Skriptes anlegen (sofern diese nicht bereits existieren.)
// ** Der Name der Variable entspricht der von dir benannten "Beschreibung" für
// ** den SNMP-Wert.
// ** Die Werte der Variablen werden mit jeder Ausführung des Skripts aktualisiert.
// **
// ** Das Skript legt benötigte Variablenprofile an. Diese sind mit einem Präfix
// ** "SNMP_" versehen. Beispielsweise "SNMP_CapacityMB".
// *****************************************************************************


/**
KONFIGURATION der SNMP Verbindung
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
**/
$host          = "192.168.2.253"; 														// IP Adresse deines SNMP Servers (QNAP, Synology, etc.)
$community     = "public"; 																		// SNMP Community
$binary 			= "C:\IP-Symcon\IPStools\ssnmpq\ssnmpq.exe";    // Pfad zur ssnmpq.exe
$debug         = false; 																			// Bei true werden Debuginformationen (echo) ausgegeben

$snmp = new SNMP($host, $community, $binary, $debug);         //DIESE ZEILE NICHT VERÄNDERN!

/**
KONFIGURATION abzurufender Werte
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

mit $snmp->registerSNMPObj($oid, $desc, $convertType) kannst du angeben,
welche Daten per SNMP abgerufen werden sollen.
Die Funktion benötigt drei Parameter:

Parameter1 ($oid):
------------------
die ID des Wertes am SNMP Server (Mit dem iReasoning MIB Browser kannst du mit
einem Windowsprogramm angenehm nach gültigen ID's in deinem System suchen.
http://www.ireasoning.com

Die vorbelegten OIDs basieren auf den Werten meiner QNAP und müssen evtl.
angepasst werden.

Parameter2 ($desc):
-------------------
Die Bezeichnung legt fest, wie die IPS-Variable genannt werden soll.

Bitte berücksichtige, dass jede OID und jede Bezeichnung eindeutig sein müssen
(keine doppelten Einträge). Ausserdem löscht das Skript keine einmal erstellten
Variablen. D.h. wenn du eine Bezeichnung umbenennst, denn musst du die "alte"
Variable manuell löschen.

Parameter 3 (convertType)
-------------------------
dieser Parameter ist optional. Wird er nicht gesetzt oder als "none" übergeben,
werden die Daten "wie empfangen" in der zugehörigen IPS-Variable gespeichert.

In einigen Fällen ist dies jedoch nicht erwünscht. Beispielsweise liefert eine
QNAP als freie Festplattenkapazität den Wert inkl. der Mengeneinheit als Text:
3.96 TB. Damit ist eine geeignete Weiterverarbeitung in IPS sowie ein Logging
der Variable ausgeschlossen.

Um das zu ändern beinhaltet das Skript einige "Converter". In diesem Fall auf
die Rohdaten der QNAP abgestimmt. Der Converter "Capacity" wandelt MB/GB/TB
(Megabyte, Gigabyte, Terrabyte)-Strings in Megabyte Zahlen um.
Aus "3.96 TB" werden "3960000".

Derzeit verfügbare Converter:
CapacityMB (Speichergrößen in Megabyte als Float)
CapacityGB(Speichergrößen in Megabyte als Float)
CapacityTB (Speichergrößen in Megabyte als Float)
Temperature (Celsius Temperatur als Integer)
FanSpeed (RPM als Integer)
SmartStatus (S.M.A.R.T Informationen der HDD, Ergebnis ist Boolean => gut / schlecht)

**/

$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.12.0", "ModelName");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.2.0", "SystemTotalMem", "CapacityMB");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.3.0", "SystemFreeMem", "CapacityMB");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.17.1.4.1", "SysVolumeTotalSize", "CapacityGB");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.17.1.5.1", "SysVolumeFreeSize", "CapacityGB");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.4.0", "SystemUptime");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.5.0", "CPU-Temperature", "Temperature");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.6.0", "System-Temperature", "Temperature");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.15.1.3.1", "System-FanSpeed", "FanSpeed");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.3.1", "HDTemperature1", "Temperature");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.3.2", "HDTemperature2", "Temperature");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.3.3", "HDTemperature3", "Temperature");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.3.4", "HDTemperature4", "Temperature");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.7.1", "HDSmartInfo1", "SmartStatus");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.7.2", "HDSmartInfo2", "SmartStatus");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.7.3", "HDSmartInfo3", "SmartStatus");
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.7.4", "HDSmartInfo4", "SmartStatus");

// ***** ab hier nichts mehr ändern
$snmp->update();

class SNMP
{
	//Objekteigenschaften
	protected $host;       			//SNMP Serveradresse
	protected $community;  			//SNMP Community
	protected $binary;     			//Dateipfad zur ssnmpq.exe
	public $debug = false; 			//Bei true werden Debuginformationen ausgegeben
	protected $snmpobj=array();	//array registrierter snmp objekte welche beim server abgefragt werden

	//IPS Datentypen
	const tBOOL		= 0;
	const tINT		= 1;
	const tFLOAT	= 2;
	const tSTRING	= 3;

	public function __construct($host, $community, $binary, $debug){
		$this->host 		= $host;
		$this->community 	= $community;
		$this->binary 		= $binary;
		$this->debug 		= $debug;


		//Prüfe ob Variablenprofile existieren und erstelle diese wenn nötig
		$this->createVariableProfile("SNMP_CapacityMB", self::tFLOAT, "", " MB");
		$this->createVariableProfile("SNMP_CapacityGB", self::tFLOAT, "", " GB");
		$this->createVariableProfile("SNMP_CapacityTB", self::tFLOAT, "", " TB");
		$this->createVariableProfile("SNMP_Temperature", self::tINT, "", " °C");
		$this->createVariableProfile("SNMP_FanSpeed", self::tINT, "", " RPM");
		if(!IPS_VariableProfileExists("SNMP_SmartStatus")){
			$this->createVariableProfile("SNMP_SmartStatus", self::tBOOL, "", "");
			IPS_SetVariableProfileAssociation("SNMP_SmartStatus", 1, "Gut", "", 0x00FF04);
			IPS_SetVariableProfileAssociation("SNMP_SmartStatus", 0, "Defekt", "", 0xFF0000);
		}
	}

	private function createVariableProfile($name, $type, $pre, $suff){
		if(!IPS_VariableProfileExists($name)){
			if($this->debug) echo "INFO - VariablenProfil $name existiert nicht und wird angelegt";
			IPS_CreateVariableProfile($name, $type);
			IPS_SetVariableProfileText($name, $pre, $suff);
		}
	}

	public function registerSNMPObj($oid, $desc, $convertType = "none"){

		//prüfe auf doppelte Einträge beim Registrieren neuer SNMP Objekte
		foreach($this->snmpobj as $obj){
			if($desc==$obj->desc){
				if($this->debug) echo "ERROR - registerSNMPObj: Variable description '$desc' already exists, it must be unique!";
				exit;
			}
			if($oid==$obj->OID){
				if($this->debug) echo "ERROR - registerSNMPObj: Variable OID '$oid' already exists, it must be unique!";
				exit;
			}
		}

		//prüfe ob IPS Variablen für SNMP Objekt existiert (Variablenname entspricht description)
		$parentID = $_IPS['SELF'];
		$ips_var = @IPS_GetVariableIDByName($desc, $parentID);
		if($ips_var == false){
			if($this->debug) echo "Variable '$desc' not found - create IPSVariable
";

			if($convertType == "none")
			$type = $this->getSNMPType($oid);
			if($convertType == "CapacityMB" || $convertType == "CapacityGB" || $convertType == "CapacityTB")
			$type = self::tFLOAT;
			if($convertType == "Temperature")
			$type = self::tINT;
			if($convertType == "FanSpeed")
			$type = self::tINT;
			if($convertType == "SmartStatus")
			$type = self::tBOOL;
			if($this->debug) echo "Type of OID '$oid' is $type 
";

			$ips_var = IPS_CreateVariable($type);
			IPS_SetName($ips_var, $desc);
			IPS_SetParent($ips_var, $parentID);

			//Verknüpfe Variablenprofil mit neu erstellter Variable
			if($convertType == "CapacityMB")
			IPS_SetVariableCustomProfile($ips_var, "SNMP_CapacityMB");
			if($convertType == "CapacityGB")
			IPS_SetVariableCustomProfile($ips_var, "SNMP_CapacityGB");
			if($convertType == "CapacityTB")
			IPS_SetVariableCustomProfile($ips_var, "SNMP_CapacityTB");
			if($convertType == "Temperature")
			IPS_SetVariableCustomProfile($ips_var, "SNMP_Temperature");
			if($convertType == "FanSpeed")
			IPS_SetVariableCustomProfile($ips_var, "SNMP_FanSpeed");
			if($convertType == "SmartStatus")
			IPS_SetVariableCustomProfile($ips_var, "SNMP_SmartStatus");
		}

		$count = count($this->snmpobj);
		array_push($this->snmpobj, new SNMPObj($oid, $desc, $convertType, $ips_var));
		$count = count($this->snmpobj);
		if($this->debug) echo "New SNMPObj registered, now monitoring '$count' snmp variables
";
	}

	//startet eine Abfrage am SNMP Server und aktualisiert die IPS-Variablen der registrierten
	//SNMP Objekte
	public function update(){
		if($this->debug) echo "Updating ". count($this->snmpobj) ." variable(s)
";

		foreach($this->snmpobj as $obj){
			$oid = ltrim($obj->OID,".");
			$exec_param =" /h:". $this->host ." /c:". $this->community ." /o:". $oid ." /v";
			if($this->debug) echo "Execute SNMP-Query: ". $this->binary, "$exec_param
";
			$obj->value = trim(IPS_Execute($this->binary, $exec_param, false, true));
			if($this->debug) echo "Result of ". $obj->desc .": ". $obj->value ."
";

			if($obj->convertType == "CapacityMB") $obj->value = $this->convertCapacity($obj->value, "MB");
			if($obj->convertType == "CapacityGB") $obj->value = $this->convertCapacity($obj->value, "GB");
			if($obj->convertType == "CapacityTB") $obj->value = $this->convertCapacity($obj->value, "TB");
			if($obj->convertType == "Temperature") $obj->value = $this->convertTemperature($obj->value);
			if($obj->convertType == "FanSpeed") $obj->value = $this->convertFanSpeed($obj->value);
			if($obj->convertType == "SmartStatus") $obj->value = $this->convertSmartStatus($obj->value);

			SetValue($obj->ips_var, $obj->value);
		}
	}

	//prüfe um welchen SNMP Rückgabetyp es sich handelt
	//returns 3 => String / 1 => Integer / 2 => Float
	private function getSNMPType($oid){
		$oid = ltrim($oid,".");
		$exec_param =" /h:". $this->host ." /c:". $this->community ." /o:". $oid;
		$result = IPS_Execute($this->binary, $exec_param, false, true);
		$pos_start = stripos ($result, "Type=");
		$pos_end = stripos ($result, "Value=");
		$type = substr($result, $pos_start + strlen("Type="), $pos_end - $pos_start);

		switch($type){
			case "OctetString":
			return self::tSTRING;
			case "Integer":
			return self::tINT;
			case "TimeTicks":
			return self::tFLOAT;
			default:
			return self::tSTRING;
		}
	}

	//returns -1 on error
	private function convertCapacity($input, $unit){
		$pos = stripos($input, "MB");
		if($pos === false) {
			$pos = stripos($input, "GB");
			if($pos === false) {
				$pos = stripos($input, "TB");
				if($pos === false) {
					return -1;
				}else{
					$funit = "TB";
				}
			} else{
				$funit = "GB";
			}
		}else{
			$funit = "MB";
		}

		$result = substr($input, 0, $pos);
		$result = trim($result);
		
		switch ($funit){
			case "GB":
			$result = $result*1000;
			break;
			case "TB":
			$result = $result*1000*1000;
			break;
		}
		
		switch($unit){
			case "MB":
			return round($result);
			case "GB":
			return round($result / 1000);
			case "TB";
			return round($result / 1000000);
		}
	}

	//returns -1 on error
	private function convertTemperature($input){
		$pos = stripos($input, "C");
		if($pos === false){
			$result = -1;
		}else{
			$result = substr($input, 0, $pos);
			$result = round(trim($result));
		}
		return $result;
	}

	//returns -1 on error
	private function convertFanSpeed($input){
		$pos = stripos($input, "RPM");
		if($pos === false){
			$result = -1;
		}else{
			$result = substr($input, 0, $pos);
			$result = round(trim($result));
		}
		return $result;
	}

	private function convertSmartStatus($input){
		$pos = stripos($input, "GOOD");
		if($pos === false){
			return false;
		}else{
			return true;
		}
	}

}

class SNMPObj
{
	//Objekteigenschaften
	public $OID;         			//SNMP Message ID
	public $desc;        			//Beschreibung
	public $value;       			//Wert
	public $convertType;          //Typ-Converter
	public $ips_var;   				//ID der IPS-Variable welche den SNMP Wert speichert

	public function __construct($OID, $desc, $convertType, $ips_var){
		$this->OID					= $OID;
		$this->desc					= $desc;
		$this->convertType	= $convertType;
		$this->ips_var 			= $ips_var;
	}
}
?>

UPDATE FÜR UBUNTU/LINUX CLIENTS

  1. SNMP Client in Ubuntu per SSH installieren:

symcon@ips:~$ sudo apt-get install snmp

  1. SNMP Client per SSH testen: (Hier Frage ich den freien Systemspeicherplatz ab. Ergebnis sollte in einem solchen Format bei euch aussehen)

symcon@ips:~$ snmpget -v 1 -O v 192.168.10.252 -c public 1.3.6.1.4.1.24681.1.2.17.1.5.1
STRING: "1.65 TB"

  1. Dieses Skript verwenden:

<?
// ***************************************************************************** 
// ** Script zum Auslesen der MIB von SNMP Server 
// ** Die Idee stammt von hardlog aus dem Symcon Forum (https://www.symcon.de/forum/threads/26977-Status-der-Synology-DS-per-Script-auslesen?p=247930#post247930) 
// ** läuft so nur unter Windows, da das Komandozeilenprogramm "ssmnpq.exe" 
// ** benötig: genanntes Programm hier http://www.digigrupp.com/ssnmpq/ downloaden 
// ** in einen beliebigen Ornder entpacken und den Ornder in diesem Script 
// ** entsprechend anpassen 
// ** Bei NAS-Servern wie Synology / QNAP muss der SNMP-Dienst aktiviert werden. 
// ** Den Standardport am SNMP Server bitte nicht ändern. 
// ** 
// ** Dieses Skript funktioniert folgendermaßen: 
// ** Du konfigurierst, welche Werte deines SNMP Servers du gerne auslesen, 
// ** möchtest (siehe "registerSNMPObj" weiter unten). 
// ** Das Skript wird den Datentyp der SNMP Daten ermitteln und als IPS-Variablen 
// ** unterhalb des Skriptes anlegen (sofern diese nicht bereits existieren.) 
// ** Der Name der Variable entspricht der von dir benannten "Beschreibung" für 
// ** den SNMP-Wert. 
// ** Die Werte der Variablen werden mit jeder Ausführung des Skripts aktualisiert. 
// ** 
// ** Das Skript legt benötigte Variablenprofile an. Diese sind mit einem Präfix 
// ** "SNMP_" versehen. Beispielsweise "SNMP_CapacityMB". 
// ***************************************************************************** 

/** 
KONFIGURATION der SNMP Verbindung 
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 
**/ 
$host          = "192.168.10.252";     // IP Adresse deines SNMP Servers (QNAP, Synology, etc.) 
$community     = "public";                // SNMP Community 
//$binary        = "C:\IP-Symcon\automatic\SnmpGet\SnmpGet.exe";            // Pfad zum SNMP Binary 
$binary        = "snmpget";            // Pfad zum SNMP Binary
$debug         = false;                    // Bei true werden Debuginformationen (echo) ausgegeben 

$snmp = new SNMP($host, $community, $binary, $debug);          //DIESE ZEILE NICHT VERÄNDERN! 

/** 
KONFIGURATION abzurufender Werte 
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 

mit $snmp->registerSNMPObj($oid, $desc, $convertType) kannst du angeben, 
welche Daten per SNMP abgerufen werden sollen. 
Die Funktion benötigt drei Parameter: 

Parameter1 ($oid): 
------------------ 
die ID des Wertes am SNMP Server (Mit dem iReasoning MIB Browser kannst du mit 
einem Windowsprogramm angenehm nach gültigen ID's in deinem System suchen. 
http://www.ireasoning.com 

Die vorbelegten OIDs basieren auf den Werten meiner QNAP und müssen evtl. 
angepasst werden. 

Parameter2 ($desc): 
------------------- 
Die Bezeichnung legt fest, wie die IPS-Variable genannt werden soll. 

Bitte berücksichtige, dass jede OID und jede Bezeichnung eindeutig sein müssen 
(keine doppelten Einträge). Ausserdem löscht das Skript keine einmal erstellten 
Variablen. D.h. wenn du eine Bezeichnung umbenennst, denn musst du die "alte" 
Variable manuell löschen. 

Parameter 3 (convertType) 
------------------------- 
dieser Parameter ist optional. Wird er nicht gesetzt oder als "none" übergeben, 
werden die Daten "wie empfangen" in der zugehörigen IPS-Variable gespeichert. 

In einigen Fällen ist dies jedoch nicht erwünscht. Beispielsweise liefert eine 
QNAP als freie Festplattenkapazität den Wert inkl. der Mengeneinheit als Text: 
3.96 TB. Damit ist eine geeignete Weiterverarbeitung in IPS sowie ein Logging 
der Variable ausgeschlossen. 

Um das zu ändern beinhaltet das Skript einige "Converter". In diesem Fall auf 
die Rohdaten der QNAP abgestimmt. Der Converter "Capacity" wandelt MB/GB/TB 
(Megabyte, Gigabyte, Terrabyte)-Strings in Megabyte Zahlen um. 
Aus "3.96 TB" werden "3960000". 

Derzeit verfügbare Converter: 
CapacityMB (Speichergrößen in Megabyte als Float) 
CapacityGB(Speichergrößen in Megabyte als Float) 
CapacityTB (Speichergrößen in Megabyte als Float) 
Temperature (Celsius Temperatur als Integer) 
FanSpeed (RPM als Integer) 
SmartStatus (S.M.A.R.T Informationen der HDD, Ergebnis ist Boolean => gut / schlecht) 

**/ 


$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.12.0", "ModelName"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.2.0", "SystemTotalMem", "CapacityMB"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.3.0", "SystemFreeMem", "CapacityMB"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.17.1.4.1", "SysVolumeTotalSize", "CapacityGB"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.17.1.5.1", "SysVolumeFreeSize", "CapacityGB"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.4.0", "SystemUptime"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.5.0", "CPU-Temperature", "Temperature"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.6.0", "System-Temperature", "Temperature"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.15.1.3.1", "System-FanSpeed", "FanSpeed"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.3.1", "HDTemperature1", "Temperature"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.3.2", "HDTemperature2", "Temperature"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.3.3", "HDTemperature3", "Temperature"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.3.4", "HDTemperature4", "Temperature"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.7.1", "HDSmartInfo1", "SmartStatus"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.7.2", "HDSmartInfo2", "SmartStatus"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.7.3", "HDSmartInfo3", "SmartStatus"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.11.1.7.4", "HDSmartInfo4", "SmartStatus"); 
$snmp->registerSNMPObj(".1.3.6.1.4.1.24681.1.2.1.0", "CPU usage", "Percent"); 

// ***** ab hier nichts mehr ändern 
$snmp->update(); 

class SNMP 
{ 
    //Objekteigenschaften 
    protected $host;                   //SNMP Serveradresse 
    protected $community;              //SNMP Community 
    protected $binary;                 //Dateipfad zur ssnmpq.exe 
    public      $debug = false;          //Bei true werden Debuginformationen ausgegeben 
    protected $snmpobj=array();        //array registrierter snmp objekte welche beim server abgefragt werden 

    //IPS Datentypen 
    const tBOOL     = 0; 
    const tINT      = 1; 
    const tFLOAT    = 2; 
    const tSTRING   = 3; 

    public function __construct($host, $community, $binary, $debug) { 
        $this->host         = $host; 
        $this->community    = $community; 
        $this->binary       = $binary; 
        $this->debug        = $debug; 


        //Prüfe ob Variablenprofile existieren und erstelle diese wenn nötig 
        $this->createVariableProfile("SNMP_Percent", self::tFLOAT, "", " %", 2); 
        $this->createVariableProfile("SNMP_CapacityMB", self::tFLOAT, "", " MB", 0); 
        $this->createVariableProfile("SNMP_CapacityGB", self::tFLOAT, "", " GB", 0); 
        $this->createVariableProfile("SNMP_CapacityTB", self::tFLOAT, "", " TB", 0); 
        $this->createVariableProfile("SNMP_Temperature", self::tINT, "", " °C", 0); 
        $this->createVariableProfile("SNMP_FanSpeed", self::tINT, "", " RPM", 0); 
        if (!IPS_VariableProfileExists("SNMP_SmartStatus")) { 
            $this->createVariableProfile("SNMP_SmartStatus", self::tBOOL, "", "", 0); 
            IPS_SetVariableProfileAssociation("SNMP_SmartStatus", 1, "Gut", "", 0x00FF04); 
            IPS_SetVariableProfileAssociation("SNMP_SmartStatus", 0, "Defekt", "", 0xFF0000); 
        } 
    } 

    private function createVariableProfile($name, $type, $pre, $suff, $digits) { 
        if (!IPS_VariableProfileExists($name)) { 
            if ($this->debug) IPS_LogMessage(IPS_GetName($_IPS['SELF']), "INFO - VariablenProfil ".$name." existiert nicht und wird angelegt."); 
            IPS_CreateVariableProfile($name, $type); 
            IPS_SetVariableProfileDigits($name, $digits); 
            IPS_SetVariableProfileText($name, $pre, $suff); 
        } 
    } 

    public function registerSNMPObj($oid, $desc, $convertType = "none") { 

        //prüfe auf doppelte Einträge beim Registrieren neuer SNMP Objekte 
        foreach($this->snmpobj as $obj) { 
            if ($desc==$obj->desc) { 
                if ($this->debug) IPS_LogMessage(IPS_GetName($_IPS['SELF']), "ERROR - registerSNMPObj: Variable description ".$desc." already exists, it must be unique!"); 
                exit; 
            } 
            if ($oid==$obj->OID) { 
                if ($this->debug) IPS_LogMessage(IPS_GetName($_IPS['SELF']), "ERROR - registerSNMPObj: Variable OID ".$oid." already exists, it must be unique!"); 
                exit; 
            } 
        } 

        //prüfe ob IPS Variablen für SNMP Objekt existiert (Variablenname entspricht description) 
        $parentID = IPS_GetParent($_IPS['SELF']); // übergeordnete Kategorie als Basis 
//        $parentID = $_IPS['SELF']; 
        $ips_var = @IPS_GetVariableIDByName($desc, $parentID); 
        if ($ips_var == false) { 
            if ($this->debug) IPS_LogMessage(IPS_GetName($_IPS['SELF']), "Variable ".$desc." not found - create IPSVariable"); 

            if ($convertType == "none") 
                $type = $this->getSNMPType($oid); 
            if ($convertType == "CapacityMB" || $convertType == "CapacityGB" || $convertType == "CapacityTB" || $convertType == "Percent") 
                $type = self::tFLOAT; 
            if ($convertType == "Temperature") 
                $type = self::tINT; 
            if ($convertType == "FanSpeed") 
                $type = self::tINT; 
            if ($convertType == "SmartStatus") 
                $type = self::tBOOL; 
            if ($this->debug) IPS_LogMessage(IPS_GetName($_IPS['SELF']), "Type of OID ".$oid." is ".$type); 

            $ips_var = IPS_CreateVariable($type); 
            IPS_SetName($ips_var, $desc); 
            IPS_SetParent($ips_var, $parentID); 

            //Verknüpfe Variablenprofil mit neu erstellter Variable 
            if ($convertType == "CapacityMB") 
                IPS_SetVariableCustomProfile($ips_var, "SNMP_CapacityMB"); 
            if ($convertType == "CapacityGB") 
                IPS_SetVariableCustomProfile($ips_var, "SNMP_CapacityGB"); 
            if ($convertType == "CapacityTB") 
                IPS_SetVariableCustomProfile($ips_var, "SNMP_CapacityTB"); 
            if ($convertType == "Temperature") 
                IPS_SetVariableCustomProfile($ips_var, "SNMP_Temperature"); 
            if ($convertType == "FanSpeed") 
                IPS_SetVariableCustomProfile($ips_var, "SNMP_FanSpeed"); 
            if ($convertType == "SmartStatus") 
                IPS_SetVariableCustomProfile($ips_var, "SNMP_SmartStatus"); 
            if ($convertType == "Percent") 
                IPS_SetVariableCustomProfile($ips_var, "SNMP_Percent"); 
        } 

        $count = count($this->snmpobj); 
        array_push($this->snmpobj, new SNMPObj($oid, $desc, $convertType, $ips_var)); 
        $count = count($this->snmpobj); 
        if ($this->debug) IPS_LogMessage(IPS_GetName($_IPS['SELF']), "New SNMPObj registered, now monitoring ".$count." snmp variables"); 
    } 

    //startet eine Abfrage am SNMP Server und aktualisiert die IPS-Variablen der registrierten 
    //SNMP Objekte 
    public function update() { 
        if ($this->debug) IPS_LogMessage(IPS_GetName($_IPS['SELF']), "Updating ".count($this->snmpobj)." variable(s)"); 

        foreach ($this->snmpobj as $obj) { 
//            $oid = ltrim($obj->OID,"."); 
            $oid = $obj->OID; 
            $exec_param =" -v 1 -O v -c ".$this->community." ".$this->host." ". $oid .""; 
            if ($this->debug) IPS_LogMessage(IPS_GetName($_IPS['SELF']), "Execute SNMP-Query: ".$this->binary.$exec_param); 
            $result = str_replace('"', '', trim(system($this->binary.$exec_param)));
			
			$pos_start = stripos ($result, ":");  
        	$result = substr($result, $pos_start+1); 
			
			$obj->value = $result; 

            if ($this->debug) IPS_LogMessage(IPS_GetName($_IPS['SELF']), "Result of ".$obj->desc.": ".$obj->value); 

            if ($obj->convertType == "Percent") $obj->value = $this->convertPercent($obj->value, "%"); 
            if ($obj->convertType == "CapacityMB") $obj->value = $this->convertCapacity($obj->value, "MB"); 
            if ($obj->convertType == "CapacityGB") $obj->value = $this->convertCapacity($obj->value, "GB"); 
            if ($obj->convertType == "CapacityTB") $obj->value = $this->convertCapacity($obj->value, "TB"); 
            if ($obj->convertType == "Temperature") $obj->value = $this->convertTemperature($obj->value); 
            if ($obj->convertType == "FanSpeed") $obj->value = $this->convertFanSpeed($obj->value); 
            if ($obj->convertType == "SmartStatus") $obj->value = $this->convertSmartStatus($obj->value); 

            SetValue($obj->ips_var, $obj->value); 
        } 
    } 

    //prüfe um welchen SNMP Rückgabetyp es sich handelt 
    //returns 3 => String / 1 => Integer / 2 => Float 
    private function getSNMPType($oid) { 
        $oid = ltrim($oid,"."); 
        $exec_param =" -v 1 -O v -c ".$this->community." ".$this->host." ". $oid; 
        $result = system($this->binary.$exec_param); 
        $pos_start = stripos ($result, " = "); 
        $pos_end = stripos ($result, ': "'); 
        $type = substr($result, $pos_start, $pos_end - $pos_start); 
        switch($type) { 
            case "STRING": 
                return self::tSTRING; 
            case "Integer": 
                return self::tINT; 
            case "Timeticks": 
                return self::tFLOAT; 
            default: 
                return self::tSTRING; 
        } 
    } 

    //returns -1 on error 
    private function convertCapacity($input, $unit) { 
        $pos = stripos($input, "MB"); 
        if ($pos === false) { 
            $pos = stripos($input, "GB"); 
            if ($pos === false) { 
                $pos = stripos($input, "TB"); 
                if ($pos === false) { 
                    return -1; 
                } else { 
                    $funit = "TB"; 
                } 
            } else { 
                $funit = "GB"; 
            } 
        } else { 
            $funit = "MB"; 
        } 

        $result = substr($input, 0, $pos); 
        $result = trim($result); 

        switch ($funit) { 
            case "GB": 
            $result = $result*1000; 
            break; 
            case "TB": 
            $result = $result*1000*1000; 
            break; 
        } 

        switch($unit) { 
            case "MB": 
            return round($result); 
            case "GB": 
            return round($result / 1000); 
            case "TB"; 
            return round($result / 1000000); 
        } 
    } 

    //returns -1 on error 
    private function convertTemperature($input) { 
        $pos = stripos($input, "C"); 
        if ($pos === false) { 
            $result = -1; 
        } else { 
            $result = substr($input, 0, $pos); 
            $result = round(trim($result)); 
        } 
        return $result; 
    } 

    private function convertPercent($input) { 
        $pos = stripos($input, "%"); 
        if ($pos === false) { 
            $result = -1; 
        } else { 
            $result = substr($input, 0, $pos); 
            $result = trim($result); 
        } 
        return $result; 
    } 

    //returns -1 on error 
    private function convertFanSpeed($input) { 
        $pos = stripos($input, "RPM"); 
        if ($pos === false) { 
            $result = -1; 
        } else { 
            $result = substr($input, 0, $pos); 
            $result = round(trim($result)); 
        } 
        return $result; 
    } 

    private function convertSmartStatus($input) { 
        $pos = stripos($input, "GOOD") + stripos($input, "Normal"); 
        if ($pos === false) { 
            return false; 
        } else { 
            return true; 
        } 
    } 

} 

class SNMPObj 
{ 
    //Objekteigenschaften 
    public $OID;                   //SNMP Message ID 
    public $desc;                  //Beschreibung 
    public $value;                 //Wert 
    public $convertType;           //Typ-Converter 
    public $ips_var;               //ID der IPS-Variable welche den SNMP Wert speichert 

    public function __construct($OID, $desc, $convertType, $ips_var) { 
        $this->OID            = $OID; 
        $this->desc           = $desc; 
        $this->convertType    = $convertType; 
        $this->ips_var        = $ips_var; 
    } 
} 
?>

Funktioniert fast ;), zwei Vorschläge.

Bei SMART kann auch „Normal“ rauskommen, z.B. bei einem „Fehler“ der nur zu einer Warnung führt. Das wird so als Defekt angezeigt.

Und beim Pfad zum binary solltest du jeweils „\“ verwenden, da z.B. „D:\IP-Symcon ools…“ das " " etwas anders verarbeitet.

Und am Anfang ein


ini_set( 'max_execution_time', 90);

würde eventuelle Fehler bei Antwortzeiten größer 30 Sekunden vermeiden.

Hallo,

danke für das tolle Skript.
Hat bei mir auf Anhieb mit einem QNAP TS-412 funktioniert.

Grüße
Björn

Hallo,

Danke für das Script, es läuft leider bei mir nicht.

Zum einen muss ich mir die aktuelle OIDs meiner QNAP raussuchen und diese austauschen, die unterscheiden sich wohl gewaltig zwischen den Modell, ich habe eine TS-853 hier stehen.

Aber was viel schlimmer ist, ich bekomme immer wieder diese Fehlermeldung:


Notice:  A non well formed numeric value encountered in D:\IP-Symcon\scripts\30329.ips.php on line 39

Fatal error:  Uncaught exception 'Exception' with message 'Unknown SNMP protocol version' in D:\IP-Symcon\scripts\30329.ips.php:39
Stack trace:
#0 D:\IP-Symcon\scripts\30329.ips.php(39): SNMP->__construct('192.168.50.100', 'public', 'D:\IP-Symcon\IP...', 0)
#1 {main}
  thrown in D:\IP-Symcon\scripts\30329.ips.php on line 39
Abort Processing during Fatal-Error: Uncaught exception 'Exception' with message 'Unknown SNMP protocol version' in D:\IP-Symcon\scripts\30329.ips.php:39
Stack trace:
#0 D:\IP-Symcon\scripts\30329.ips.php(39): SNMP->__construct('192.168.50.100', 'public', 'D:\IP-Symcon\IP...', 0)
#1 {main}
  thrown
   Error in Script D:\IP-Symcon\scripts\30329.ips.php on Line 39

Zeile 39 ist diese:


$snmp = new SNMP($host, $community, $binary, $debug);         //DIESE ZEILE NICHT VERÄNDERN!

Jemand eine Idee, was das sein kann.
( aktiviert in der QNAP ist SNMP-Verison v1/v2 )

Dnake und Grüsse

Hallo Tuxtom007,

das die OIDs unterschiedlich sind ist sehr wahrscheinlich. Aber mithilfe des Browsers konntest du die ja anpassen.

Bezüglich der Problematik mit der Fehlermeldung:

Die von dir genannte Zeile

$snmp = new SNMP($host, $community, $binary, $debug);

führt die snmpq.exe aus und startet eine Abfrage an den auf der QNAP laufenden SNMP Server.

Da die snmpq.exe nur V1 SNMP queries unterstützt ist es richtig, dass deine QNAP auf SNMP V1/2 eingestellt ist.
Ich frage mich nur, ob eine spezielle Abfrage einer OID fehlschlägt oder jede Verbindung.

Stelle bitte die Variable $debug auf true. Nach dem Ausführen des Skripts erscheint unten ein Log wie dieses:


New SNMPObj registered, now monitoring '1' snmp variables
New SNMPObj registered, now monitoring '2' snmp variables
New SNMPObj registered, now monitoring '3' snmp variables
New SNMPObj registered, now monitoring '4' snmp variables
New SNMPObj registered, now monitoring '5' snmp variables
New SNMPObj registered, now monitoring '6' snmp variables
New SNMPObj registered, now monitoring '7' snmp variables
New SNMPObj registered, now monitoring '8' snmp variables
New SNMPObj registered, now monitoring '9' snmp variables
New SNMPObj registered, now monitoring '10' snmp variables
New SNMPObj registered, now monitoring '11' snmp variables
New SNMPObj registered, now monitoring '12' snmp variables
New SNMPObj registered, now monitoring '13' snmp variables
New SNMPObj registered, now monitoring '14' snmp variables
New SNMPObj registered, now monitoring '15' snmp variables
New SNMPObj registered, now monitoring '16' snmp variables
New SNMPObj registered, now monitoring '17' snmp variables
Updating 17 variable(s)
Execute SNMP-Query: C:\IP-Symcon\IPStools\ssnmpq\ssnmpq.exe /h:192.168.2.253 /c:public /o:1.3.6.1.4.1.24681.1.2.12.0 /v
Result of ModelName: TS-470 Pro
Execute SNMP-Query: C:\IP-Symcon\IPStools\ssnmpq\ssnmpq.exe /h:192.168.2.253 /c:public /o:1.3.6.1.4.1.24681.1.2.2.0 /v
Result of SystemTotalMem: 7883.1 MB
....
....
....usw.

Bitte prüfe ob nur bestimmte Abfragen fehlschlagen oder alle.

Falls generell etwas nicht stimmt, versuche mal den Befehl per Windows-Konsole (Start->Ausführen->cmd) manuell zu starten. Beispielsweise so:

C:\IP-Symcon\IPStools\ssnmpq\ssnmpq.exe /h:192.168.2.253 /c:public /o:1.3.6.1.4.1.24681.1.2.12.0 /v

Schlägt das auch fehl, stimmt etwas nicht zwischen der Kommunikation zwischen der QNAP und der ssnmpg.exe.

Hallo,

Dnake für die Infos.

Die manuelle Abfrage mit ssnmpg.exe funktioniert vom IP-Server soweit, getest mit diversen OIDs

Debug hab ich aktiviert, aber ausser der selben Fehlermeldung kommt garnichts.

Ich werde mal als erstes die ganzen OIDs ändern, mal sehen ob es dann besser aussieht.

Ich nutze übrigens ein nettes Tool namens „The Dude“, kommt von Mikrotik, den Hersteller meiner Switche/Router und kann ausser Netzwerke graphisch darstellen auch SNMPWalk- Abfragen schön auflisten.
( nur meckert die QNAP das dann immer als SNMP-DoS Attake :frowning: )

Dankes fürs erste, ich melde mich wieder.

Grüsse

Thomas

Hallo,

so ich nochmal.

Ich habe nun mal die ganzen OIDs rausgesucht und damit getestet, keine Änderung.
Die Fehlermeldung bleibt die selbe.

Was mir aber aufgefallen ist, wenn ich das Kommando mehrfach hintereinander aufrufe, antwortet die NAS nicht immer, da kommt sehr häufig „no response“ zurück, evtl. liegt hier das Problem. Vielleicht macht die NAS zu, wenn zuviele Abfragen hintereinander kommen. Wenn ich snmpwalk starte, gibt die ja auch eine Warnung „SNMP DoS“ raus.

Oder ssnmpq.exe funktioniert unter Win10/64bit nicht richtig.

Ich werde mal spasseshalber eines der Scripte überarbeiten, mit denen ich den Status und die Daten meiner Switch abfrage, das wird direkt per snmpget aus dem Script raus gemacht und funktioniert bei den Switchen sehr gut, für die NAS reicht ja auch dann ein 5 min Intervall.

Oder hat jemand eine andere Idee, wo nich noch nachschauen kann ?

Danke im Voraus

Thomas

Hallo,

so mal ein Update geben kann, ich habe einiges rumprobiert.

Ergebniss: ssnmpq.exe macht dir Probleme, es funktioniert selbst bei manuellem Aufruf per Kommadozeile nur zeitweise, warum weiss ich nicht, vermuttlich ist das Programm nicht Win10/64Bit Kompatiblet.
Ich habs geteste auf zwei Rechnern ( IPS-Server und Notebook, beide Win10/64bit ).

Meldung immer wieder „no response“, ich hab selbe Firewall usw. deaktiviert, bringt keinen Unterschied. IPS-Server und NAS hängen am selben Switch.

Frage ich die selben OIDs per snmpwalk auf einem Monitoringtool ab, bekomme ich alle Daten aus der QNAP ausgelesen, selbst der Abruf eines kompletten snmpwalk zeigt mir alles an Daten an, was die QNAP rausschickt, das ist eine ganze Latte.

Jetzt hab ich ein andere IPS-Skript benutzt, welche hier aus dem Forum ist und womit ich meine Switche abfrage, per direkter PHP-snmpget Kommando, funktioniert es bisher mit einigen Test-OID sehr gut und stabil. Alleridngs sind die Daten noch nicht brauchbar, da muss ich die Formatierung noch umbauen.

Schade eigentlich - diese Script finde ich sehr gut gelungen

Hi Thomas,

danke für die Infos, ich werde das auch mal bei mir testen.

Die Variante mit snmpget ist sehr interessant. Ich werde mich die Tage damit mal auseinandersetzen und eventuell mein Skript anpassen.

Ansonsten ist es halt auch sehr gewagt IP-Symcon auf Windows 10 laufen zu lassen :slight_smile: Es ist ein brandneues Betriebssystem und hat sicher neben vielen Kinderkrankheiten, Kompatibilitätsproblemen auch sehr viele Sicherheitsproblemchen. Mir ist das zu unsicher für meine Haussteuerung. Ich werde hier frühestens in 1-2 Jahren auf Windows 10 wechseln.

Gruß

Floran

Hallo,

für smnpget braucht es wenn ich das richtig verstanden habe, noch die alte SSL-Bibliothek 0,98, mit der neuen in IPS habe ich das noch nicht probiert. Ich baue gerade erst mein IPS komplett neu auf.

IPS läuft problemlos unter Win10, dazu gibt es auch hier im Forum schon einige Aussagen, das Problem hier sehe ich eindeutig bei ssnmpq.exe - das letzte Update ist von 2007, da gabs gerade mal WinXP und zwischen XP und 10 liegen nun mal Welten.

Du könntest dir Visual Studio Community Edition runterladen und dann die ssnmpq.exe mit den neuen Frameworks neu kompilieren. Das Tool ist jetzt nicht sooo mächtig und wenn man so über den auf der Webseite frei erhältlichen Quellcode schaut, dann vermute ich, dass es fast problemlos auf neue C# Bibliotheken übertragbar ist.

Hallo,

nette Idee, aber das ist mir too much. So tief bin ich in Programmierthemen nicht drin, daher lasse ich es besser gleich :slight_smile:

Also ich habe hier auch ein Win10 x64 am Laufen. Habe jetzt mal die ssnmpq.exe von der o.g. Seite runtergeladen und einfach aus der Zip auf mein Laufwerk D: kopiert. Dann im Command Fenster einfach den folgenden Befehl ca. 3-4 mal pro Sekunde ausgeführt.


D:\>ssnmpq.exe /h:192.168.2.253 /c:public /o:1.3.6.1.4.1.24681.1.2.2.0 /v
7883.1 MB

Das Ergebnis ist wie gewünscht…

Auch andere Abfragen klappen wundervoll.


D:\>ssnmpq.exe /h:192.168.2.253 /c:public /o:1.3.6.1.4.1.24681.1.2.12.0 /v
TS-470 Pro

Also das Programm läuft wundervoll. Es muss an deiner Konfiguration liegen.

Hallo,

sehr merkwürdig, ich hab das Tool auch nochmal runtergeladen, unter d:\Temp entpackt und das selbe Kommando ausgeführt:

D:\Temp>ssnmpq.exe /h:192.168.50.100 /c:public /o:1.3.6.1.4.1.24681.1.2.12.0 /v

No response

immer wieder und auf zwei verschiedenen Rechnern ( Notebook und meinem IPS-Server, beide Win10/64 )

Mache ich das selbe mit meinem SNMP-Tools, egal welches auf die selbe OID, funktioniert das einwandfrei, hier z.b. auf die OID selber und einmal auf den komplette Subtree ( siehe Screenshots 1 & 2 ):

Einstellungen an der QNAP ( Screenshot 3 ) auch ganz normal, da ist ja nicht viel dran einzustellen.

Hast du noch irgentwas anders gemacht ?

Grüsse
Thomas

Bin grad selbst drauf reingefallen - SNMP auf dem QNAP war bei mir nicht aktiviert …

(ggf. auch in WIndows aktivieren)

LG Tom

Tja - zu früh gefreut, es geht bei der QNAP nur die /h:192.168.2.253 /c:public /o:1.3.6.1.4.1.24681.1.2.2.0 /v
der Rest ist bisher tot. Unter XP geht alles …

Bei der Synology klappt es aber komischerweise…

Hi,

Es liegt bei mir defintiv an ssnmpq.exe, ich kann kein einziges Gerät abfragen, kommt immer wieder no-response, selbst wenn ich den IPS-Server lokal abfragen kommt nichts.
Selbst von den beiden Switche, die ich von IPS aus schon per SNMP abfrage, kann ssnmpq nicht erkennen.

Ich habe 3 SNMP-Tools ausprobiert ( The Dude, SNMP-Tester, MIB-Browser ) - alle 3 fragen die selben Geräte problemlos ab und zwar alle Daten.
Von meiner QNAP bekommen ich locker 100+ Werte ausgegeben, selbst die ganzen Prozessstatisktiken und Netzwerkkarten-Counter.

so richtig strange ist aber, wenn ich snmpq.exe nur mit IP-Adresse aufrufen, holt es Daten von der NAS:


D:\IP-Symcon\IPSTools\ssnmpq>ssnmpq.exe /h:192.168.50.100
Simple SNMP Command Line Query Tool, Toomas Kaljus, January 2007

Searching 1.3.6.1.2.1.1 ... (iso.org.dod.internet.mgmt.mib-2.system)

OID=1.3.6.1.2.1.1.1.0
  Path=iso.org.dod.internet.mgmt.mib-2.system.sysDescr.0
  Type=OctetString
  Value='Linux TS-X53 4.2.0'
OID=1.3.6.1.2.1.1.9.1.2.1
  Path=iso.org.dod.internet.mgmt.mib-2.system.sysORTable.sysOREntry.sysORID.1
  Type=ObjectIdentifier
  Value='1.3.6.1.6.3.11.2.3.1.1'
OID=1.3.6.1.2.1.1.9.1.2.2
  Path=iso.org.dod.internet.mgmt.mib-2.system.sysORTable.sysOREntry.sysORID.2
  Type=ObjectIdentifier
  Value='1.3.6.1.6.3.15.2.1.1'
OID=1.3.6.1.2.1.1.9.1.2.3
  Path=iso.org.dod.internet.mgmt.mib-2.system.sysORTable.sysOREntry.sysORID.3
  Type=ObjectIdentifier
  Value='1.3.6.1.6.3.10.3.1.1'
OID=1.3.6.1.2.1.1.9.1.2.4
  Path=iso.org.dod.internet.mgmt.mib-2.system.sysORTable.sysOREntry.sysORID.4
  Type=ObjectIdentifier
  Value='1.3.6.1.6.3.1'

Ich verstehs nicht :confused:

Windows Firewall auf der Maschine, auf der du das Programm ausführst? Es wird ja ein „bestimmter Port nach außen“ genutzt.

Hallo,

Hab die zwar testweise deaktiviert, aber kann nicht sein, dann würde die anderen SNMP-Tools auch nicht funktionieren.

Im Netzwerktrace ist die Anfrage an die NAS und auch deren Antwort zu sehen, also die Netzwerkkomunikation funktioniert zwischen Notebook und NAS.
Bliebt also nur noch das Stück zw. Netzwerkkarte und Software übrig.

Hallo Tuxtom007,

hast Du den Fehler gefunden?

Ich bekomme auch den Fehler „no reponse“ wenn ich den Script teste.

Wie kann man das Programm snmpq.exe gegen das Programm SnmpGet.exe auswechseln?
Weil nur den Programmnamen ändern funktioniert nicht, SnmpGet.exe kann nicht mit /v umgehen braucht -v, wo kann man das einstellen?

Tschau Hein09