netdisco / snmp-info

Other
39 stars 32 forks source link

Meraki AP can't be discovered as sysUptime isn't implemented #397

Open JeroenvIS opened 4 years ago

JeroenvIS commented 4 years ago

As reported by 'fiet' on IRC: Meraki access point can't be discovered by Netdisco. Root cause appears to be that sysUptime isn't returned. AFAIK that's a mandatory object so I believe that Meraki is not conforming to the standards, but still opening this ticket for reference and to see if workarounds are possible.

The bit where sysUptime is checked, causing discovery to fail: https://github.com/netdisco/netdisco/blob/8ff595c32113fb3749d9bf10c37b4cd374e0b70c/lib/App/Netdisco/Transport/SNMP.pm#L246

JeroenvIS commented 4 years ago

Discover output as provided by fiet:

SNMP::Info::_global uptime : DISMAN-EVENT-MIB::sysUpTimeInstance : .1.3.6.1.2.1.1.3.0 SNMP::Info::_global uptime : DISMAN-EVENT-MIB::sysUpTimeInstance : .1.3.6.1.2.1.1.3.0 SNMP::Info::_global uptime : DISMAN-EVENT-MIB::sysUpTimeInstance : .1.3.6.1.2.1.1.3.0 SNMP::Info::_global uptime : DISMAN-EVENT-MIB::sysUpTimeInstance : .1.3.6.1.2.1.1.3.0 orker check/base/0 [2991] 2020-06-16 17:51:22 debug Discover is able to run. [2991] 2020-06-16 17:51:22 debug => running workers for phase: early [2991] 2020-06-16 17:51:22 debug -> run worker early/properties/100 [2991] 2020-06-16 17:51:22 debug snmp reader cache warm: [x.x.1.140] [2991] 2020-06-16 17:51:22 debug [x.x.1.140:161] try_connect with ver: 2, class: SNMP::Info, comm: SNMP::Info::_global(uptime) NOSUCHOBJECT at /home/netdisco/perl5/lib/perl5/App/Netdisco/Transport/SNMP.pm line 245. [2991] 2020-06-16 17:51:22 debug [x.x.1.140:161] try_connect with ver: 1, class: SNMP::Info, comm: SNMP::Info::_global(uptime) (noSuchName) There is no such variable name in this MIB. at /home/netdisco/perl5/lib/perl5/App/Netdisco/Transport/SNMP.pm line 245. [2991] 2020-06-16 17:51:22 debug [x.x.1.140:161] try_connect with ver: 2, class: SNMP::Info, comm: SNMP::Info::_global(uptime) Timeout at /home/netdisco/perl5/lib/perl5/App/Netdisco/Transport/SNMP.pm line 245. [2991] 2020-06-16 17:51:25 debug [x.x.1.140:161] try_connect with ver: 1, class: SNMP::Info, comm: SNMP::Info::_global(uptime) Timeout at /home/netdisco/perl5/lib/perl5/App/Netdisco/Transport/SNMP.pm line 245. [2991] 2020-06-16 17:51:28 debug discover failed: could not SNMP connect to x.x.1.140 [2991] 2020-06-16 17:51:28 debug -> run worker early/properties/100 [2991] 2020-06-16 17:51:28 debug -> run worker early/properties/100 [2991] 2020-06-16 17:51:28 debug -> run worker early/properties/100 [2991] 2020-06-16 17:51:28 debug => running workers for phase: main [2991] 2020-06-16 17:51:28 debug -> run worker main/canonicalip/100 [2991] 2020-06-16 17:51:28 debug -> run worker main/entities/100 [2991] 2020-06-16 17:51:28 debug -> run worker main/neighbors/100 [2991] 2020-06-16 17:51:28 debug -> run worker main/neighbors/100 [2991] 2020-06-16 17:51:28 debug -> run worker main/neighbors/100 [2991] 2020-06-16 17:51:28 debug -> run worker main/portpower/100 [2991] 2020-06-16 17:51:28 debug -> run worker main/portproperties/100 [2991] 2020-06-16 17:51:28 debug -> run worker main/vlans/100 [2991] 2020-06-16 17:51:28 debug -> run worker main/wireless/100 [2991] 2020-06-16 17:51:28 debug -> run worker main/withnodes/0 [2991] 2020-06-16 17:51:28 info discover: finished at Tue Jun 16 19:51:28 2020 [2991] 2020-06-16 17:51:28 info discover: status defer: discover failed: could not SNMP connect to x.x.1.140

pioevogel commented 4 years ago

I raised an issue with Meraki for this. Will update when I receive feedback.

DISMAN-EVENT-MIB::sysUpTimeInstance = No Such Object available on this agent at this OID

inphobia commented 4 years ago

netdisco requires a valid return value when it issues uptime().

however, that does not mean it has to be the standard. as long as uptime() returns a value netdisco accepts you're good. i had the same issue with exinda support:

https://github.com/netdisco/snmp-info/blob/543072ca259a21c7f9f3f852b6b6df9f7acbbfb8/lib/SNMP/Info/Layer2/Exinda.pm#L48-L60

https://github.com/netdisco/snmp-info/blob/543072ca259a21c7f9f3f852b6b6df9f7acbbfb8/lib/SNMP/Info/Layer2/Exinda.pm#L178-L180

if you have an uptime value in a meraki specific mib this can most likely be made to work with netdisco

ollyg commented 3 years ago

The solution from @inphobia is fine (I would even be happy with an uptime() which returned "0"), but the problem with implementing it here is that this example seems to have no device specific class.

So, we have nowhere to implement this specific behaviour, and I really don't think it's a good idea to hack this globally (which effectively means we should just stop checking for sysUptime).

note for fiet: is there not a more specific device class to use?

pioevogel commented 3 years ago

Hi,

all I can find is: SNMPv2-MIB::sysORUpTime.1 = Timeticks: (0) 0:00:00.00 SNMPv2-MIB::sysORUpTime.2 = Timeticks: (0) 0:00:00.00 SNMPv2-MIB::sysORUpTime.3 = Timeticks: (0) 0:00:00.00 SNMPv2-MIB::sysORUpTime.4 = Timeticks: (0) 0:00:00.00

Not sure if this is what you're looking for. And as you can see they all return '0'. Meraki does not use proprietary MIB's, only standard:

_Proprietary MIB

Additional Meraki-specific information can be found in the MERAKI-CLOUD-CONTROLLER-MIB, which is located under Organization > Settings > SNMP. Please note that this MIB is used to poll the dashboard, not Meraki devices locally. Please reference the standard MIBs above for options when polling local devices._

JeroenvIS commented 3 years ago

@ollyg interesting details in Netdisco::Transport::SNMP.pm: in _try_connect we call _try_read, which requires that a device returns uptime() combined with either layers() or description() (and also class() is required). Ie now we have 'uptime and class and (layers or description)' before we consider a connection as successful. Wouldn't this also make discovery of eg Exinda impossible, unless the device class is already known prior to connecting? Because the class has to be set in advance, otherwise Exinda wouldn't return uptime() either.

We could consider 'class and (uptime or layers or description)' as logic here, but not sure if that would break anything else.

ollyg commented 3 years ago

@JeroenvIS yes you are right! I realised later my error in thinking. The more specific device class is only assigned after initial connection, but if we need specific device class code to make that initial connection work... 🤯

Yeah sure we could reduce the requirements -- that is, make them less strict on the RFC. Honestly the basic requirement is probably "just enough to get the specific identification done" and for that we need... layers(), OR description(), OR id(), anything else? Not uptime(), as far as I know.

After that, any missing RFC parts can be provided by the specific class.

ollyg commented 3 years ago

It did occur to me that perhaps Netdisco is insistent on uptime() because without it, macsuck would be messed up (calculating time last seen, wrapping clock, etc).