CZ 
05.11.2024 Miriam VÍTEJTE V MÉM SVĚTĚ

Zjišťování topologie pomocí STP, SNMP a PHP

| Petr Macek - Macek |
Další článek, který popisuje využití jazyka PHP a protokolu SNMP pro zjišťování síťových údajů. Tentokrát se využívají informace z rozšířeného protokolu Spanning Tree Protocol (STP).
zobrazeno: 13 179x | Komentáře [5]

O autorovi:
Autorem tohoto článku je Petr Macek, kterého můžete kontaktovat na e-mailu petr.macek@kostax.cz.

Ve starších článcích jsem popsal, jak pomocí PHP ze SNMP vyčíst a prezentovat údaje z  CDP a LLDP protokolu. Pro kompletní zjištění síťového okolí je možné tyto informace doplnit o údaje ze Spanning Tree protokolu. O STP se zde již psalo v článcích Cisco IOS 9 - Spanning Tree Protocol a Cisco IOS 10 - Rapid Spanning Tree Protocol. Pro správné pochopení doporučuji alespoň první článek přečíst. STP nám neřekne tolik údajů jako LLDP nebo CDP, ale na rozdíl od výše zmiňovaných protokolů je implementován snad ve všech přepínačích s managementem.

STP používá jako ID prvku nejnižší MAC adresu zařízení uloženou v OID 1.3.6.1.2.1.17.1.1.0. STP MIB opět obsahuje informace o konfiguraci STP protokolu a tabulku se stavem portů. Jediným indexem této tabulky je index portu, který odpovídá indexu portu v IF-MIBu (intrface MIB) v tabulce portů (OID 1.3.6.1.2.1.2.2.1).

Z celé tabulky je zajímavý sloupec 1.3.6.1.2.1.17.2.15.1.8. Ten obsahuje buď svou nejnižší MAC adresu, pokud je prvek root bridge nebo MAC adresu protistrany, která vede k root bridge pro síťový segment. Proto jsou zajímavé pouze záznamy, kde je uložena jiná MAC adresa než nejnižší MAC tohoto prvku. Pokud takový záznam najdeme, s pomocí indexu se doptáme na jméno portu přes Bridge MIB a IF-MIB. Lze tedy zjišťovat pouze spoje směrem od konce větví ke kořenu (root bridge přepínači).

Teď tedy PHP kód

$ip = "192.168.1.1";
$community = "public";

// tato funkce pouze vycisti vracenou SNMP hodnotu, 
// snmp vraci vysledek vcetne typu, napr: INTEGER: 123

function uprav ($value)	{
  $value = trim($value);

  if (!strncasecmp("STRING:",$value,7))	{
	   $value = substr($value,8);
	   
     if ($value[0] == "\"" && $value[strlen($value)-1] == "\"")
	     $value = substr($value,1,strlen($value)-2);
	   
     return ($value);
  }
  else if (!strncasecmp("Timeticks:",$value,10))	{ // tady je to taky slozitejsi
    $value = substr($value,11);
  	$pos = strpos ($value, "(");
    if ($pos === false)	// je to obycejne cislo
	     return ($value);
	  else	{
	     $pos2 = strpos ($value,")");
	     return (trim(substr ($value, $pos+1,$pos2-$pos-1)));
	  }
  }
  else if (!strncasecmp("INTEGER:",$value,8))		{ // tady je to slozitejsi, v status a admin status je napr: down(2)
	  $value = substr($value,9);
  	$pos = strpos ($value, "(");
    if ($pos === false)	// je to obycejne cislo
	     return ($value);
	  else	{
	     $pos2 = strpos ($value,")");
	     return (substr ($value, $pos+1,$pos2-$pos-1));
	  }
  }
  else if (!strncasecmp("IpAddress:",$value,10))	
	   return (substr($value,11));
  else if (!strncasecmp("Hex-STRING:",$value,11))	
	   return (substr($value,12));
  else if (!strncasecmp("Gauge32:",$value,8))	
	   return (substr($value,9));
  else if (!strncasecmp("Counter32:",$value,10))	
	   return (substr($value,11));
  else
	   return trim($value);
}	       

// zjistuju svoje chassis ID (stp id)
$stp_id = snmpget($ip, $community, "SNMPv2-SMI::mib-2.17.1.1.0");  
if ($stp_id)  {
    $stp_id = uprav ($stp_id);
    echo "Chassis ID je $stp_id<br/><br/>\n";
   
    // zjistuju stp okoli
    $porty = snmprealwalk($ip, $community, "1.3.6.1.2.1.17.2.15.1.8");    
    
   foreach ($porty as $key=>$value)       {
      $value = uprav($value);

      // pro vsechny nalezene porty si zjistim index portu
      $pos = strrpos ($key,".");
      $index = substr ($key,-(strlen($key)-$pos-1));    

      // je to index z mibu bridge, zeptame se tedy tam
      $index_mib = uprav (snmpget ($ip, $community, "1.3.6.1.2.1.17.1.4.1.2.$index"));
      $nazev_portu = uprav (snmpget ($ip], $community, "1.3.6.1.2.1.2.2.1.2.$index_mib"));
      
      // z casti vracene hodnoty poskladame MAC adresu            
      $sl = explode (" ", $value);
      foreach ($sl as $xkey=>$sloupec) {
          $sloupec = str_pad ($sloupec, 2, "0", STR_PAD_LEFT);
          $sl[$xkey] = $sloupec;
      }
      $mac = $sl[2] . ":" . $sl[3] . ":" . $sl[4] . ":" . $sl[5] . ":" . $sl[6] . ":" . $sl[7];

      // pokud se mac nerovna ID switche, nasli jsme port smerujici k root bridge
      if ($mac != $stp_id)        
        echo "Nalez na portu $nazev_portu, protistrana $mac<br/>\n";
	} 
else
  echo "Spatne SNMP udaje nebo STP MIB neni implementovan v zarizeni";

Jak jsem zmínil - STP nám nedá tolik informací jako ostatní protokoly, ale pokud tyto informace vyčteme ze všech prvků, výsledkem by měla být celá topologie.

Související články:

SNMP

Protokol SNMP (Simple Network Management Protocol) je velice užitečný pro správu počítačové sítě.

Pokud se chcete vyjádřit k tomuto článku, využijte komentáře níže.

Komentáře
  1. [1] Dragonn

    A jakým způsobem mi tyto informace pomohou k sestavení topologie sítě? Switch sice možná ví, kterou cestou se dostane k Root Bridge, ale už nemá nejmenší šanci, jak zjistit ke komu jsem skutečně připojen

    Neděle, 04.05.2014 15:23 | odpovědět
  2. [2] Petr Macek

    Topologii je v tomto pripade mysleno zapojeni switchu, ne vsech zarizeni v siti. Uz jsem zde psal clanky na zjistovani z CDP a LLDP. Pokud je zajem, muzu doplnit jeste o ziskavani udaju z dalsich MIBU (napr. prepinaci tabulka switche) a s tim uz se zjistit i pripojeni koncovych zarizeni

    Úterý, 13.05.2014 23:20 | odpovědět
  3. [3] Hasak

    Protokoly CDP a LLDP nejsou implementovany ve vsech HW. Jedina moznost jak generovat sitovou topologii je pomoci snmp protokolu a prohledavani. Tzn. hledani nejkratsi cesty k mac adrese nalezene na nejakem switchi/bridgi. Nebo existuje nejaky jiny exefktivni zpusob prohledavani?

    Pátek, 09.01.2015 07:58 | odpovědět
  4. [4] Petr Zima

    Dá se to i zjednodušit přes OID 1.3.6.1.2.1.17.2.7, které vrací číslo portu vedoucího k root bridge. Když je switch sám root bridge, vrací 0.

    Čtvrtek, 02.04.2015 22:56 | odpovědět
  5. [5] MichaelsCZ

    Doporučuji vyzkoušet nedi.ch

    Zajímavý nástroj - udělá topologi, zobrazí switche a info o jejich portech, dohledá ale i nody s IP a MAC takže lze dohledat i zpětně, kde bylo jaké zařízení připojené k síti.

    Pátek, 08.10.2021 12:09 | odpovědět
Přidat komentář

Vložit tag: strong em link

Nápověda:
  • maximální délka komentáře je 2000 znaků
  • HTML tagy nejsou povoleny (budou odstraněny), použít se mohou pouze speciální tagy (jsou uvedeny nad vstupním polem)
  • nový řádek (ENTER) ukončí odstavec a začne nový
  • pokud odpovídáte na jiný komentář, vložte na začátek odstavce (řádku) číslo komentáře v hranatých závorkách