Friday 10 October 2014

Using SNMP to recover access to a device

Summary


I am sure many of you, at some point, have completed an installation at a remote office and come away from site forgetting to check remote access.  This can be quite painful if the site is many hours away or even in a different country.  Maybe it wasn't you but a more junior engineer ;)

All is not lost if you have the following:

1) SNMP write access to the remote device
2) The remote device has access to a TFTP or SCP server

If so then you are in luck!  With these two components we can create a config snippet to add the missing pieces such as (and not limited to):

  • Overwriting the enable secret
  • Enabling ip https server to create an SSH key
  • Enabling telnet and a one time password

Recovering Access


Step 1

First create the config snippet and upload this to your TFTP server.  It does not have to be a complete config as we are going to merge it with the running configuration.

Example:

 

service tcp-keepalives-in
service tcp-keepalives-out
username tempaccess one-time password cisco

enable secret recovery
!

line vty 0 4
transport input telnet ssh
login local
end


NOTE: If you have AAA configured then your sample may look like this:

service tcp-keepalives-in
service tcp-keepalives-out
username tempaccess one-time password cisco

aaa authentication login VTY-LOCAL local
enable secret recovery
!

line vty 0 4
transport input telnet ssh
login authentication VTY-LOCAL
end

Upload the configuration snippet to the root directory of the TFTP server.


Step 2

The second step is to gather details and test SNMP access to the device.

You will need:

1) IP address of the device you wish to recover
2) SNMP read/write access
3) The IP address of the TFTP server
4) A config snippet uploaded to the root directory of the TFTP server

For this example I will use the following:

IP: 172.31.0.5
SNMP Community (v2c): SNMPRW
TFTP Server: 172.31.0.1
Config snippet: recovery-snippet

The commands here are sent from a Linux host with the Net-SNMP library installed.  This can be done from other operating systems or utilities but the command line options may vary.

Here we can see my lab device is pingable but I have no access via ssh or telnet.  Telnet wasn't configured and I cannot recommend it but we are going to use it temporarily to get us out of a tricky spot.

$ ssh 172.31.0.5
ssh: connect to host 172.31.0.5 port 22: Connection refused

$ telnet 172.31.0.5
Trying 172.31.0.5...
telnet: Unable to connect to remote host: Connection refused

$ ping 172.31.0.5
PING 172.31.0.5 (172.31.0.5) 56(84) bytes of data.
64 bytes from 172.31.0.5: icmp_seq=1 ttl=255 time=0.302 ms
64 bytes from 172.31.0.5: icmp_seq=2 ttl=255 time=0.428 ms
64 bytes from 172.31.0.5: icmp_seq=3 ttl=255 time=0.452 ms
64 bytes from 172.31.0.5: icmp_seq=4 ttl=255 time=0.273 ms


It's a good idea to test SNMP access before we try and recover the device:


snmpget  -v2c -cSNMPRW 172.31.0.5 1.3.6.1.2.1.1.5.0



OID 1.3.6.1.2.1.1.5 is sysName and should return the hostname configured on our remote device:

$snmpget  -v2c -cSNMPRW 172.31.0.5 1.3.6.1.2.1.1.5.0
iso.3.6.1.2.1.1.5.0 = STRING: "Test-Router1"


Step 3

We are now ready to apply the SNMP recovery method as follows:


snmpset -v 2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.14.43 i 5
snmpset -v 2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.2.43 i 1
snmpset -v 2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.3.43 i 1
snmpset -v 2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.4.43 i 4
snmpset -v 2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.5.43 a 172.31.0.1
snmpset -v 2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.6.43 s recovery-snippet
snmpset -v 2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.14.43 i 1
 

NOTE: You need to delete the job once completed (see step after checking status below)

The above code will create a row (row 43) in the ccCopy table and then activate it. 

And here is the output when I ran this against my test device:



$ snmpset -v2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.14.43 i 5
iso.3.6.1.4.1.9.9.96.1.1.1.1.14.43 = INTEGER: 5
$ snmpset -v2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.2.43 i 1
iso.3.6.1.4.1.9.9.96.1.1.1.1.2.43 = INTEGER: 1
$ snmpset -v2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.3.43 i 1
iso.3.6.1.4.1.9.9.96.1.1.1.1.3.43 = INTEGER: 1
$ snmpset -v2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.4.43 i 4
iso.3.6.1.4.1.9.9.96.1.1.1.1.4.43 = INTEGER: 4
$ snmpset -v2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.5.43 a 172.31.0.1
iso.3.6.1.4.1.9.9.96.1.1.1.1.5.43 = IpAddress: 172.31.0.1
$ snmpset -v2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.6.43 s recovery-snippet
iso.3.6.1.4.1.9.9.96.1.1.1.1.6.43 = STRING: "recovery-snippet"
$ snmpset -v2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.14.43 i 1
iso.3.6.1.4.1.9.9.96.1.1.1.1.14.43 = INTEGER: 1


We can check the status as follows:


$ snmpget -v2c -cSNMPRW 172.31.0.5 .1.3.6.1.4.1.9.9.96.1.1.1.1.10.43
iso.3.6.1.4.1.9.9.96.1.1.1.1.10.43 = INTEGER: 3


1=waiting, 2=running, 3=successful, 4=failed

As this was successful we will delete the row then check the status (which should fail as we just deleted it):


  
$ snmpset -v2c -cSNMPRW 172.31.0.5 1.3.6.1.4.1.9.9.96.1.1.1.1.14.43 i 6
iso.3.6.1.4.1.9.9.96.1.1.1.1.14.43 = INTEGER: 6
$ snmpget -v2c -cSNMPRW 172.31.0.5 .1.3.6.1.4.1.9.9.96.1.1.1.1.10.43
iso.3.6.1.4.1.9.9.96.1.1.1.1.10.43 = No Such Instance currently exists at this OID


And now to test access...

$ telnet 172.31.0.5
Trying 172.31.0.5...
Connected to 172.31.0.5.
Escape character is '^]'.


User Access Verification

Username:



\o/ Now we can login with our one time password, create an SSH key, test SSH access then remove the telnet access, save the config.

The above was demonstrated with SNMP version 2 but this can be done with Version 1, 2 or 3 (recommended).

If you want to know what the OID's are then you can find them here:

MIB Object Name
Object Identifier
Values used in the example
ccCopyEntryRowStatus.1.3.6.1.4.1.9.9.96.1.1.1.1.14
active (1) createAndGo(4)
createAndWait(5)
destroy(6)
ccCopyProtocol1.3.6.1.4.1.9.9.96.1.1.1.1.2
tftp(1)
rcp(2)
ccCopySourceFileType.1.3.6.1.4.1.9.9.96.1.1.1.1.3
networkFile(1)
iosFile(2)
startupConfig(3)
runningConfig(4)
terminal(5)
ccCopyDestFileType.1.3.6.1.4.1.9.9.96.1.1.1.1.4
ccCopyServerAddress.1.3.6.1.4.1.9.9.96.1.1.1.1.5
ccCopyFileName.1.3.6.1.4.1.9.9.96.1.1.1.1.6
ccCopyState.1.3.6.1.4.1.9.9.96.1.1.1.1.10waiting(1)
running(2)
successful(3)
failed(4)


The following Cisco support was very useful in putting this guide together:

https://supportforums.cisco.com/document/10046/how-copy-configuration-files-and-cisco-ios-routers-use-snmp

The comments section include information on using scp. 

You can also retrieve or push a whole configuration using the same technique.  See the following blog for more details:

https://ccie20728.wordpress.com/2008/05/20/get-the-cisco-configuration-over-snmp/