1package ios; 2## 3## @PACKAGE@ @VERSION@ 4@copyright@ 5# 6# RANCID - Really Awesome New Cisco confIg Differ 7# 8# ios.pm - Cisco IOS rancid procedures 9 10use 5.010; 11use strict 'vars'; 12use warnings; 13no warnings 'uninitialized'; 14require(Exporter); 15our @ISA = qw(Exporter); 16 17use rancid @VERSION@; 18 19our $proc; 20our $ios; 21our $found_version; 22our $found_env; 23our $found_diag; 24our $found_inventory; 25our $config_register; # configuration register value 26 27our %hwbuf; # defined in ShowContCbus 28our %hwmemc; # defined in ShowContCbus 29our %hwmemd; # defined in ShowContCbus 30our %hwucode; # defined in ShowContCbus 31our $supbootdisk; # skip sup-bootflash if sup-bootdisk 32 # worked 33our $type; # device model, from ShowVersion 34our %ucode; # defined in ShowContCbus 35 36our $ssp; # SSP/SSE info, from ShowVersion 37our $sspmem; # SSP/SSE info, from ShowVersion 38 39our $C0; # output formatting control 40our $E0; 41our $H0; 42our $I0; 43our $DO_SHOW_VLAN; 44 45our $vss_show_module; # Use "show module switch" on 6k VSS systems 46 47@ISA = qw(Exporter rancid main); 48#XXX @Exporter::EXPORT = qw($VERSION @commandtable %commands @commands); 49 50# load-time initialization 51sub import { 52 0; 53} 54 55# post-open(collection file) initialization 56sub init { 57 $proc = ""; 58 $ios = "IOS"; 59 $found_version = 0; 60 $found_env = 0; 61 $found_diag = 0; 62 $found_inventory = 0; 63 $config_register = undef; # configuration register value 64 65 $supbootdisk = 0; # skip sup-bootflash if sup-bootdisk 66 # worked 67 $type = undef; # device model, from ShowVersion 68 69 $ssp = 0; # SSP/SSE info, from ShowVersion 70 $sspmem = undef; # SSP/SSE info, from ShowVersion 71 72 $C0 = 0; # output formatting control 73 $E0 = 0; 74 $H0 = 0; 75 $I0 = 0; 76 $DO_SHOW_VLAN = 0; 77 78 $vss_show_module = 0; # Use "show module switch" on 6k VSS systems 79 # add content lines and separators 80 ProcessHistory("","","","!RANCID-CONTENT-TYPE: $devtype\n!\n"); 81 ProcessHistory("COMMENTS","keysort","B0","!\n"); 82 ProcessHistory("COMMENTS","keysort","D0","!\n"); 83 ProcessHistory("COMMENTS","keysort","F0","!\n"); 84 ProcessHistory("COMMENTS","keysort","G0","!\n"); 85 86 0; 87} 88 89# main loop of input of device output 90sub inloop { 91 my($INPUT, $OUTPUT) = @_; 92 my($cmd, $rval); 93 94TOP: while(<$INPUT>) { 95 tr/\015//d; 96 if (/[>#]\s?exit$/) { 97 $clean_run = 1; 98 last; 99 } 100 if (/^Error:/) { 101 print STDOUT ("$host clogin error: $_"); 102 print STDERR ("$host clogin error: $_") if ($debug); 103 $clean_run = 0; 104 last; 105 } 106 while (/[>#]\s*($cmds_regexp)\s*$/) { 107 $cmd = $1; 108 if (!defined($prompt)) { 109 $prompt = ($_ =~ /^([^#>]+[#>])/)[0]; 110 $prompt =~ s/([][}{)(+\\])/\\$1/g; 111 print STDERR ("PROMPT MATCH: $prompt\n") if ($debug); 112 } 113 print STDERR ("HIT COMMAND:$_") if ($debug); 114 if (! defined($commands{$cmd})) { 115 print STDERR "$host: found unexpected command - \"$cmd\"\n"; 116 $clean_run = 0; 117 last TOP; 118 } 119 if (! defined(&{$commands{$cmd}})) { 120 printf(STDERR "$host: undefined function - \"%s\"\n", 121 $commands{$cmd}); 122 $clean_run = 0; 123 last TOP; 124 } 125 $rval = &{$commands{$cmd}}($INPUT, $OUTPUT, $cmd); 126 delete($commands{$cmd}); 127 if ($rval == -1) { 128 $clean_run = 0; 129 last TOP; 130 } 131 } 132 } 133} 134 135# This routine parses "show version" 136sub ShowVersion { 137 my($INPUT, $OUTPUT, $cmd) = @_; 138 my($slave, $slaveslot); 139 print STDERR " In ShowVersion: $_" if ($debug); 140 141 while (<$INPUT>) { 142 tr/\015//d; 143 if (/^$prompt/) { $found_version = 1; last}; 144 next if (/^(\s*|\s*$cmd\s*)$/); 145 next if (/^\s+\^$/); 146 next if (/^Load for five/); 147 next if (/^Time source is/); 148 return(1) if (/Line has invalid autocommand /); 149 return(1) if (/(invalid (input|command) detected|type help or )/i); 150 return(0) if ($found_version); # Only do this routine once 151 return(-1) if (/(?:%|command)? authorization failed/i); 152 # the pager can not be disabled per-session on the PIX 153 if (/^(<-+ More -+>)/) { 154 my($len) = length($1); 155 s/^$1\s{$len}//; 156 } 157 158 if (/^Slave in slot (\d+) is running/) { 159 $slave = " Slave:"; 160 $slaveslot = ", slot $1"; 161 next; 162 } 163 if (/cisco ios.*(IOS-)?XE/i) { $ios = "XE"; } 164 if (/^Application and Content Networking .*Software/) { $type = "CE"; } 165 # treat the ACE like the Content Engines for matching endofconfig 166 if (/^Cisco Application Control Software/) { $type = "CE"; } 167 if (/^Cisco Storage Area Networking Operating System/) { $type = "SAN";} 168 if (/^Cisco Nexus Operating System/) { $type = "NXOS";} 169 /^Application and Content Networking Software Release /i && 170 ProcessHistory("COMMENTS","keysort","F1", "!Image: $_") && next; 171 /^Cisco Secure PIX /i && 172 ProcessHistory("COMMENTS","keysort","F1", "!Image: $_") && next; 173 # ASA "time-based licenses" - eg: bot-net 174 /^This (PIX|platform) has a time-based license that will expire in\s+(\d{2,})\s+day.*$/ && 175 ProcessHistory("COMMENTS","keysort","D1", 176 "!This $1 has a time-based license\n") && next; 177 # PIX 6 fail-over license, as in "This PIX has an Unrestricted (UR) 178 # license." PIX 7 as "his platform has ..." 179 /^This (PIX|platform) has an?\s+(.*)$/ && 180 ProcessHistory("COMMENTS","keysort","D1", "!$_") && next; 181 /^(Cisco )?IOS .* Software,? \(([A-Za-z0-9_-]*)\), .*Version\s+(.*)$/ && 182 ProcessHistory("COMMENTS","keysort","F1", 183 "!Image:$slave Software: $2, $3\n") && next; 184 /^([A-Za-z-0-9_]*) Synced to mainline version: (.*)$/ && 185 ProcessHistory("COMMENTS","keysort","F2", 186 "!Image:$slave $1 Synced to mainline version: $2\n") && next; 187 /^Compiled (.*)$/ && 188 ProcessHistory("COMMENTS","keysort","F3", 189 "!Image:$slave Compiled: $1\n") && next; 190 /^ROM: (IOS \S+ )?(System )?Bootstrap.*(Version.*)$/ && 191 ProcessHistory("COMMENTS","keysort","G1", 192 "!ROM Bootstrap: $3\n") && next; 193 if (/^Hardware:\s+(.*), (.* RAM), CPU (.*)$/) { 194 ProcessHistory("COMMENTS","keysort","A1", 195 "!Chassis type: $1 - a PIX\n"); 196 ProcessHistory("COMMENTS","keysort","A2", 197 "!CPU: $3\n"); 198 ProcessHistory("COMMENTS","keysort","B1", "!Memory: $2\n"); 199 } 200 /^serial number:\s+(.*)$/i && 201 ProcessHistory("COMMENTS","keysort","C1", "!Serial Number: $1\n") && 202 next; 203 # More PIX stuff 204 /^Encryption hardware device\s+:\s+(.*)/ && 205 ProcessHistory("COMMENTS","keysort","A3", "!Encryption: $1\n") && 206 next; 207 /^running activation key\s*:\s+(.*)/i && 208 ProcessHistory("COMMENTS","keysort","D2", "!Key: $1\n") && 209 next; 210 # Flash on the PIX or FWSM (FireWall Switch Module) 211 /^Flash(\s+\S+)+ \@ 0x\S+,\s+(\S+)/ && 212 ProcessHistory("COMMENTS","keysort","B2", "!Memory: Flash $2\n") && 213 next; 214 # 3750 switch stacks 215 next if (/^Model revision number/ && $type eq "3750"); 216 next if (/^Motherboard/ && $type eq "3750"); 217 next if (/^Power supply/ && $type eq "3750"); 218 /^Model number : (.*)$/ && $type eq "3750" && 219 ProcessHistory("COMMENTS","keysort","C2", "!Model number: $1\n") && 220 next; 221 /^System serial number : (.*)$/ && $type eq "3750" && 222 ProcessHistory("COMMENTS","keysort","C2", "!Serial number: $1\n") && 223 next; 224 # CatOS 3500xl stuff 225 /^system serial number\s*:\s+(.*)$/i && 226 ProcessHistory("COMMENTS","keysort","C1", "!Serial Number: $1\n") && 227 next; 228 /^Model / && 229 ProcessHistory("COMMENTS","keysort","C2", "!$_") && next; 230 /^Motherboard / && 231 ProcessHistory("COMMENTS","keysort","C3", "!$_") && next; 232 /^Power supply / && 233 ProcessHistory("COMMENTS","keysort","C4", "!$_") && next; 234 235 /^Activation Key:\s+(.*)$/ && 236 ProcessHistory("COMMENTS","keysort","C2", "!$_") && next; 237 /^ROM: \d+ Bootstrap .*(Version.*)$/ && 238 ProcessHistory("COMMENTS","keysort","G2", 239 "!ROM Image: Bootstrap $1\n!\n") && next; 240 /^ROM: .*(Version.*)$/ && 241 ProcessHistory("COMMENTS","keysort","G3","!ROM Image: $1\n") && next; 242 /^BOOTFLASH: .*(Version.*)$/ && 243 ProcessHistory("COMMENTS","keysort","G4","!BOOTFLASH: $1\n") && next; 244 /^BOOTLDR: .*(Version.*)$/ && 245 ProcessHistory("COMMENTS","keysort","G4","!BOOTLDR: $1\n") && next; 246 /^System image file is "([^\"]*)", booted via (\S*)/ && 247# removed the booted source due to 248# CSCdk28131: cycling info in 'sh ver' 249# ProcessHistory("COMMENTS","keysort","F4","!Image: booted via $2, $1\n") && 250 ProcessHistory("COMMENTS","keysort","F4","!Image: booted $1\n") && 251 next; 252 /^System image file is "([^\"]*)"$/ && 253 ProcessHistory("COMMENTS","keysort","F5","!Image: $1\n") && next; 254 # 2800 at least don't have a processor line 255 if ((/(\S+(?:\sseries)?)\s+(?:\(([^)]+)\)\s+processor|\(revision[^)]+\)).*\s+with (\S+k) bytes/i) || 256 (/isco\s+(\S+)\s+\(.+\)\s+with (\S+[kK]) bytes/)) { 257 $proc = $1; 258 my($cpu) = $2; 259 my($mem) = $3; 260 261 # the next line ought to be the more specific cpu info, grab it. 262 # yet, some boards/IOS vers have a processor ID line between these 263 # two. grrr. make sure we dont grab the "software" junk that 264 # follows these lines by looking for "CPU at " or the 2600s 265 # "processor: " unique string. there are undoubtedly many other 266 # incantations. for a slave, we dont get this info, its just a 267 # blank line. 268 $_ = <$INPUT>; 269 if (/processor board id/i) { 270 my($sn); 271 272 if (/processor board id (\S+)/i) { 273 $sn = $1; 274 $sn =~ s/,$//; 275 ProcessHistory("COMMENTS","keysort","D9", 276 "!Processor ID: $sn\n"); 277 } 278 $_ = <$INPUT>; 279 } 280 # for 6500 sup-2t 281 if ($cpu =~ /M8572/) { 282 if (defined($cpu)) { 283 s/^ CPU://; 284 ProcessHistory("COMMENTS","keysort","A3", "!CPU: $cpu, $_"); 285 } 286LINE: while (<$INPUT>) { 287 last LINE if /^\s*$/; 288 ProcessHistory("COMMENTS","keysort","A3", "!CPU: $_"); 289 last LINE if /^\s*I-cache/; 290 } 291 undef ($cpu); 292 } 293 $_ = "" if (! /(cpu at |processor: |$cpu processor,)/i); 294 tr/\015//d; 295 s/implementation/impl/i; 296 if ($_ !~ /^\s*$/) { 297 chomp; 298 s/^/, /; 299 } 300 301 if ($proc eq "CSC") { 302 $type = "AGS"; 303 } elsif ($proc eq "CSC4") { 304 $type = "AGS+"; 305 } elsif ($proc =~ /1900/) { 306 $type = "1900"; 307 } elsif ($proc =~ /2811/) { 308 $type = "2800"; 309 } elsif ($proc =~ /^ME-3400/) { 310 $type = "ME3400"; 311 } elsif ($proc =~ /^ME-C37/) { 312 $type = "ME3700"; 313 } elsif ($proc =~ /^ME-C65/) { 314 $type = "ME6500"; 315 } elsif ($proc =~ /C3750/) { 316 $type = "3750"; 317 } elsif ($proc =~ /^(AS)?25[12][12]/) { 318 $type = "2500"; 319 } elsif ($proc =~ /261[01]/ || $proc =~ /262[01]/) { 320 $type = "2600"; 321 } elsif ($proc =~ /WS-C29/) { 322 $type = "2900XL"; 323 } elsif ($proc =~ /WS-C355/) { 324 $type = "3550"; 325 } elsif ($proc =~ /WS-C35/) { 326 $type = "3500XL"; 327 } elsif ($proc =~ /^36[0246][0-9]/) { 328 $type = "3600"; 329 } elsif ($proc =~ /^37/) { 330 $type = "3700"; 331 } elsif ($proc =~ /WS-C375/) { 332 $type = "3750"; 333 } elsif ($proc =~ /^38/) { 334 $type = "3800"; 335 } elsif ($proc =~ /WS-C45/) { 336 $type = "4500"; 337 } elsif ($proc =~ /^AS5300/) { 338 $type = "AS5300"; 339 } elsif ($proc =~ /^AS5350/) { 340 $type = "AS5350"; 341 } elsif ($proc =~ /^AS5400/) { 342 $type = "AS5400"; 343 } elsif ($proc =~ /^ASR920/) { 344 $type = "ASR920"; 345 } elsif ($proc =~ /6000/) { 346 $type = "6000"; 347 } elsif ($proc eq "WK-C65") { 348 $type = "6500"; 349 } elsif ($proc =~ /WS-C6509/) { 350 $type = "6500"; 351 } elsif ($proc eq "RP") { 352 $type = "7000"; 353 } elsif ($proc eq "RP1") { 354 $type = "7000"; 355 } elsif ($proc =~ /720[246]/) { 356 $type = "7200"; 357 } elsif ($proc =~ /^73/) { 358 $type = "7300"; 359 } elsif ($proc eq "RSP7000") { 360 $type = "7500"; 361 } elsif ($proc =~ /RSP\d/) { 362 $type = "7500"; 363 } elsif ($proc =~ /OSR-76/) { 364 $type = "7600"; 365 } elsif ($proc =~ /CISCO76/) { 366 $type = "7600"; 367 } elsif ($proc =~ /1200[48]\/(GRP|PRP)/ || $proc =~ /1201[26]\/(GRP|PRP)/) { 368 $type = "12000"; 369 } elsif ($proc =~ /1201[26]-8R\/(GRP|PRP)/) { 370 $type = "12000"; 371 } elsif ($proc =~ /1240[48]\/(GRP|PRP)/ || $proc =~ /1241[06]\/(GRP|PRP)/) { 372 $type = "12400"; 373 } elsif ($proc =~ /AIR-L?AP1[12][1234][[1234]/) { 374 $type="Aironet"; 375 } else { 376 $type = $proc; 377 } 378 379 print STDERR "TYPE = $type\n" if ($debug); 380 ProcessHistory("COMMENTS","keysort","A1", 381 "!Chassis type:$slave $proc\n"); 382 ProcessHistory("COMMENTS","keysort","B1", 383 "!Memory:$slave main $mem\n"); 384 if (defined($cpu)) { 385 ProcessHistory("COMMENTS","keysort","A3", 386 "!CPU:$slave $cpu$_$slaveslot\n"); 387 } 388 next; 389 } 390 if (/(\S+) Silicon\s*Switch Processor/) { 391 if (!$C0) { 392 $C0 = 1; ProcessHistory("COMMENTS","keysort","C0","!\n"); 393 } 394 ProcessHistory("COMMENTS","keysort","C2","!SSP: $1\n"); 395 $ssp = 1; 396 $sspmem = $1; 397 next; 398 } 399 /^(\d+[kK]) bytes of multibus/ && 400 ProcessHistory("COMMENTS","keysort","B2", 401 "!Memory: multibus $1\n") && next; 402 /^(\d+[kK]) bytes of (non-volatile|NVRAM)/ && 403 ProcessHistory("COMMENTS","keysort","B3", 404 "!Memory: nvram $1\n") && next; 405 /^(\d+[kK]) bytes of (flash memory|processor board System flash|ATA CompactFlash)/ && 406 ProcessHistory("COMMENTS","keysort","B5","!Memory: flash $1\n") && 407 next; 408 /^(\d+[kK]) bytes of .*flash partition/ && 409 ProcessHistory("COMMENTS","keysort","B6", 410 "!Memory: flash partition $1\n") && next; 411 /^(\d+[kK]) bytes of Flash internal/ && 412 ProcessHistory("COMMENTS","keysort","B4", 413 "!Memory: bootflash $1\n") && next; 414 if (/^(\d+[kK]) bytes of (Flash|ATA)?.*PCMCIA .*(slot|disk) ?(\d)/i) { 415 ProcessHistory("COMMENTS","keysort","B7", 416 "!Memory: pcmcia $2 $3$4 $1\n"); 417 next; 418 } 419 if (/^(\d+[kK]) bytes of (slot|disk)(\d)/i) { 420 ProcessHistory("COMMENTS","keysort","B7", 421 "!Memory: pcmcia $2$3 $1\n"); 422 next; 423 } 424 if (/^(\d+[kK]) bytes of physical memory/i) { 425 ProcessHistory("COMMENTS","keysort","B1", "!Memory: physical $1\n"); 426 next; 427 } 428 if (/^WARNING/) { 429 if (!$I0) { 430 $I0 = 1; 431 ProcessHistory("COMMENTS","keysort","I0","!\n"); 432 } 433 ProcessHistory("COMMENTS","keysort","I1","! $_"); 434 } 435 if (/^Configuration register is (.*)$/) { 436 $config_register = $1; 437 next; 438 } 439 if (/^Configuration register on node \S+ is (.*)$/) { 440 $config_register = $1 if (length($config_register) < 1); 441 next; 442 } 443 } 444 return(0); 445} 446 447# This routine parses "show activation-key" on ASA 448sub ShowActivationKey { 449 my($INPUT, $OUTPUT, $cmd) = @_; 450 print STDERR " In ShowMTU: $_" if ($debug); 451 452 while (<$INPUT>) { 453 tr/\015//d; 454 last if (/^$prompt/); 455 next if (/^(\s*|\s*$cmd\s*)$/); 456 next if (/^\s+\^$/); 457 next if (/^Load for five/); 458 next if (/^Time source is/); 459 return(1) if (/Line has invalid autocommand /); 460 return(1) if (/(invalid (input|command) detected|type help or )/i); 461 # the pager can not be disabled per-session on the PIX 462 if (/^(<-+ More -+>)/) { 463 my($len) = length($1); 464 s/^$1\s{$len}//; 465 } 466 467 if (/^(failover|licensed) .* for this platform:/i || 468 /^active .* activation key/i) { 469 ProcessHistory("COMMENTS","keysort","LICENSE","! $_"); 470 # parse license features/permanents/etc until an empty line 471 while (<$INPUT>) { 472 tr/\015//d; 473 goto OUT if (/^$prompt/); # should not occur 474 s/\s*$//; # trim trailing WS 475 # the pager can not be disabled per-session on the PIX 476 if (/^(<-+ More -+>)/) { 477 my($len) = length($1); 478 s/^$1\s{$len}//; 479 } 480 if (/^\s*$/) { 481 ProcessHistory("COMMENTS","keysort","LICENSE","!\n"); 482 last; 483 } 484 if (/^([^:]+: \S+\s+)(.*)/) { 485 my($L) = $1; 486 my($T) = $2; 487 if ($T !~ /perpetual/i) { 488 $T = "<limited>"; 489 } 490 ProcessHistory("COMMENTS","keysort","LICENSE","! $L $T\n"); 491 } else { 492 ProcessHistory("COMMENTS","keysort","LICENSE","! $_\n"); 493 } 494 } 495 next; 496 } 497 ProcessHistory("COMMENTS","keysort","LICENSE","! $_"); 498 } 499OUT:ProcessHistory("COMMENTS","keysort","LICENSE","!\n"); 500 return(0); 501} 502 503# This routine parses "show cellular 0 profile" 504sub ShowCellular { 505 my($INPUT, $OUTPUT, $cmd) = @_; 506 print STDERR " In ShowCellular: $_" if ($debug); 507 508 while (<$INPUT>) { 509 tr/\015//d; 510 last if (/^$prompt/); 511 next if (/^(\s*|\s*$cmd\s*)$/); 512 next if (/^\s+\^$/); 513 return(1) if (/Line has invalid autocommand /); 514 return(1) if (/(invalid (input|command) detected|type help or )/i); 515 516 # Ignore the PDP address and assigned DNS servers 517 next if (/^pdp (ipv6 )?address/i); 518 next if (/^\s*(primary|secondary) DNS (ipv6 )?address/i); 519 520 ProcessHistory("COMMENTS","keysort","CELL","!CELL: $_"); 521 } 522 ProcessHistory("COMMENTS","keysort","CELL","!\n"); 523 return(0); 524} 525 526# This routine parses "show switch detail" 527sub ShowDetail { 528 my($INPUT, $OUTPUT, $cmd) = @_; 529 print STDERR " In ShowDetail: $_" if ($debug); 530 531 while (<$INPUT>) { 532 tr/\015//d; 533 last if (/^$prompt/); 534 next if (/^(\s*|\s*$cmd\s*)$/); 535 next if (/^\s+\^$/); 536 next if (/^Load for five/); 537 next if (/^Time source is/); 538 539 next if (/^Load for five/); 540 next if (/^Time source is/); 541 return(1) if (/Line has invalid autocommand /); 542 return(1) if (/(invalid (input|command) detected|type help or )/i); 543 544 ProcessHistory("COMMENTS","keysort","IO","!STACK: $_"); 545 } 546 ProcessHistory("COMMENTS","keysort","IO","!\n"); 547 return(0); 548} 549 550# This routine parses "show license" & "show license udi" 551sub ShowLicense { 552 my($INPUT, $OUTPUT, $cmd) = @_; 553 print STDERR " In ShowLicense: $_" if ($debug); 554 555 while (<$INPUT>) { 556 tr/\015//d; 557 last if (/^$prompt/); 558 next if (/^(\s*|\s*$cmd\s*)$/); 559 next if (/^\s+\^$/); 560 next if (/^Load for five/); 561 next if (/^Time source is/); 562 return(0) if (/% no licensable udi in the system/i); # show udi on old box 563 return(0) if (/% license not supported on this device/i);# show lic on old box 564 return(0) if (/% incomplete command/i); # show lic on old XE box 565 return(1) if (/Line has invalid autocommand /); 566 return(1) if (/(invalid (input|command) detected|type help or )/i); 567 return(-1) if (/(?:%|command)? authorization failed/i); 568 return(-1) if (/unable to retrieve license info/i); 569 570 # filter the BS from license broker 571 next if (/(renewal attempt|communication attempt):/i); 572 next if (/next registration attempt:/i); # timestamp 573 next if (/(period used:|requested time:)/i); # show lic feature 574 if (/(^\s*(evaluation )?period (left|remaining):\s*)\d+/i) { 575 ProcessHistory("COMMENTS","keysort","LICENSE","! $1<limited>\n"); 576 next; 577 } 578 579 # drop license counts 580 next if (/license usage:/i); 581 if (/(.*)count status/i) { 582 my($hdr) = $1; 583 my($len) = length($hdr); 584 585 $hdr =~ s/\s*$//; 586 ProcessHistory("COMMENTS", "keysort", "LICENSE", "! $hdr\n"); 587 while (<$INPUT>) { 588 tr/\015//d; 589 return(0) if (/^$prompt/); 590 591 s/^(.{1,$len}).*/$1/; 592 ProcessHistory("COMMENTS", "keysort", "LICENSE", "! $_"); 593 } 594 next; 595 } 596 597 ProcessHistory("COMMENTS","keysort","LICENSE","! $_"); 598 } 599 ProcessHistory("COMMENTS","keysort","LICENSE","!\n"); 600 return(0); 601} 602 603# This routine parses "showMTU" 604sub ShowMTU { 605 my($INPUT, $OUTPUT, $cmd) = @_; 606 print STDERR " In ShowMTU: $_" if ($debug); 607 608 while (<$INPUT>) { 609 tr/\015//d; 610 last if (/^$prompt/); 611 next if (/^(\s*|\s*$cmd\s*)$/); 612 next if (/^\s+\^$/); 613 return(1) if (/Line has invalid autocommand /); 614 return(1) if (/(invalid (input|command) detected|type help or )/i); 615 616 if (/System MTU size is (\d+) bytes/) { 617 ProcessHistory("COMMENTS","keysort","IO","!MTU: $1\n"); 618 next; 619 } 620 if (/System Jumbo MTU size is (\d+) bytes/) { 621 ProcessHistory("COMMENTS","keysort","IO","!MTU-Jumbo: $1\n"); 622 next; 623 } 624 if (/Routing MTU size is (\d+) bytes/) { 625 ProcessHistory("COMMENTS","keysort","IO","!MTU-Routing: $1\n"); 626 next; 627 } 628 # XE version 629 if (/Global Ethernet MTU is (\d+) bytes./) { 630 ProcessHistory("COMMENTS","keysort","IO","!MTU-Global: $1\n"); 631 next; 632 } 633 if (/On next reload, (.*)/) { 634 ProcessHistory("COMMENTS","keysort","IO","!MTU-Reload: $1\n"); 635 next; 636 } 637 } 638 ProcessHistory("COMMENTS","keysort","IO","!\n"); 639 return(0); 640} 641 642# This routine parses "show sdm prefer" 643sub ShowSDM { 644 my($INPUT, $OUTPUT, $cmd) = @_; 645 print STDERR " In ShowSDM: $_" if ($debug); 646 647 while (<$INPUT>) { 648 tr/\015//d; 649 last if (/^$prompt/); 650 next if (/^(\s*|\s*$cmd\s*)$/); 651 next if (/^\s+\^$/); 652 next if (/^Load for five/); 653 next if (/^Time source is/); 654 next if (/^Load for five/); 655 next if (/^Time source is/); 656 return(1) if (/Line has invalid autocommand /); 657 return(1) if (/(invalid (input|command) detected|type help or )/i); 658 659 if (/current template is "(.+)" template/) { 660 ProcessHistory("COMMENTS","keysort","IO","!SDM Template: $1\n"); 661 next; 662 } 663 if (/current template is the (\S+) template/) { 664 ProcessHistory("COMMENTS","keysort","IO","!SDM Template: $1\n"); 665 next; 666 } 667 # XE version 668 if (/This is the (\S+.*) template/) { 669 ProcessHistory("COMMENTS","keysort","IO","!SDM Template: $1\n"); 670 next; 671 } 672 if (/On next reload, template will be "(.+)" template/) { 673 ProcessHistory("COMMENTS","keysort","IO","!SDM Template-Reload: $1\n"); 674 next; 675 } 676 if (/(current template is|next reload)/) { 677 ProcessHistory("COMMENTS","keysort","IO","!SDM: $_"); 678 } 679 } 680 ProcessHistory("COMMENTS","keysort","IO","!\n"); 681 return(0); 682} 683 684# This routine parses "show redundancy" 685sub ShowRedundancy { 686 my($INPUT, $OUTPUT, $cmd) = @_; 687 my($slave, $slaveslot); 688 print STDERR " In ShowRedundancy: $_" if ($debug); 689 690 while (<$INPUT>) { 691 tr/\015//d; 692 last if (/^$prompt/); 693 next if (/^(\s*|\s*$cmd\s*)$/); 694 next if (/^\s+\^$/); 695 next if (/^Load for five/); 696 next if (/^Time source is/); 697 return(1) if (/Line has invalid autocommand /); 698 return(1) if (/(invalid (input|command) detected|type help or )/i); 699 # the pager can not be disabled per-session on the PIX 700 if (/^(<-+ More -+>)/) { 701 my($len) = length($1); 702 s/^$1\s{$len}//; 703 } 704 705 if (/^Version information for secondary in slot (\d+):/) { 706 $slave = " Slave:"; 707 $slaveslot = ", slot $1"; 708 next; 709 } 710 711 /^IOS .* Software \(([A-Za-z0-9_-]*)\), .*Version\s+(.*)$/ && 712 ProcessHistory("COMMENTS","keysort","F1", 713 "!Image:$slave Software: $1, $2\n") && next; 714 /^Compiled (.*)$/ && 715 ProcessHistory("COMMENTS","keysort","F3", 716 "!Image:$slave Compiled: $1\n") && next; 717 } 718 return(0); 719} 720 721# This routine parses "show IDprom" 722sub ShowIDprom { 723 my($INPUT, $OUTPUT, $cmd) = @_; 724 my($tmp); 725 726 print STDERR " In ShowIDprom: $_" if ($debug); 727 728 while (<$INPUT>) { 729 tr/\015//d; 730 last if (/^$prompt/); 731 next if (/^(\s*|\s*$cmd\s*)$/); 732 next if (/^\s+\^$/); 733 next if (/^Load for five/); 734 next if (/^Time source is/); 735 return(1) if (/Line has invalid autocommand /); 736 return(1) if (/(invalid (input|command) detected|type help or )/i); 737 # the pager can not be disabled per-session on the PIX 738 if (/^(<-+ More -+>)/) { 739 my($len) = length($1); 740 s/^$1\s{$len}//; 741 } 742 743 /FRU is .(.*)\'/ && ($tmp = $1); 744 /Product Number = .(.*)\'/ && 745 ProcessHistory("COMMENTS","keysort","D0", 746 "!Catalyst Chassis type: $1, $tmp\n"); 747 /Serial Number = .([0-9A-Za-z]+)/ && 748 ProcessHistory("COMMENTS","keysort","D1", 749 "!Catalyst Chassis S/N: $1\n"); 750 /Manufacturing Assembly Number = .([-0-9]+)/ && ($tmp = $1); 751 /Manufacturing Assembly Revision = .(.*)\'/ && ($tmp .= ", rev " . $1); 752 /Hardware Revision = ([0-9.]+)/ && 753 ProcessHistory("COMMENTS","keysort","D2", 754 "!Catalyst Chassis assembly: $tmp, ver $1\n"); 755 } 756 return(0); 757} 758 759# This routine parses "show install active" 760sub ShowInstallActive { 761 my($INPUT, $OUTPUT, $cmd) = @_; 762 print STDERR " In ShowInstallActive: $_" if ($debug); 763 764 while (<$INPUT>) { 765 tr/\015//d; 766 last if (/^$prompt/); 767 next if (/^(\s*|\s*$cmd\s*)$/); 768 next if (/^\s+\^$/); 769 next if (/^Load for five/); 770 next if (/^Time source is/); 771 return(1) if (/Line has invalid autocommand /); 772 return(1) if (/(invalid (input|command) detected|type help or )/i); 773 return(-1) if (/(?:%|command)? authorization failed/i); 774 # the pager can not be disabled per-session on the PIX 775 if (/^(<-+ More -+>)/) { 776 my($len) = length($1); 777 s/^$1\s{$len}//; 778 } 779 780 ProcessHistory("COMMENTS","keysort","F5","!Image: $_") && next; 781 } 782 return(0); 783} 784 785# This routine parses "show env all" 786sub ShowEnv { 787 my($INPUT, $OUTPUT, $cmd) = @_; 788 print STDERR " In ShowEnv: $_" if ($debug); 789 790 while (<$INPUT>) { 791 tr/\015//d; 792 if (/^$prompt/) { $found_env = 1; last}; 793 next if (/^(\s*|\s*$cmd\s*)$/); 794 next if (/^\s+\^$/); 795 next if (/^Load for five/); 796 next if (/^Time source is/); 797 return(1) if (/Line has invalid autocommand /); 798 return(1) if (/(invalid (input|command) detected|type help or )/i); 799 return(0) if ($found_env); # Only do this routine once 800 return(-1) if (/(?:%|command)? authorization failed/i); 801 # the pager can not be disabled per-session on the PIX 802 if (/^(<-+ More -+>)/) { 803 my($len) = length($1); 804 s/^$1\s{$len}//; 805 } 806 807 # remove "Fan n RPM is #" on 7201, 7301 808 next if (/ RPM is /); 809 810 if (!$E0) { 811 $E0 = 1; 812 ProcessHistory("COMMENTS","keysort","E0","!\n"); 813 } 814 if (/^Arbiter type (\d), backplane type (\S+)/) { 815 if (!$C0) { 816 $C0 = 1; ProcessHistory("COMMENTS","keysort","C0","!\n"); 817 } 818 ProcessHistory("COMMENTS","keysort","C1", 819 "!Enviromental Arbiter Type: $1\n"); 820 ProcessHistory("COMMENTS","keysort","A2", 821 "!Chassis type: $2 backplane\n"); 822 next; 823 } 824 # AC revision from UBRs and some others fluctuates 825 s/is AC Revision [A-F]0\./is AC./; 826 /^Power Supply Information$/ && next; 827 /^\s*Power Module\s+Voltage\s+Current$/ && next; 828 /^\s*(Power [^:\n]+)$/ && 829 ProcessHistory("COMMENTS","keysort","E1","!Power: $1\n") && next; 830 /^\s*(Lower Power .*)/i && 831 ProcessHistory("COMMENTS","keysort","E2","!Power: $1\n") && next; 832 /^\s*(redundant .*)/i && 833 ProcessHistory("COMMENTS","keysort","E2","!Power: $1\n") && next; 834 /^\s*((RPS|power-supply) (\d|is) .*)/i && 835 ProcessHistory("COMMENTS","keysort","E2","!Power: $1\n") && next; 836 /^\s*FAN \d RPM is \d+$/ && next; 837 # Fan speed on ASR901 838 # Fan 1 Operation: Normal, is running at 40 percent speed 839 /^(\s*Fan \d Operation: \S+), .*$/ && 840 ProcessHistory("COMMENTS","keysort","E3","!FAN: $1\n") && next; 841 842 if (/^\s*((FAN|fan-tray) (\d|is) .*)/i) { 843 my($tmp) = ($1); 844 $tmp =~ s/, \S+ speed setting//; 845 $tmp =~ s/, is running at \d{1,3}\s* percent speed//; 846 ProcessHistory("COMMENTS","keysort","E3","!FAN: $tmp\n"); 847 next; 848 } 849 } 850 ProcessHistory("COMMENTS","","","!\n"); 851 return(0); 852} 853 854# This routine parses "show hw-programmable all" 855sub ShowHWProgrammable { 856 my($INPUT, $OUTPUT, $cmd) = @_; 857 print STDERR " In ShowPlatform: $_" if ($debug); 858 859 while (<$INPUT>) { 860 tr/\015//d; 861 last if (/^$prompt/); 862 next if (/^(\s*|\s*$cmd\s*)$/); 863 next if (/^\s+\^$/); 864 next if (/^Load for five/); 865 next if (/^Time source is/); 866 return(0) if (/% incomplete command/i); # every platform is different 867 return(1) if (/(invalid (input|command) detected|type help or )/i); 868 return(-1) if (/(?:%|command)? authorization failed/i); 869 # return(1) if ($type !~ /^12[40]/); 870 # the pager can not be disabled per-session on the PIX 871 if (/^(<-+ More -+>)/) { 872 my($len) = length($1); 873 s/^$1\s{$len}//; 874 } 875 /^$/ && next; 876 877 # XXX parsing for show platform, which has CPLD info on some platforms 878 # but is inconsistent across platforms. 879 #if (/^(.*) insert time.*$/i) { 880 # my($len) = length($1); 881 # ProcessHistory("PLATFORM","","", "! $1\n"); 882 # 883 # while (<$INPUT>) { 884 # tr/\015//d; 885 # return(0) if (/^$prompt/); 886 # 887 # s/^(.{1,$len}).*/$1/; 888 # ProcessHistory("PLATFORM","","", "! $_"); 889 # last if (/^$/); 890 # } 891 # next; 892 #} 893 894 ProcessHistory("HWP","","", "! $_"); 895 } 896 ProcessHistory("HWP","","", "!\n"); 897 898 return(0); 899} 900 901# This routine parses "show rsp chassis-info" for the rsp 902# This will create arrays for hw info. 903sub ShowRSP { 904 my($INPUT, $OUTPUT, $cmd) = @_; 905 print STDERR " In ShowRSP: $_" if ($debug); 906 907 while (<$INPUT>) { 908 tr/\015//d; 909 last if (/^$prompt/); 910 next if (/^(\s*|\s*$cmd\s*)$/); 911 next if (/^\s+\^$/); 912 return(1) if (/(invalid (input|command) detected|type help or )/i); 913 return(-1) if (/(?:%|command)? authorization failed/i); 914 # return(1) if ($type !~ /^12[40]/); 915 # the pager can not be disabled per-session on the PIX 916 if (/^(<-+ More -+>)/) { 917 my($len) = length($1); 918 s/^$1\s{$len}//; 919 } 920 /^$/ && next; 921 922 /^\s+Chassis model: (\S+)/ && 923 ProcessHistory("COMMENTS","keysort","D1", 924 "!RSP Chassis model: $1\n") && 925 next; 926 /^\s+Chassis S\/N: (.*)$/ && 927 ProcessHistory("COMMENTS","keysort","D2", 928 "!RSP Chassis S/N: $1\n") && 929 next; 930 } 931 932 return(0); 933} 934 935# This routine parses "show gsr chassis-info" for the gsr 936# This will create arrays for hw info. 937sub ShowGSR { 938 my($INPUT, $OUTPUT, $cmd) = @_; 939 # Skip if this is not a 1200n. 940 print STDERR " In ShowGSR: $_" if ($debug); 941 942 while (<$INPUT>) { 943 tr/\015//d; 944 last if (/^$prompt/); 945 next if (/^(\s*|\s*$cmd\s*)$/); 946 next if (/^\s+\^$/); 947 next if (/^Load for five/); 948 next if (/^Time source is/); 949 next if (/^Load for five/); 950 next if (/^Time source is/); 951 return(1) if (/(invalid (input|command) detected|type help or )/i); 952 return(-1) if (/(?:%|command)? authorization failed/i); 953 # return(1) if ($type !~ /^12[40]/); 954 # the pager can not be disabled per-session on the PIX 955 if (/^(<-+ More -+>)/) { 956 my($len) = length($1); 957 s/^$1\s{$len}//; 958 } 959 /^$/ && next; 960 961 /^\s+Chassis: type (\S+) Fab Ver: (\S+)/ && 962 ProcessHistory("COMMENTS","keysort","D1", 963 "!GSR Chassis type: $1 Fab Ver: $2\n") && 964 next; 965 /^\s+Chassis S\/N: (.*)$/ && 966 ProcessHistory("COMMENTS","keysort","D2", 967 "!GSR Chassis S/N: $1\n") && 968 next; 969 /^\s+PCA: (\S+)\s*rev: (\S+)\s*dev: \S+\s*HW ver: (\S+)$/ && 970 ProcessHistory("COMMENTS","keysort","D3", 971 "!GSR Backplane PCA: $1, rev $2, ver $3\n") && 972 next; 973 /^\s+Backplane S\/N: (\S+)$/ && 974 ProcessHistory("COMMENTS","keysort","D4", 975 "!GSR Backplane S/N: $1\n") && 976 next; 977 } 978 ProcessHistory("COMMENTS","","","!\n"); 979 return(0); 980} 981 982# This routine parses "show boot" 983sub ShowBoot { 984 my($INPUT, $OUTPUT, $cmd) = @_; 985 # Pick up boot variables if 7000/7200/7500/12000/2900/3500; 986 # otherwise pick up bootflash. 987 print STDERR " In ShowBoot: $_" if ($debug); 988 989 while (<$INPUT>) { 990 tr/\015//d; 991 last if (/^$prompt/); 992 next if (/^(\s*|\s*$cmd\s*)$/); 993 next if (/^\s+\^$/); 994 next if (/^Load for five/); 995 next if (/^Time source is/); 996 return(1) if (/Line has invalid autocommand /); 997 return(1) if (/(invalid (input|command) detected|type help or )/i); 998 return(1) if (/Ambiguous command/i); 999 return(1) if (/(Open device \S+ failed|Error opening \S+:)/); 1000 return(-1) if (/(?:%|command)? authorization failed/i); 1001 # the pager can not be disabled per-session on the PIX 1002 if (/^(<-+ More -+>)/) { 1003 my($len) = length($1); 1004 s/^$1\s{$len}//; 1005 } 1006 1007 next if /CONFGEN variable/; 1008 if (!$H0) { 1009 $H0 = 1; ProcessHistory("COMMENTS","keysort","H0","!\n"); 1010 } 1011 if ($type !~ /^(12[04]|7)/) { 1012 if ($type !~ /^(29|35)00/) { 1013 ProcessHistory("COMMENTS","keysort","H2","!BootFlash: $_"); 1014 } else { 1015 ProcessHistory("COMMENTS","keysort","H1","!Variable: $_"); 1016 } 1017 } elsif (/(variable|register)/) { 1018 ProcessHistory("COMMENTS","keysort","H1","!Variable: $_"); 1019 } 1020 } 1021 ProcessHistory("COMMENTS","","","!\n"); 1022 return(0); 1023} 1024 1025# This routine parses "show flash" 1026sub ShowFlash { 1027 my($INPUT, $OUTPUT, $cmd) = @_; 1028 print STDERR " In ShowFlash: $_" if ($debug); 1029 1030 while (<$INPUT>) { 1031 tr/\015//d; 1032 last if (/^$prompt/); 1033 next if (/^(\s*|\s*$cmd\s*)$/); 1034 # skip if this is 7000, 7200, 7500, 12000, or IOS-XE; else we have 1035 # redundant data from dir /all slot0: 1036 return(1) if ($type =~ /^(12[40]|7)/); 1037 return(1) if ($ios eq "XE"); 1038 next if (/^\s+\^$/); 1039 1040 next if (/^Load for five/); 1041 next if (/^Time source is/); 1042 return(1) if (/Line has invalid autocommand /); 1043 return(1) if (/(invalid (input|command) detected|type help or )/i); 1044 return(-1) if (/(?:%|command)? authorization failed/i); 1045 # the pager can not be disabled per-session on the PIX 1046 if (/^(<-+ More -+>)/) { 1047 my($len) = length($1); 1048 s/^$1\s{$len}//; 1049 } 1050 1051 # Drop these files entirely. 1052 /\s+(private-multiple-fs|multiple-fs|LISP-MapCache-IPv\S+|nv_hdr)$/ && 1053 next; 1054 1055 if (/(dhcp_[^. ]*\.txt|license_evlog|vlan\.dat|sflog|snooping)/ || 1056 /(LOCAL-CA-SERVER(?:[^\s]*))\s*$/ || 1057 /(smart-log\/agentlog|syslog)\s*$/ || 1058 /(log\/(?:ssp_tz\/)?[^. ]+\.log(?:\.[0-9]+\.gz)?)\s*$/) { 1059 # filter frequently changing files (dhcp & vlan database, logs) from flash 1060 # change from: 1061 # 537549598 38354 Feb 19 2019 20:59:32 log/ssp_tz/ssp_tz.log.1.gz 1062 # 9 660 Jan 15 2011 20:43:54 vlan.dat 1063 # 9 660 Jan 15 2011 20:43:54 +00:00 vlan.dat 1064 # to: 1065 # log/ssp_tz/ssp_tz.log.1.gz 1066 # vlan.dat 1067 # vlan.dat 1068 if (/(\s*\d+)(\s+[-drwx]+\s+)(\d+)(\s+)(\w+ \d+\s+\d+ \d+:\d+:\d+ .\d+:\d+)/) { 1069 my($fn, $a, $sz, $c, $dt, $rem) = ($1, $2, $3, $4, $5, $'); 1070 my($fnl, $szl, $dtl) = (length($fn), length($sz), length($dt)); 1071 my($fmt) = "%-". $fnl ."s%s%-". $szl ."s%s%-". $dtl ."s%s"; 1072 $_ = sprintf($fmt, "", $a, "", $c, "", $rem); 1073 } elsif (/(\s*\d+)(\s+[-drwx]+\s+)(\d+)(\s+)(\w+ \d+\s+\d+ \d+:\d+:\d+)/) { 1074 my($fn, $a, $sz, $c, $dt, $rem) = ($1, $2, $3, $4, $5, $'); 1075 my($fnl, $szl, $dtl) = (length($fn), length($sz), length($dt)); 1076 my($fmt) = "%-". $fnl ."s%s%-". $szl ."s%s%-". $dtl ."s%s"; 1077 $_ = sprintf($fmt, "", $a, "", $c, "", $rem); 1078 } elsif (/(\s*\d+)(\s+)(\d+)(\s+)(\w+ \d+\s+\d+ \d+:\d+:\d+ .\d+:\d+)/) { 1079 # System flash directory: 1080 # File Length Name/status 1081 # 1 12138448 c3640-ik9s-mz.122-40.bin 1082 my($fn, $a, $sz, $c, $dt, $rem) = ($1, $2, $3, $4, $5, $'); 1083 my($fnl, $szl, $dtl) = (length($fn), length($sz), length($dt)); 1084 my($fmt) = "%-". $fnl ."s%s%-". $szl ."s%s%-". $dtl ."s%s"; 1085 $_ = sprintf($fmt, "", $a, "", $c, "", $rem); 1086 } elsif (/(\s*\d+)(\s+)(\d+)(\s+)(\w+ \d+\s+\d+ \d+:\d+:\d+)/) { 1087 my($fn, $a, $sz, $c, $dt, $rem) = ($1, $2, $3, $4, $5, $'); 1088 my($fnl, $szl, $dtl) = (length($fn), length($sz), length($dt)); 1089 my($fmt) = "%-". $fnl ."s%s%-". $szl ."s%s%-". $dtl ."s%s"; 1090 $_ = sprintf($fmt, "", $a, "", $c, "", $rem); 1091 } 1092 /\s+(\S+)\s*$/ && 1093 ProcessHistory("FLASH","keysort","$1","!Flash: $_") && next; 1094 } elsif (/(running-config-archive-)\S+\s*$/) { 1095 # filter config archives from flash 1096 # change from: 1097 # 9 660 Jan 15 2011 20:43:54 running-config-archive-Jul--1-16-50-27.123-113 1098 # 9 660 Jan 15 2011 20:43:54 +00:00 running-config-archive-Jul--1-16-50-27.123-113 1099 # to: 1100 # running-config-archive-<removed> 1101 # running-config-archive-<removed> 1102 my($arc) = $1; 1103 if (/(\s*\d+)(\s+[-drwx]+\s+)(\d+)(\s+)(\w+ \d+\s+\d+ \d+:\d+:\d+ .\d+:\d+)/) { 1104 my($fn, $a, $sz, $c, $dt, $rem) = ($1, $2, $3, $4, $5, $'); 1105 my($fnl, $szl, $dtl) = (length($fn), length($sz), length($dt)); 1106 my($fmt) = "%-". $fnl ."s%s%-". $szl ."s%s%-". $dtl ."s%s%s\n"; 1107 $_ = sprintf($fmt, "", $a, "", $c, "", $arc , "<removed>"); 1108 } elsif (/(\s*\d+)(\s+[-drwx]+\s+)(\d+)(\s+)(\w+ \d+\s+\d+ \d+:\d+:\d+)/) { 1109 my($fn, $a, $sz, $c, $dt, $rem) = ($1, $2, $3, $4, $5, $'); 1110 my($fnl, $szl, $dtl) = (length($fn), length($sz), length($dt)); 1111 my($fmt) = "%-". $fnl ."s%s%-". $szl ."s%s%-". $dtl ."s%s%s\n"; 1112 $_ = sprintf($fmt, "", $a, "", $c, "", $arc, "<removed>"); 1113 } elsif (/(\s*\d+)(\s+)(\d+)(\s+)(\w+ \d+\s+\d+ \d+:\d+:\d+ .\d+:\d+)/) { 1114 my($fn, $a, $sz, $c, $dt, $rem) = ($1, $2, $3, $4, $5, $'); 1115 my($fnl, $szl, $dtl) = (length($fn), length($sz), length($dt)); 1116 my($fmt) = "%-". $fnl ."s%s%-". $szl ."s%s%-". $dtl ."s%s%s\n"; 1117 $_ = sprintf($fmt, "", $a, "", $c, "", $arc, "<removed>"); 1118 } elsif (/(\s*\d+)(\s+)(\d+)(\s+)(\w+ \d+\s+\d+ \d+:\d+:\d+)/) { 1119 my($fn, $a, $sz, $c, $dt, $rem) = ($1, $2, $3, $4, $5, $'); 1120 my($fnl, $szl, $dtl) = (length($fn), length($sz), length($dt)); 1121 my($fmt) = "%-". $fnl ."s%s%-". $szl ."s%s%-". $dtl ."s%s%s\n"; 1122 $_ = sprintf($fmt, "", $a, "", $c, "", $arc, "<removed>"); 1123 } 1124 /\s+(\S+)\s*$/ && 1125 ProcessHistory("FLASH","keysort","$1","!Flash: $_") && next; 1126 } elsif (/^(\s*\d+)(\s+[-drwx]+\s+\d+\s+\w+ \d+\s+\d+ \d+:\d+:\d+ .\d+:\d+\s+)(\S+)/ || 1127 /^(\s*\d+)(\s+[-drwx]+\s+\d+\s+\w+ \d+\s+\d+ \d+:\d+:\d+\s+)(\S+)/ || 1128 /^(\s*\d+)(\s+\d+\s+\w+ \d+\s+\d+ \d+:\d+:\d+ .\d+:\d+\s+)(\S+)/ || 1129 /^(\s*\d+)(\s+\d+\s+\w+ \d+\s+\d+ \d+:\d+:\d+\s+)(\S+)/) { 1130 my($fmt) = "%-". length($1) ."s%s%s\n"; 1131 $_ = sprintf($fmt, "", $2, $3); 1132 ProcessHistory("FLASH","keysort","$3","!Flash: $_") && next; 1133 } 1134 1135 if (/(\d+) bytes (available|total) \((\d+) bytes (free|used)(\/\s+% free)?\)/) { 1136 my($avail); 1137 my($preamble) = ""; 1138 if ($2 eq "available") { 1139 $avail = $1; 1140 } else { 1141 $preamble = "$1 bytes total"; 1142 if ($4 eq "free") { 1143 $avail = $3; 1144 } else { 1145 $avail = $1 - $3; 1146 } 1147 } 1148 if ($avail >= (1024 * 1024 * 1024)) { 1149 $avail = int($avail / (1024 * 1024 * 1024)); 1150 $_ = "$avail GB free\n"; 1151 } elsif ($avail >= (1024 * 1024)) { 1152 $avail = int($avail / (1024 * 1024)); 1153 $_ = "$avail MB free\n"; 1154 } elsif ($avail >= (1024)) { 1155 $avail = int($avail / 1024); 1156 $_ = "$avail KB free\n"; 1157 } elsif ($avail > 0) { 1158 $_ = "< 1KB free\n"; 1159 } else { 1160 $_ = "0 bytes free\n"; 1161 } 1162 if (length($preamble)) { 1163 chomp($_); 1164 $_ = "$preamble ($_)\n"; 1165 } 1166 } 1167 ProcessHistory("FLASH","","","!Flash: $_"); 1168 } 1169 ProcessHistory("","","","!\n"); 1170 return; 1171} 1172 1173# This routine parses "dir /all ((disk|slot)N|bootflash|nvram):" 1174sub DirSlotN { 1175 my($INPUT, $OUTPUT, $cmd) = @_; 1176 print STDERR " In DirSlotN: $_" if ($debug); 1177 1178 my($dev) = (/\s([^\s]+):/); 1179 1180 while (<$INPUT>) { 1181 tr/\015//d; 1182 last if (/^$prompt/); 1183 next if (/^(\s*|\s*$cmd\s*)$/); 1184 next if (/^\s+\^$/); 1185 next if (/^Load for five/); 1186 next if (/^Time source is/); 1187 return(1) if (/Line has invalid autocommand /); 1188 return(1) if (/(invalid (input|command) detected|type help or )/i); 1189 return(1) if (/(No such device|Error Sending Request)/i); 1190 return(1) if (/\%Error: No such file or directory/); 1191 return(1) if (/No space information available/); 1192 # Corrupt flash 1193 /\%Error calling getdents / && 1194 ProcessHistory("FLASH","","","!Flash: $dev: $_") && next; 1195 return(-1) if (/\%Error calling/); 1196 return(-1) if (/(: device being squeezed|ATA_Status time out)/i); # busy 1197 return(-1) if (/\%Error opening \S+:\S+ \(Device or resource busy\)/i); 1198 return(-1) if (/(?:%|command)? authorization failed/i); 1199 return(1) if (/(Open device \S+ failed|Error opening \S+:)/); 1200 # the pager can not be disabled per-session on the PIX 1201 if (/^(<-+ More -+>)/) { 1202 my($len) = length($1); 1203 s/^$1\s{$len}//; 1204 } 1205 1206 # skip dir sup-bootflash if dir sup-bootdisk was successful, duplicates 1207 if ($cmd =~ / sup-bootdisk/) { 1208 $supbootdisk++; 1209 } elsif ($supbootdisk && $cmd =~ / sup-bootflash/) { 1210 return(0); 1211 } 1212 1213 # Drop LISP cache. 1214 /\s+LISP-MapCache-IPv\S+$/ && next; 1215 1216 # Filter internal file used by ISSU (In-Service Software Upgrade) 1217 # on dual RP ASR systems 1218 next if (/\.issu_loc_lock\s*$/); 1219 1220 # vASA nonsense 1221 # 9 file(s) total size: 252854822 bytes 1222 next if (/\d+ file\S+ total size: \d+ bytes/i); 1223 1224 # filter frequently changing files (dhcp & vlan database) 1225 # change from: 1226 # 9 -rw- 660 Jan 15 2011 20:43:54 vlan.dat 1227 # 9 -rw- 660 Jan 15 2011 20:43:54 +00:00 vlan.dat 1228 # to: 1229 # -rw- vlan.dat 1230 # -rw- vlan.dat 1231 if (/(dhcp_[^. ]*\.txt|vlan\.dat|sflog|snooping|syslog)\s*$/ || 1232 /(tracelogs|throughput_monitor_params|underlying-config)\s*$/) { 1233 if (/(\s*\d+\s+)(\S+\s+)(\d+)(\s+)(\w+ \d+\s+\d+ \d+:\d+:\d+ .\d+:\d+)/) { 1234 my($fn, $a, $sz, $c, $dt, $rem) = ($1, $2, $3, $4, $5, $'); 1235 my($fnl, $szl, $dtl) = (length($fn), length($sz), length($dt)); 1236 my($fmt) = "%s%-". $szl ."s%s%-". $dtl ."s%s"; 1237 $_ = sprintf($fmt, $a, "", $c, "", $rem); 1238 } elsif (/(\s*\d+\s+)(\S+\s+)(\d+)(\s+)(\w+ \d+\s+\d+ \d+:\d+:\d+)/) { 1239 my($fn, $a, $sz, $c, $dt, $rem) = ($1, $2, $3, $4, $5, $'); 1240 my($fnl, $szl, $dtl) = (length($fn), length($sz), length($dt)); 1241 my($fmt) = "%s%-". $szl ."s%s%-". $dtl ."s%s"; 1242 $_ = sprintf($fmt, $a, "", $c, "", $rem); 1243 } elsif (/(\s*\d+\s+)(\S+\s+)(\d+)(\s+<no date>)/i) { 1244 # 32771 -rw- 24520 <no date> underlying-config 1245 my($fn, $a, $sz, $dt, $rem) = ($1, $2, $3, $4, $'); 1246 my($fnl, $szl) = (length($fn), length($sz)); 1247 my($fmt) = "%s%-". $szl ."s%s%s"; 1248 $_ = sprintf($fmt, $a, "", $dt, $rem); 1249 } 1250 /\s+(\S+)\s*$/ && 1251 ProcessHistory("FLASH","keysort","$1","!Flash: $dev: $_") && 1252 next; 1253 } elsif (/(running-config-archive-)\S+\s*$/) { 1254 my($arc) = $1; 1255 1256 # filter frequently changing files of the config archive feature 1257 # change from: 1258 # 9 -rw- 660 Jan 15 2011 20:43:54 running-config-archive-Jul--1-16-50-27.123-113 1259 # 9 -rw- 660 Jan 15 2011 20:43:54 +00:00 running-config-archive-Jul--1-16-50-27.123-113 1260 # to: 1261 # -rw- running-config-archive-Jul--1-16-50-27.123-113 1262 # -rw- running-config-archive-Jul--1-16-50-27.123-113 1263 if (/(\s*\d+\s+)(\S+\s+)(\d+)(\s+)(\w+ \d+\s+\d+ \d+:\d+:\d+ .\d+:\d+)/) { 1264 my($fn, $a, $sz, $c, $dt, $rem) = ($1, $2, $3, $4, $5, $'); 1265 my($fnl, $szl, $dtl) = (length($fn), length($sz), length($dt)); 1266 my($fmt) = "%s%-". $szl ."s%s%-". $dtl ."s%s%s\n"; 1267 $_ = sprintf($fmt, $a, "", $c, "", $arc, "<removed>"); 1268 } elsif (/(\s*\d+\s+)(\S+\s+)(\d+)(\s+)(\w+ \d+\s+\d+ \d+:\d+:\d+)/) { 1269 my($fn, $a, $sz, $c, $dt, $rem) = ($1, $2, $3, $4, $5, $'); 1270 my($fnl, $szl, $dtl) = (length($fn), length($sz), length($dt)); 1271 my($fmt) = "%s%-". $szl ."s%s%-". $dtl ."s%s%s\n"; 1272 $_ = sprintf($fmt, $a, "", $c, "", $arc, "<removed>"); 1273 } 1274 /\s+(\S+)\s*$/ && 1275 ProcessHistory("FLASH","keysort","$1","!Flash: $dev: $_") && 1276 next; 1277 } else { 1278 # drop file number (from the various formats): 1279 # 3 -rw- 1011 <no date> ifIndex-table 1280 # 9 -rw- 660 Jan 15 2011 20:43:54 vlan.dat 1281 # 16 -rw- 5437 Jan 16 2016 02:22:32 +00:00 licenses 1282 # 114 -rwx 92 13:22:08 Aug 15 2019 .boot_string (ASA) 1283 if (/(\s*\d+\s+)(\S+\s+\d+\s+\w+ \d+\s+\d+ \d+:\d+:\d+ .\d+:\d+)/ || 1284 /(\s*\d+\s+)(\S+\s+\d+\s+\w+ \d+\s+\d+ \d+:\d+:\d+)/ || 1285 /(\s*\d+\s+)(\S+\s+\d+\s+<no date>\s+\S+)/ || 1286 /(\s*\d+\s+)(\S+\s+\d+\s+\d+:\d+:\d+ \w+ \d+\s+\d+\s+\S+)/) { 1287 #my($fn, $a, $rem) = ($1, $2, $'); 1288 #my($fnl) = length($fn); 1289 #my($fmt) = "%-". $fnl ."s%s%s\n"; 1290 #$_ = sprintf($fmt, "", $a, $rem); 1291 $_ = $2 . $'; 1292 /\s+(\S+)\s*$/ && 1293 ProcessHistory("FLASH","keysort","$1","!Flash: $dev: $_") && 1294 next; 1295 } 1296 } 1297 1298 # XE: 822083584 bytes total (821081600 bytes free) 1299 if (/^\s*(\d+) bytes total\s+\((\d+) bytes free\)/i) { 1300 ProcessHistory("FLASH","","","!Flash: $dev: " . 1301 diskszsummary($1, $2) . "\n"); 1302 next; 1303 } 1304 # vASA: 8571076608 bytes total (8306561024 bytes free/96% free) 1305 if (/^\s*(\d+) bytes total \((\d+) bytes free\/\d+% free\)/) { 1306 ProcessHistory("FLASH","","","!Flash: $dev: " . 1307 diskszsummary($1, $2) . "\n"); 1308 next; 1309 } 1310 1311 ProcessHistory("FLASH","","","!Flash: $dev: $_"); 1312 } 1313 ProcessHistory("","","","!\n"); 1314 return(0); 1315} 1316 1317# This routine parses "show controllers" 1318sub ShowContAll { 1319 my($INPUT, $OUTPUT, $cmd) = @_; 1320 my($INT); 1321 # Skip if this is a 70[01]0, 7500, or 12000. 1322 print STDERR " In ShowContAll: $_" if ($debug); 1323 1324 while (<$INPUT>) { 1325 tr/\015//d; 1326 last if (/^$prompt/); 1327 next if (/^(\s*|\s*$cmd\s*)$/); 1328 next if (/^\s+\^$/); 1329 next if (/^Load for five/); 1330 next if (/^Time source is/); 1331 return(1) if (/(invalid (input|command) detected|type help or )/i); 1332 # return(1) if ($type =~ /^(12[40]|7[05])/); 1333 return(-1) if (/(?:%|command)? authorization failed/i); 1334 # the pager can not be disabled per-session on the PIX 1335 if (/^(<-+ More -+>)/) { 1336 my($len) = length($1); 1337 s/^$1\s{$len}//; 1338 } 1339 1340 if (/^Interface ([^ \n(]*)/) { $INT = "$1, "; next; } 1341 /^(BRI unit \d)/ && 1342 ProcessHistory("INT","","","!Interface: $1\n") && next; 1343 /^LANCE unit \d, NIM/ && 1344 ProcessHistory("INT","","","!Interface: $_") && next; 1345 /^(LANCE unit \d)/ && 1346 ProcessHistory("INT","","","!Interface: $1\n") && next; 1347 /(Media Type is \S+),/ && 1348 ProcessHistory("INT","","","!\t$1\n"); 1349 if (/(M\dT[^ :]*:) show controller:$/) { 1350 my($ctlr) = $1; 1351 $_ = <$INPUT>; tr/\015//d; s/ subunit \d,//; 1352 ProcessHistory("INT","","","!Interface: $ctlr $_"); 1353 } 1354 if (/^(\S+) : show controller:$/) { 1355 my($ctlr) = $1; 1356 $_ = <$INPUT>; tr/\015//d; s/ subunit \d,//; 1357 ProcessHistory("INT","","","!Interface: $ctlr: $_"); 1358 } 1359 /^(HD unit \d), idb/ && 1360 ProcessHistory("INT","","","!Interface: $1\n") && next; 1361 /^HD unit \d, NIM/ && 1362 ProcessHistory("INT","","","!Interface: $_") && next; 1363 /^buffer size \d+ HD unit \d, (.*)/ && 1364 ProcessHistory("INT","","","!\t$1\n") && next; 1365 /^AM79970 / && ProcessHistory("INT","","","!Interface: $_") && next; 1366 /^buffer size \d+ (Universal Serial: .*)/ && 1367 ProcessHistory("INT","","","!\t$1\n") && next; 1368 # Remove dynamic addresses like: 1369 # !Interface: FastEthernet0/0, GT96K FE ADDR: 62AFB684, FASTSEND: 6 1579E4C, MCI_INDEX: 0 1370 /^ *Hardware is (.*?)($| ADDR: .*| at 0x.*)/ && 1371 ProcessHistory("INT","","","!Interface: $INT$1\n") && next; 1372 /^Hardware is (.*)/ && 1373 ProcessHistory("INT","","","!Interface: $INT$1\n") && next; 1374 /^(QUICC Serial unit \d),/ && 1375 ProcessHistory("INT","","","!$1\n") && next; 1376 /^QUICC Ethernet .*/ && 1377 ProcessHistory("INT","","","!$_") && next; 1378 /^DTE .*\.$/ && next; 1379 /^(cable type :.*),/ && 1380 ProcessHistory("INT","","","!\t$1\n") && next; 1381 /^(.* cable.*), received clockrate \d+$/ && 1382 ProcessHistory("INT","","","!\t$1\n") && next; 1383 /^.* cable.*$/ && 1384 ProcessHistory("INT","","","!\t$_") && next; 1385 } 1386 return(0); 1387} 1388 1389# This routine parses "show controllers cbus" 1390# Some of this is printed out in ShowDiagbus. 1391sub ShowContCbus { 1392 my($INPUT, $OUTPUT, $cmd) = @_; 1393 my($interface, $slot); 1394 # Skip if this is not a 7000 or 7500. 1395 print STDERR " In ShowContCbus: $_" if ($debug); 1396 1397 while (<$INPUT>) { 1398 my(%board, %hwver); 1399 tr/\015//d; 1400 last if (/^$prompt/); 1401 next if (/^(\s*|\s*$cmd\s*)$/); 1402 next if (/^\s+\^$/); 1403 next if (/^Load for five/); 1404 next if (/^Time source is/); 1405 return(1) if (/(invalid (input|command) detected|type help or )/i); 1406 #return(1) if ($type !~ /^7[05]0/); 1407 return(-1) if (/(?:%|command)? authorization failed/i); 1408 # the pager can not be disabled per-session on the PIX 1409 if (/^(<-+ More -+>)/) { 1410 my($len) = length($1); 1411 s/^$1\s{$len}//; 1412 } 1413 1414 if (/^\s*slot(\d+): ([^,]+), hw (\S+), sw (\S+), ccb/) { 1415 $slot = $1; 1416 $board{$slot} = $2; 1417 $hwver{$slot} = $3; 1418 $hwucode{$slot} = $4; 1419 } elsif (/^\s*(\S+) (\d+), hardware version (\S+), microcode version (\S+)/) { 1420 $slot = $2; 1421 $board{$slot} = $1; 1422 $hwver{$slot} = $3; 1423 $hwucode{$slot} = $4; 1424 } elsif (/(Microcode .*)/) { 1425 $ucode{$slot} = $1; 1426 } elsif (/(software loaded .*)/) { 1427 $ucode{$slot} = $1; 1428 } elsif (/(\d+) Kbytes of main memory, (\d+) Kbytes cache memory/) { 1429 $hwmemd{$slot} = $1; 1430 $hwmemc{$slot} = $2; 1431 } elsif (/byte buffers/) { 1432 chop; 1433 s/^\s*//; 1434 $hwbuf{$slot} = $_; 1435 } elsif (/Interface (\d+) - (\S+ \S+),/) { 1436 $interface = $1; 1437 ProcessHistory("HW","","", 1438 "!\n!Int $interface: in slot $slot, named $2\n"); next; 1439 } elsif (/(\d+) buffer RX queue threshold, (\d+) buffer TX queue limit, buffer size (\d+)/) { 1440 ProcessHistory("HW","","","!Int $interface: rxq $1, txq $2, bufsize $3\n"); 1441 next; 1442 } 1443 } 1444 return(0); 1445} 1446 1447# This routine parses "show debug" 1448sub ShowDebug { 1449 my($INPUT, $OUTPUT, $cmd) = @_; 1450 print STDERR " In ShowDebug: $_" if ($debug); 1451 my($lines) = 0; 1452 1453 while (<$INPUT>) { 1454 tr/\015//d; 1455 last if (/^$prompt/); 1456 next if (/^(\s*|\s*$cmd\s*)$/); 1457 next if (/^\s+\^$/); 1458 next if (/^Load for five/); 1459 next if (/^Time source is/); 1460 return(1) if (/Line has invalid autocommand /); 1461 return(1) if (/(invalid (input|command) detected|type help or )/i); 1462 return(-1) if (/(?:%|command)? authorization failed/i); 1463 # ASAv produce this error occasionally 1464 return(-1) if (/unable to retrieve licensing debug info/i); 1465 # the pager can not be disabled per-session on the PIX 1466 if (/^(<-+ More -+>)/) { 1467 my($len) = length($1); 1468 s/^$1\s{$len}//; 1469 } 1470 1471 /Load for / && next; 1472 /^Time source is / && next; 1473 /^No matching debug flags set$/ && next; 1474 /^No debug flags set$/ && next; 1475 ProcessHistory("COMMENTS","keysort","J1","!DEBUG: $_"); 1476 $lines++; 1477 } 1478 if ($lines) { 1479 ProcessHistory("COMMENTS","keysort","J0","!\n"); 1480 } 1481 return(0); 1482} 1483 1484# This routine parses "show diagbus" 1485# This will create arrays for hw info. 1486sub ShowDiagbus { 1487 my($INPUT, $OUTPUT, $cmd) = @_; 1488 my($board, $slot); 1489 # Skip if this is not a 7000, 70[01]0, or 7500. 1490 print STDERR " In ShowDiagbus: $_" if ($debug); 1491 1492 while (<$INPUT>) { 1493 tr/\015//d; 1494 last if (/^$prompt/); 1495 next if (/^(\s*|\s*$cmd\s*)$/); 1496 #return(1) if ($type !~ /^7[05]/); 1497 next if (/^\s+\^$/); 1498 next if (/^Load for five/); 1499 next if (/^Time source is/); 1500 return(1) if (/Line has invalid autocommand /); 1501 return(1) if (/(invalid (input|command) detected|type help or )/i); 1502 return(-1) if (/(?:%|command)? authorization failed/i); 1503 # the pager can not be disabled per-session on the PIX 1504 if (/^(<-+ More -+>)/) { 1505 my($len) = length($1); 1506 s/^$1\s{$len}//; 1507 } 1508 1509 if (/^\s*Slot (\d+):/i) { 1510 $slot = $1; 1511 next; 1512 } elsif (/^\s*Slot (\d+) \(virtual\):/i) { 1513 $slot = $1; 1514 next; 1515 } elsif (/^\s*(.*Processor.*|.*controller|.*controler|.*Chassis Interface)(, FRU\s?:.*)?, HW rev (\S+), board revision (\S+)/i) { 1516 $board = $1; 1517 my($hwver) = $3; 1518 my($boardrev) = $4; 1519 if ($board =~ /Processor/) { 1520 if ($board =~ /7000 Route\/Switch/) { 1521 $board = "RSP7000"; 1522 } elsif ($board =~ /Route\/Switch Processor (\d)/) { 1523 $board = "RSP$1"; 1524 } elsif ($board =~ /Route/) { 1525 $board = "RP"; 1526 } elsif ($board =~ /Silicon Switch/) { 1527 $board = "SSP"; 1528 } elsif ($board =~ /Switch/) { 1529 $board = "SP"; 1530 $board = "SSP $sspmem" if $ssp; 1531 } elsif ($board =~ /ATM/) { 1532 $board = "AIP"; 1533 } 1534 } elsif ($board =~ /(.*) controller/i) { 1535 $board = $1; 1536 } 1537 # hwucode{$slot} defined in ShowContCbus 1538 if (defined($hwucode{$slot})) { 1539 ProcessHistory("SLOT","","","!\n!Slot $slot/$board: hvers $hwver rev $boardrev ucode $hwucode{$slot}\n"); 1540 } else { 1541 ProcessHistory("SLOT","","","!\n!Slot $slot/$board: hvers $hwver rev $boardrev\n"); 1542 } 1543 # These are also from the ShowContCbus 1544 ProcessHistory("SLOT","","","!Slot $slot/$board: $ucode{$slot}\n") if (defined $ucode{$slot}); 1545 ProcessHistory("SLOT","","","!Slot $slot/$board: memd $hwmemd{$slot}, cache $hwmemc{$slot}\n") 1546 if ((defined $hwmemd{$slot}) && (defined $hwmemc{$slot})); 1547 ProcessHistory("SLOT","","","!Slot $slot/$board: $hwbuf{$slot}\n") if (defined $hwbuf{$slot}); 1548 next; 1549 } 1550 /Serial number: (\S+)\s*Part number: (\S+)/ && 1551 ProcessHistory("SLOT","","", 1552 "!Slot $slot/$board: part $2, serial $1\n") && 1553 next; 1554 /^\s*Controller Memory Size: (.*)$/ && 1555 ProcessHistory("SLOT","","","!Slot $slot/$board: $1\n") && 1556 next; 1557 if (/PA Bay (\d) Information/) { 1558 my($pano) = $1; 1559 if ("PA" =~ /$board/) { 1560 my($s,$c) = split(/\//,$board); 1561 $board = "$s/$c/PA $pano"; 1562 } else { 1563 $board =~ s/\/PA \d//; 1564 $board = "$board/PA $pano"; 1565 } 1566 next; 1567 } 1568 /\s+(.*) (IP|PA), (\d) ports?,( \S+,)? (FRU\s?: )?(\S+)/ && 1569 ProcessHistory("SLOT","","","!Slot $slot/$board: type $6, $3 ports\n") && 1570 next; 1571 /\s+(.*) (IP|PA)( \(\S+\))?, (\d) ports?/ && 1572 ProcessHistory("SLOT","","","!Slot $slot/$board: type $1$3, $4 ports\n") && 1573 next; 1574 /^\s*HW rev (\S+), Board revision (\S+)/ && 1575 ProcessHistory("SLOT","","","!Slot $slot/$board: hvers $1 rev $2\n") && 1576 next; 1577 /Serial number: (\S+)\s*Part number: (\S+)/ && 1578 ProcessHistory("SLOT","","","!Slot $slot/$board: part $2, serial $1\n") && next; 1579 } 1580 return(0); 1581} 1582 1583# This routine parses "show diag" for the gsr, 7200, 3700, 3600, 2600. 1584# This will create arrays for hw info. 1585sub ShowDiag { 1586 my($INPUT, $OUTPUT, $cmd) = @_; 1587 my($fn, $slot, $WIC); 1588 print STDERR " In ShowDiag: $_" if ($debug); 1589 1590 while (<$INPUT>) { 1591REDUX: tr/\015//d; 1592 if (/^$prompt/) { $found_diag = 1; last}; 1593 next if (/^(\s*|\s*$cmd\s*)$/); 1594 return(1) if (/Line has invalid autocommand /); 1595 next if (/^\s+\^\s*$/); 1596 next if (/^Load for five/); 1597 next if (/^Time source is/); 1598 return(1) if (/(invalid (input|command) detected|type help or )/i); 1599 return(0) if ($found_diag); # Only do this routine once 1600 return(-1) if (/(?:%|command)? authorization failed/i); 1601 /^$/ && next; 1602 # the pager can not be disabled per-session on the PIX 1603 if (/^(<-+ More -+>)/) { 1604 my($len) = length($1); 1605 s/^$1\s{$len}//; 1606 } 1607 1608 s/Port Packet Over SONET/POS/; 1609 if (/^\s*SLOT\s+(\d+)\s+\((.*)\): (.*)/) { 1610 $slot = $1; 1611 ProcessHistory("SLOT","","","!\n"); 1612 ProcessHistory("SLOT","keysort","A","!Slot $slot: $3\n"); 1613 next; 1614 } 1615 if (/^\s*NODE\s+(\S+) : (.*)/) { 1616 $slot = $1; 1617 ProcessHistory("SLOT","","","!\n"); 1618 ProcessHistory("SLOT","keysort","A","!Slot $slot: $2\n"); 1619 next; 1620 } 1621 if (/^\s*PLIM\s+(\S+) : (.*)/) { 1622 $slot = $1 . " PLIM"; 1623 ProcessHistory("SLOT","","","!\n"); 1624 ProcessHistory("SLOT","keysort","A","!Slot $slot: $2\n"); 1625 next; 1626 } 1627 if (/^\s*RACK\s+(\S+) : (.*)/) { 1628 $slot = "Rack/" . $1; 1629 ProcessHistory("SLOT","","","!\n"); 1630 ProcessHistory("SLOT","keysort","A","!Slot $slot: $2\n"); 1631 next; 1632 } 1633 if (/^\s+MAIN:\s* type \S+,\s+(.*)/) { 1634 my($part) = $1; 1635 $_ = <$INPUT>; 1636 if (/^\s+(HW version|Design Release) (\S+)\s+S\/N (\S+)/i) { 1637 ProcessHistory("SLOT","keysort","AM","!Slot $slot/MAIN: part $part, serial $3\n"); 1638 ProcessHistory("SLOT","keysort","AM","!Slot $slot/MAIN: hvers $2\n"); 1639 } else { 1640 ProcessHistory("SLOT","keysort","AM","!Slot $slot/MAIN: part $part\n"); 1641 goto REDUX; 1642 } 1643 next; 1644 } 1645 if (/^\s+MAIN:\s* board type \S+$/) { 1646 $_ = <$INPUT>; 1647 tr/\015//d; 1648 if (/^\s+(.+)$/) { 1649 my($part) = $1; 1650 $_ = <$INPUT>; 1651 tr/\015//d; 1652 if (/^\s+dev (.*)$/) { 1653 my($dev) = $1; 1654 $_ = <$INPUT>; 1655 if (/^\s+S\/N (\S+)/) { 1656 ProcessHistory("SLOT","keysort","AM","!Slot $slot/MAIN: part $part, dev $dev, serial $1\n"); 1657 } else { 1658 ProcessHistory("SLOT","keysort","AM","!Slot $slot/MAIN: part $part, dev $dev\n"); 1659 goto REDUX; 1660 } 1661 } else { 1662 ProcessHistory("SLOT","keysort","AM","!Slot $slot/MAIN: part $part\n"); 1663 goto REDUX; 1664 } 1665 } else { 1666 goto REDUX; 1667 } 1668 next; 1669 } 1670 if (/^c3700\s+(io-board|mid-plane)/i) { 1671 $slot = $1; 1672 ProcessHistory("SLOT","","","!\n"); 1673 ProcessHistory("SLOT","keysort","A","!Slot $slot: part $1\n"); 1674 next; 1675 } 1676 if (/ Engine:\s+(.*)/) { 1677 ProcessHistory("SLOT","keysort","AE","!Slot $slot/Engine: $1\n"); 1678 } 1679 if (/FRU:\s+Linecard\/Module:\s+(\S+)/) { 1680 ProcessHistory("SLOT","keysort","AF","!Slot $slot/FRU: Linecard/Module: $1\n"); 1681 next; 1682 } 1683 if (/\s+Processor Memory:\s+(\S+)/) { 1684 ProcessHistory("SLOT","keysort","AF","!Slot $slot/FRU: Processor Memory: $1\n"); 1685 next; 1686 } 1687 if (/\s+Packet Memory:\s+(\S+)/) { 1688 ProcessHistory("SLOT","keysort","AF","!Slot $slot/FRU: Packet Memory: $1\n"); 1689 next; 1690 } 1691 if (/\s+Route Memory:\s+(\S+)/) { 1692 ProcessHistory("SLOT","keysort","AF","!Slot $slot/FRU: Route Memory: $1\n"); 1693 next; 1694 } 1695 if (/^\s+PCA:\s+(.*)/) { 1696 my($part) = $1; 1697 $_ = <$INPUT>; 1698 if (/^\s+(HW version|design release) (\S+)\s+S\/N (\S+)/i) { 1699 ProcessHistory("SLOT","keysort","C1","!Slot $slot/PCA: part $part, serial $3\n"); 1700 ProcessHistory("SLOT","keysort","C2","!Slot $slot/PCA: hvers $2\n"); 1701 } else { 1702 ProcessHistory("SLOT","keysort","C1","!Slot $slot/PCA: part $part\n"); 1703 goto REDUX; 1704 } 1705 next; 1706 } 1707 if (/^\s+MBUS: .*\)\s+(.*)/) { 1708 my($tmp) = "!Slot $slot/MBUS: part $1"; 1709 $_ = <$INPUT>; 1710 /^\s+HW version (\S+)\s+S\/N (\S+)/ && 1711 ProcessHistory("SLOT","keysort","MB1","$tmp, serial $2\n") && 1712 ProcessHistory("SLOT","keysort","MB2","!Slot $slot/MBUS: hvers $1\n"); 1713 next; 1714 } 1715 if (/^\s+MBUS Agent Software version (.*)/) { 1716 ProcessHistory("SLOT","keysort","MB3","!Slot $slot/MBUS: software $1\n"); 1717 next; 1718 } 1719 if (/^\s+PLD: (.*)/) { 1720 ProcessHistory("SLOT","keysort","P","!Slot $slot/PLD: $1\n"); 1721 next; 1722 } 1723 if (/^\s+MONLIB: (.*)/) { 1724 ProcessHistory("SLOT","keysort","Q","!Slot $slot/MONLIB: $1\n"); 1725 next; 1726 } 1727 if (/^\s+ROM Monitor version (.*)/) { 1728 ProcessHistory("SLOT","keysort","R","!Slot $slot/ROM Monitor: version $1\n"); 1729 next; 1730 } 1731 if (/^\s+ROMMON: Version (.*)/) { 1732 ProcessHistory("SLOT","keysort","R","!Slot $slot/ROMMON: version $1\n"); 1733 next; 1734 } 1735 if (/^\s+Fabric Downloader version used (.*)/) { 1736 ProcessHistory("SLOT","keysort","Z","!Slot $slot/Fabric Downloader: version $1\n"); 1737 next; 1738 } 1739 if (/^\s+DRAM size: (\d+)/) { 1740 my($dram) = $1 / 1048576; 1741 $_ = <$INPUT>; 1742 if (/^\s+FrFab SDRAM size: (\d+)/) { 1743 ProcessHistory("SLOT","keysort","MB4","!Slot $slot/MBUS: $dram Mbytes DRAM, " 1744 . $1 / 1024 . " Kbytes SDRAM\n"); 1745 } else { 1746 ProcessHistory("SLOT","keysort","MB4","!Slot $slot/MBUS: $dram Mbytes DRAM\n"); 1747 goto REDUX; 1748 } 1749 next; 1750 } 1751 # 7200, 3800, 3600, 2600, and 1700 stuff 1752 if (/^(Slot)\s+(\d+(\/\d+)?):/ 1753 || /^\s+(PVDM|WIC|VIC|WIC\/VIC|WIC\/VIC\/HWIC) Slot (\d):/ 1754 || /^(Encryption AIM) (\d):/ 1755 || /^(AIM Module in slot:) (\d)/) { 1756 if ($1 eq "PVDM") { 1757 $WIC = "/$2"; 1758 } elsif ($1 eq "WIC") { 1759 $WIC = "/$2"; 1760 } elsif ($1 eq "VIC") { 1761 $WIC = "/$2"; 1762 } elsif ($1 eq "WIC/VIC") { 1763 $WIC = "/$2"; 1764 } elsif ($1 eq "WIC/VIC/HWIC") { 1765 $WIC = "/$2"; 1766 } elsif ($1 eq "DSP") { 1767 $WIC = "/$2"; 1768 } elsif ($1 eq "Encryption AIM") { 1769 $slot = "$2"; 1770 $WIC = undef; 1771 ProcessHistory("SLOT","","","!\n"); 1772 ProcessHistory("SLOT","keysort","B","!Slot $slot: type $1\n"); 1773 next; 1774 } elsif ($1 eq "AIM Module in slot:") { 1775 $slot = "AIM $2"; 1776 $WIC = undef; 1777 ProcessHistory("SLOT","","","!\n"); 1778 ProcessHistory("SLOT","keysort","B", 1779 "!Slot $slot: type AIM Module\n"); 1780 next; 1781 } else { 1782 $slot = $2; 1783 $WIC = undef; 1784 } 1785 $_ = <$INPUT>; tr/\015//d; 1786 1787 # clean up hideous 7200/etc formats to look more like 7500 output 1788 s/Fast-ethernet on C7200 I\/O card/FE-IO/; 1789 s/ with MII or RJ45/-TX/; 1790 s/Fast-ethernet /100Base/; s/[)(]//g; 1791 s/intermediate reach/IR/i; 1792 1793 ProcessHistory("SLOT","","","!\n"); 1794 /\s+(.*) port adapter,?\s+(\d+)\s+/i && 1795 ProcessHistory("SLOT","keysort","B", 1796 "!Slot $slot: type $1, $2 ports\n") && next; 1797 # I/O controller with no interfaces 1798 /\s+(.*)\s+port adapter\s*$/i && 1799 ProcessHistory("SLOT","keysort","B", 1800 "!Slot $slot: type $1, 0 ports\n") && next; 1801 /\s+(.*)\s+daughter card(.*)$/ && 1802 ProcessHistory("SLOT","keysort","B", 1803 "!Slot $slot$WIC: type $1$2\n") && next; 1804 /\s+(FT1)$/ && 1805 ProcessHistory("SLOT","keysort","B", 1806 "!Slot $slot$WIC: type $1\n") && next; 1807 # AS5300/5400 handling 1808 /^Hardware is\s+(.*)$/i && 1809 ProcessHistory("SLOT","keysort","B","!Slot $slot: type $1\n") 1810 && next; 1811 /^DFC type is\s+(.*)$/i && 1812 ProcessHistory("SLOT","keysort","B","!Slot $slot: type $1\n") 1813 && next; 1814 # 1815 # handle WICs lacking "daughter card" in the 2nd line of their 1816 # show diag o/p 1817 if (length($WIC)) { 1818 s/^\s+//; 1819 ProcessHistory("SLOT","keysort","B","!Slot $slot$WIC: type $_"); 1820 } 1821 next; 1822 } elsif (/^\s+(.* (DSP) Module) Slot (\d):/) { 1823 # The 1760 (at least) has yet another format...where it has two 1824 # dedicated DSP slots, and thus two slot 0s. 1825 my($TYPE) = $1; 1826 $WIC = "/$3"; 1827 ProcessHistory("SLOT","","","!\n"); 1828 ProcessHistory("SLOT","keysort","B", 1829 "!Slot $slot$WIC: type $TYPE\n"); 1830 next; 1831 } 1832 # yet another format. seen on 2600s w/ 12.1, but appears to be all 1833 # 12.1, including 7200s & 3700s. Sometimes the PCB serial appears 1834 # before the hardware revision. 1835 if (/(pcb serial number|hardware revision)\s+:\s+(\S+)$/i) { 1836 my($hw, $pn, $rev, $sn); 1837 if ($1 =~ /^pcb/i) { 1838 $sn = $2; 1839 } else { 1840 $hw = $2; 1841 } 1842 while (<$INPUT>) { 1843 tr/\015//d; 1844 1845 # Sometimes "show diag" just ends while we are 1846 # trying to process this pcb stuff. Check for a 1847 # prompt so we can get out. 1848 if (/^$prompt/) { 1849 $found_diag = 1; 1850 goto PerlSucks; 1851 } 1852 1853 if (/0x..: / || /^$/) { 1854 # no effing idea why break does not work there 1855 goto PerlSucks; 1856 } 1857 if (/hardware revision\s+:\s+(\S+)/i) { $hw = $1; } 1858 if (/part number\s+:\s+(\S+)/i) { $pn = $1; } 1859 if (/board revision\s+:\s+(\S+)/i) { $rev = $1; } 1860 if (/pcb serial number\s+:\s+(\S+)/i) { $sn = $1; } 1861 # fru/pid bits, true Cisco evolving "standard", hopefully 1862 # "show inventory" will be "the way" soon. 1863 # 1864 if (/product \(fru\) number\s+:\s+(\S+)/i) { $fn = $1; } 1865 if (/product number\s+:\s+(\S+)/i) { $fn = $1; } 1866 if (/product\s+identifier\s+\(PID\)\s+:\s+(\S+)/i) { $fn = $1; } 1867 if (/fru\s+part\s+number\s+(\S+)/i) { $fn = $1; } 1868 } 1869PerlSucks: 1870 # fru/pid bits 1871 # If slot is blank, call it "Chassis" 1872 if ($slot eq "") { 1873 $slot = "Chassis"; 1874 } 1875 ProcessHistory("SLOT","keysort","AG","!Slot $slot$WIC: fru $fn\n"); 1876 # 1877 ProcessHistory("SLOT","keysort","B","!Slot $slot$WIC: hvers $hw rev $rev\n"); 1878 ProcessHistory("SLOT","keysort","C","!Slot $slot$WIC: part $pn, serial $sn\n"); 1879 # If we saw the prompt, then we are done. 1880 last if $found_diag; 1881 } 1882 /revision\s+(\S+).*revision\s+(\S+)/ && 1883 ProcessHistory("SLOT","keysort","C","!Slot $slot$WIC: hvers $1 rev $2\n") && 1884 next; 1885 /number\s+(\S+)\s+Part number\s+(\S+)/ && 1886 ProcessHistory("SLOT","keysort","D","!Slot $slot$WIC: part $2, serial $1\n") && 1887 next; 1888 # AS5x00 bits 1889 /^\ Board Revision\s+(\S+),\s+Serial Number\s+(\S+),/ && 1890 ProcessHistory("SLOT","keysort","D", 1891 "!Slot $slot$WIC: rev $1, serial $2\n") && next; 1892 /^\ Board Hardware Version\s+(\S+),\s+Item Number\s+(\S+),/ && 1893 ProcessHistory("SLOT","keysort","D", 1894 "!Slot $slot$WIC: hvers $1, part $2\n") && next; 1895 /^Motherboard Info:/ && 1896 ProcessHistory("SLOT","keysort","D", 1897 "!Slot $slot$WIC: Motherboard\n") && next; 1898 # 1899 } 1900 ProcessHistory("SLOT","","","!\n"); 1901 return(0); 1902} 1903 1904# This routine parses "show inventory". 1905sub ShowInventory { 1906 my($INPUT, $OUTPUT, $cmd) = @_; 1907 print STDERR " In ShowInventory: $_" if ($debug); 1908 1909 while (<$INPUT>) { 1910 tr/\015//d; 1911 return if (/^\s*\^$/); 1912 if (/^$prompt/) { $found_inventory = 1; last}; 1913 next if (/^(\s*|\s*$cmd\s*)$/); 1914 return(1) if (/Line has invalid autocommand /); 1915 next if (/^\s+\^\s*$/); 1916 next if (/^Load for five/); 1917 next if (/^Time source is/); 1918 return(1) if (/(invalid (input|command) detected|type help or )/i); 1919 return(-1) if (/(?:%|command)? authorization failed/i); 1920 return(0) if ($found_inventory); # Only do this routine once 1921 # the pager can not be disabled per-session on the PIX 1922 if (/^(<-+ More -+>)/) { 1923 my($len) = length($1); 1924 s/^$1\s{$len}//; 1925 } 1926 1927 next if (/^Load for /); 1928 next if (/^Time source is /); 1929 if (/^(NAME: "[^"]*",) (DESCR: "[^"]+")/) { 1930 ProcessHistory("INVENTORY","","", sprintf("!%-30s %s\n", $1, $2)); 1931 next; 1932 } 1933 # split PID/VID/SN line 1934 if (/^PID: (\S*)\s*,\s*VID: (\S*)\s*,\s*SN: (\S*)\s*$/) { 1935 my($pid,$vid,$sn) = ($1, $2, $3); 1936 my($entries) = ""; 1937 # filter <empty>, "0x" and "N/A" lines 1938 if ($pid !~ /^(|0x|N\/A)$/) { 1939 $entries .= "!PID: $pid\n"; 1940 } 1941 if ($vid !~ /^(|0x|N\/A)$/) { 1942 $entries .= "!VID: $vid\n"; 1943 } 1944 if ($sn !~ /^(|0x|N\/A)$/) { 1945 $entries .= "!SN: $sn\n"; 1946 } 1947 ProcessHistory("INVENTORY","","", "$entries"); 1948 next; 1949 } 1950 ProcessHistory("INVENTORY","","","!$_"); 1951 } 1952 ProcessHistory("INVENTORY","","","!\n"); 1953 1954 return(0); 1955} 1956 1957# This routine parses "show module". 1958sub ShowModule { 1959 my($INPUT, $OUTPUT, $cmd) = @_; 1960 print STDERR " In ShowModule: $_" if ($debug); 1961 1962 my(@lines); 1963 my($slot, $pa); 1964 my($switch, $switch_n); 1965 1966 if ($vss_show_module == 1) { 1967 while (<$INPUT>) { 1968 last if (/^$prompt/); 1969 } 1970 return(0); 1971 } 1972 while (<$INPUT>) { 1973 tr/\015//d; 1974 next if (/^\s*\^$/); 1975 next if (/^Load for five/); 1976 next if (/^Time source is/); 1977 if (/online diag status/i) { 1978 $vss_show_module = 1; 1979 next; 1980 } 1981 last if (/^$prompt/); 1982 next if (/^(\s*|\s*$cmd\s*)$/); 1983 return(-1) if (/(?:%|command)? authorization failed/i); 1984 # the pager can not be disabled per-session on the PIX 1985 if (/^(<-+ More -+>)/) { 1986 my($len) = length($1); 1987 s/^$1\s{$len}//; 1988 } 1989 1990 # match Switch Number: 2 Role: Virtual Switch Active/Standby 1991 if (/^ *Switch Number: *(\d) .*Virtual Switch\s+(\S+)/) { 1992 $switch_n = $1; 1993 $switch = "Sw$1 "; 1994 ProcessHistory("Module","","","!Virtual Switch $1 is $2\n"); 1995 next; 1996 } 1997 1998 # match slot/card info line 1999 if (/^ *(\d+)\s+(\d+)\s+(.*)\s+(\S+)\s+(\S+)\s*$/) { 2000 $lines[$switch_n * 10000 + $1 * 1000] .= "!Slot ${switch}$1: type $3, $2 ports\n!Slot ${switch}$1: part $4, serial $5\n"; 2001 $lines[$switch_n * 10000 + $1 * 1000] =~ s/\s+,/,/g; 2002 next; 2003 } 2004 # now match the Revs in the second paragraph of o/p and stick it in 2005 # the array with the previous bits...grumble. 2006 if (/^ *(\d+)\s+\S+\s+to\s+\S+\s+(\S+)\s+(\S*)\s+(\S+)(\s+\S+)?\s*$/) { 2007 $lines[$switch_n * 10000 + $1 * 1000] .= "!Slot ${switch}$1: hvers $2, firmware $3, sw $4\n"; 2008 $lines[$switch_n * 10000 + $1 * 1000] =~ s/\s+,/,/g; 2009 next; 2010 } 2011 # grab the sub-modules, if any 2012 if (/^\s+(\d+)\s(.*)\s+(\S+)\s+(\S+)\s+(\S+)\s+\S+\s*$/) { 2013 my($idx); 2014 $pa = 0 if ($1 != $slot); 2015 $slot = $1; 2016 $idx = $switch_n * 10000 + $1 * 1000 + $1 * 10 + $pa; 2017 $lines[$idx] .= "!Slot ${switch}$1/$pa: type $2\n"; 2018 $lines[$idx] .= "!Slot ${switch}$slot/$pa: part $3, serial $4\n"; 2019 $lines[$idx] .= "!Slot ${switch}$slot/$pa: hvers $5\n"; 2020 $pa++; 2021 } 2022 } 2023 if ($switch_n != 0) { 2024 ProcessHistory("Module","","","!\n"); 2025 } 2026 foreach $slot (@lines) { 2027 next if ($slot =~ /^\s*$/); 2028 ProcessHistory("Module","","","$slot!\n"); 2029 } 2030 2031 return(0); 2032} 2033 2034# This routine parses "show spe version". 2035sub ShowSpeVersion { 2036 my($INPUT, $OUTPUT, $cmd) = @_; 2037 print STDERR " In ShowSpeVersion: $_" if ($debug); 2038 2039 while (<$INPUT>) { 2040 tr/\015//d; 2041 last if (/^$prompt/); 2042 next if (/^(\s*|\s*$cmd\s*)$/); 2043 return(1) if /^\s*\^\s*$/; 2044 return(1) if (/Line has invalid autocommand /); 2045 next if (/^\s+\^\s*$/); 2046 next if (/^Load for five/); 2047 next if (/^Time source is/); 2048 return(1) if (/(invalid (input|command) detected|type help or )/i); 2049 return(-1) if (/(?:%|command)? authorization failed/i); 2050 2051 ProcessHistory("MODEM","","","!Modem: $_") && next; 2052 } 2053 ProcessHistory("MODEM","","","!\n"); 2054 return(0); 2055} 2056 2057# This routine parses "show c7200" for the 7200 2058# This will create arrays for hw info. 2059sub ShowC7200 { 2060 my($INPUT, $OUTPUT, $cmd) = @_; 2061 # Skip if this is not a 7200. 2062 print STDERR " In ShowC7200: $_" if ($debug); 2063 2064 while (<$INPUT>) { 2065 tr/\015//d; 2066 last if (/^$prompt/); 2067 next if (/^(\s*|\s*$cmd\s*)$/); 2068 next if (/^\s+\^\s*$/); 2069 next if (/^Load for five/); 2070 next if (/^Time source is/); 2071 return(1) if (/(invalid (input|command) detected|type help or )/i); 2072 #return(1) if ($type !~ /^72/); 2073 return(-1) if (/(?:%|command)? authorization failed/i); 2074 /^$/ && next; 2075 # the pager can not be disabled per-session on the PIX 2076 if (/^(<-+ More -+>)/) { 2077 my($len) = length($1); 2078 s/^$1\s{$len}//; 2079 } 2080 2081 if (/^(C7200 )?Midplane EEPROM:/) { 2082 $_ = <$INPUT>; 2083 /revision\s+(\S+).*revision\s+(\S+)/; 2084 ProcessHistory("SLOT","","","!Slot Midplane: hvers $1 rev $2\n"); 2085 $_ = <$INPUT>; 2086 /number\s+(\S+)\s+Part number\s+(\S+)/; 2087 ProcessHistory("SLOT","","","!Slot Midplane: part $2, serial $1\n!\n"); 2088 next; 2089 } 2090 if (/C720\d(VXR)? CPU EEPROM:/) { 2091 my ($hvers,$rev,$part,$serial); 2092 # npe400s report their cpu eeprom info differently w/ 12.0.21S 2093 while (<$INPUT>) { 2094 /Hardware Revision\s+: (\S+)/ && ($hvers = $1) && next; 2095 /Board Revision\s+: (\S+)/ && ($rev = $1) && next; 2096 /Part Number\s+: (\S+)/ && ($part = $1) && next; 2097 /Serial Number\s+: (\S+)/ && ($serial = $1) && next; 2098 /revision\s+(\S+).*revision\s+(\S+)/ && 2099 ($hvers = $1, $rev = $2) && next; 2100 /number\s+(\S+)\s+Part number\s+(\S+)/ && 2101 ($serial = $1, $part = $2) && next; 2102 /^\s*$/ && last; 2103 } 2104 ProcessHistory("SLOT","","","!Slot CPU: hvers $hvers rev $rev\n"); 2105 ProcessHistory("SLOT","","","!Slot CPU: part $part, serial $serial\n!\n"); 2106 next; 2107 } 2108 } 2109 return(0); 2110} 2111 2112# This routine parses "show capture". Intended for ASA/PIXes. 2113sub ShowCapture { 2114 my($INPUT, $OUTPUT, $cmd) = @_; 2115 print STDERR " In ShowCapture: $_" if ($debug); 2116 my $capture_found = 0; 2117 while (<$INPUT>) { 2118 tr/\015//d; 2119 last if (/^$prompt/); 2120 return(1) if (/^(\s*|\s*$cmd\s*)$/); 2121 return(1) if /^\s*\^\s*$/; 2122 return(1) if (/Line has invalid autocommand /); 2123 next if (/^\s+\^\s*$/); 2124 next if (/^Load for five/); 2125 next if (/^Time source is/); 2126 return(1) if (/(invalid (input|command) detected|type help or )/i); 2127 return(-1) if (/(?:%|command)? authorization failed/i); 2128 # the pager can not be disabled per-session on the PIX 2129 if (/^(<-+ More -+>)/) { 2130 my($len) = length($1); 2131 s/^$1\s{$len}//; 2132 } 2133 2134 if (/capture (.*) type/) { 2135 my $cap_name = $1; 2136 s/\d+ bytes/<COUNTER> bytes/; 2137 ProcessHistory("CAPTURE","","","!Capture: $cap_name\n"); 2138 ProcessHistory("CAPTURE","","","!Capture: $_"); 2139 } else { 2140 ProcessHistory("CAPTURE","","","!Capture: $_"); 2141 } 2142 $capture_found = 1 2143 } 2144 ProcessHistory("CAPTURE","","","!\n") if ($capture_found == 1); 2145 return(0); 2146} 2147 2148# This routine parses "show dot1x" 2149sub ShowDot1x { 2150 my($INPUT, $OUTPUT, $cmd) = @_; 2151 print STDERR " In ShowVTP: $_" if ($debug); 2152 2153 while (<$INPUT>) { 2154 tr/\015//d; 2155 last if (/^$prompt/); 2156 next if (/^(\s*|\s*$cmd\s*)$/); 2157 return(1) if /^\s*\^\s*$/; 2158 return(1) if (/Line has invalid autocommand /); 2159 next if (/^\s+\^\s*$/); 2160 next if (/^Load for five/); 2161 next if (/^Time source is/); 2162 return(1) if (/(invalid (input|command) detected|type help or )/i); 2163 return(-1) if (/(?:%|command)? authorization failed/i); 2164 next if (/^Configuration last modified by/); 2165 # the pager can not be disabled per-session on the PIX 2166 if (/^(<-+ More -+>)/) { 2167 my($len) = length($1); 2168 s/^$1\s{$len}//; 2169 } 2170 2171 # if dot1x is enabled, do not collect show vlan output 2172 if (/^sysauthcontrol\s+(?:=\s+)?(\S+)/i) { 2173 if ($1 !~ /disabled/i && $filter_osc > 1) { 2174 $DO_SHOW_VLAN = 1; 2175 } 2176 } 2177 ProcessHistory("COMMENTS","keysort","I0","!DOT1x: $_"); 2178 } 2179 ProcessHistory("COMMENTS","keysort","I0","!\n"); 2180 return(0); 2181} 2182 2183 2184# This routine parses "show vtp status" 2185sub ShowVTP { 2186 my($INPUT, $OUTPUT, $cmd) = @_; 2187 print STDERR " In ShowVTP: $_" if ($debug); 2188 2189 while (<$INPUT>) { 2190 tr/\015//d; 2191 last if (/^$prompt/); 2192 next if (/^(\s*|\s*$cmd\s*)$/); 2193 return(1) if /^\s*\^\s*$/; 2194 return(1) if (/Line has invalid autocommand /); 2195 next if (/^\s+\^\s*$/); 2196 next if (/^Load for five/); 2197 next if (/^Time source is/); 2198 return(1) if (/(invalid (input|command) detected|type help or )/i); 2199 #return(1) if ($type !~ /^(2900XL|3500XL|6000)$/); 2200 return(-1) if (/(?:%|command)? authorization failed/i); 2201 next if (/^Configuration last modified by/); 2202 # the pager can not be disabled per-session on the PIX 2203 if (/^(<-+ More -+>)/) { 2204 my($len) = length($1); 2205 s/^$1\s{$len}//; 2206 } 2207 2208 if (/^VTP Operating Mode\s+:\s+(Client)/) { 2209 $DO_SHOW_VLAN = 1; 2210 } 2211 ProcessHistory("COMMENTS","keysort","I0","!VTP: $_"); 2212 } 2213 ProcessHistory("COMMENTS","keysort","I0","!\n"); 2214 return(0); 2215} 2216 2217# This routine parses "show vlan" 2218sub ShowVLAN { 2219 my($INPUT, $OUTPUT, $cmd) = @_; 2220 print STDERR " In ShowVLAN: $_" if ($debug); 2221 2222 ($_ = <$INPUT>, return(1)) if ($DO_SHOW_VLAN); 2223 2224 while (<$INPUT>) { 2225 tr/\015//d; 2226 last if (/^$prompt/); 2227 next if (/^(\s*|\s*$cmd\s*)$/); 2228 return(1) if /^\s*\^\s*$/; 2229 return(1) if (/Line has invalid autocommand /); 2230 next if (/^\s+\^\s*$/); 2231 next if (/^Load for five/); 2232 next if (/^Time source is/); 2233 return(1) if (/(invalid (input|command) detected|type help or )/i); 2234 return(1) if (/ambiguous command/i); 2235 return(1) if (/incomplete command/i); 2236 return(-1) if (/(?:%|command)? authorization failed/i); 2237 # the pager can not be disabled per-session on the PIX 2238 if (/^(<-+ More -+>)/) { 2239 my($len) = length($1); 2240 s/^$1\s{$len}//; 2241 } 2242 return(0) if (/no virtual lans configured/i); 2243 # some ASAs do not support show vlan 2244 return(0) if (/use .show switch vlan. to view the vlans that have /i); 2245 2246 # GSR-specific, i think, filter 2247 if (/received:\s+transmitted:/i) { 2248 while (<$INPUT>) { 2249 last if (/^\s*$/); 2250 goto OUT if (/^$prompt/); 2251 } 2252 } 2253 2254 next if (/total.*packets.*(input|output)/i); 2255 2256 # Aironet AP's traffic counters 2257 next if (/\d+\s+bytes.*(input|output)/i); 2258 next if (/^\s*Other\s+\d+\s+\d+\s*$/i); 2259 next if (/^\s*Bridging\s+Bridge.Group.\d+\s+\d+\s+\d+\s*$/i); 2260 2261 ProcessHistory("COMMENTS","keysort","IO","!VLAN: $_"); 2262 } 2263OUT:ProcessHistory("COMMENTS","keysort","IO","!\n"); 2264 return(0); 2265} 2266 2267# This routine processes a "show shun". Intended for ASA/PIXes. 2268sub ShowShun { 2269 my($INPUT, $OUTPUT, $cmd) = @_; 2270 print STDERR " In ShowShun: $_" if ($debug); 2271 my $shun_found = 0; 2272 2273 while (<$INPUT>) { 2274 tr/\015//d; 2275 last if (/^$prompt/); 2276 return(1) if (/^(\s*|\s*$cmd\s*)$/); 2277 return(1) if /^\s*\^\s*$/; 2278 return(1) if (/Line has invalid autocommand /); 2279 return(1) if (/(invalid (input|command) detected|type help or )/i); 2280 return(-1) if (/(?:%|command)? authorization failed/i); 2281 2282 next if (/^\s+\^\s*$/); 2283 next if (/^Load for five/); 2284 next if (/^Time source is/); 2285 # the pager can not be disabled per-session on the PIX 2286 if (/^(<-+ More -+>)/) { 2287 my($len) = length($1); 2288 s/^$1\s{$len}//; 2289 } 2290 2291 ProcessHistory("SHUN","","","!Shun: $_"); 2292 $shun_found = 1; 2293 } 2294 ProcessHistory("SHUN","","","!\n") if ($shun_found == 1); 2295 return(0); 2296} 2297 2298# This routine processes a "write term" 2299sub WriteTerm { 2300 my($INPUT, $OUTPUT, $cmd) = @_; 2301 print STDERR " In WriteTerm: $_" if ($debug); 2302 my($comment, $linecnt) = (0,0); 2303 2304 while (<$INPUT>) { 2305TOP: 2306 tr/\015//d; 2307 last if (/^$prompt/); 2308 return(1) if (!$linecnt && /^\s+\^\s*$/); 2309 next if (/^\s*$cmd\s*$/); 2310 return(1) if (/Line has invalid autocommand /); 2311 next if (/^\s+\^\s*$/); 2312 next if (/^Load for five/); 2313 next if (/^Time source is/); 2314 return(1) if (/(invalid (input|command) detected|type help or )/i); 2315 return(1) if (/\%Error: No such file or directory/); 2316 return(1) if (/(Open device \S+ failed|Error opening \S+:)/); 2317 return(0) if ($found_end); # Only do this routine once 2318 return(-1) if (/(?:%|command)? authorization failed/i); 2319 return(-1) if (/% ?configuration buffer full/i); 2320 # the pager can not be disabled per-session on the PIX 2321 if (/^(<-+ More -+>)/) { 2322 my($len) = length($1); 2323 s/^$1\s{$len}//; 2324 } 2325 /^! no configuration change since last restart/i && next; 2326 # skip emtpy lines at the beginning 2327 if (!$linecnt && /^\s*$/) { 2328 next; 2329 } 2330 if (!$linecnt && defined($config_register)) { 2331 ProcessHistory("","","", "!\nconfig-register $config_register\n"); 2332 } 2333 2334 /Non-Volatile memory is in use/ && return(-1); # NvRAM is locked 2335 /% Configuration buffer full, / && return(-1); # buffer is in use 2336 $linecnt++; 2337 # skip the crap 2338 if (/^(##+|(building|current) configuration)/i) { 2339 while (<$INPUT>) { 2340 next if (/^Current configuration\s*:/i); 2341 next if (/^:/); 2342 next if (/^([%!].*|\s*)$/); 2343 next if (/^ip add.*ipv4:/); # band-aid for 3620 12.0S 2344 last; 2345 } 2346 tr/\015//d; 2347 } 2348 # config timestamp on MDS/NX-OS 2349 /Time: / && next; 2350 # skip ASA 5520 configuration author line 2351 /^: written by /i && next; 2352 # some versions have other crap mixed in with the bits in the 2353 # block above 2354 /^! (Last configuration|NVRAM config last)/ && next; 2355 # and for the ASA 2356 /^: (Written by \S+ at|Saved)/ && next; 2357 2358 # skip consecutive comment lines to avoid oscillating extra comment 2359 # line on some access servers. grrr. 2360 if (/^!\s*$/) { 2361 next if ($comment); 2362 ProcessHistory("","","",$_); 2363 $comment++; 2364 next; 2365 } 2366 $comment = 0; 2367 2368 # Dog gone Cool matches to process the rest of the config 2369 /^tftp-server flash / && next; # kill any tftp remains 2370 /^ntp clock-period / && next; # kill ntp clock-period 2371 /^ clockrate / && next; # kill clockrate on serial interfaces 2372 # kill rx/txspeed (particularly on cellular modem cards) 2373 if (/^(line (\d+(\/\d+\/\d+)?|con|aux|vty))/) { 2374 my($key) = $1; 2375 my($lineauto) = (0); 2376 if ($key =~ /con/) { 2377 $key = -1; 2378 } elsif ($key =~ /aux/) { 2379 $key = -2; 2380 } elsif ($key =~ /vty/) { 2381 $key = -3; 2382 } 2383 ProcessHistory("LINE","keysort","$key","$_"); 2384 while (<$INPUT>) { 2385 tr/\015//d; 2386 last if (/^$prompt/); 2387 goto TOP if (! /^ /); 2388 next if (/\s*(rx|tx)speed \d+/); 2389 next if (/^ length /); # kill length on serial lines 2390 next if (/^ width /); # kill width on serial lines 2391 $lineauto = 0 if (/^[^ ]/); 2392 $lineauto = 1 if /^ modem auto/; 2393 /^ speed / && $lineauto && next; # kill speed on serial lines 2394 if (/^(\s+password) \d+ / && $filter_pwds >= 1) { 2395 $_ = "!$1 <removed>\n"; 2396 } 2397 ProcessHistory("LINE","keysort","$key","$_"); 2398 } 2399 } 2400 if (/^(enable )?(password|passwd)( level \d+)? / && $filter_pwds >= 1) { 2401 ProcessHistory("ENABLE","","","!$1$2$3 <removed>\n"); 2402 next; 2403 } 2404 if (/^(enable secret) / && $filter_pwds >= 2) { 2405 ProcessHistory("ENABLE","","","!$1 <removed>\n"); 2406 next; 2407 } 2408 if (/^username (\S+)(\s.*)? secret /) { 2409 if ($filter_pwds >= 2) { 2410 ProcessHistory("USER","keysort","$1", 2411 "!username $1$2 secret <removed>\n"); 2412 } else { 2413 ProcessHistory("USER","keysort","$1","$_"); 2414 } 2415 next; 2416 } 2417 if (/^username (\S+)(\s.*)? password ((\d) \S+|\S+)/) { 2418 if ($filter_pwds >= 2) { 2419 ProcessHistory("USER","keysort","$1", 2420 "!username $1$2 password <removed>\n"); 2421 } elsif ($filter_pwds >= 1 && $4 ne "5"){ 2422 ProcessHistory("USER","keysort","$1", 2423 "!username $1$2 password <removed>\n"); 2424 } else { 2425 ProcessHistory("USER","keysort","$1","$_"); 2426 } 2427 next; 2428 } 2429 # cisco AP w/ IOS 2430 if (/^(wlccp \S+ username (\S+)(\s.*)? password) (\d \S+|\S+)/) { 2431 if ($filter_pwds >= 1) { 2432 ProcessHistory("USER","keysort","$2","!$1 <removed>\n"); 2433 } else { 2434 ProcessHistory("USER","keysort","$2","$_"); 2435 } 2436 next; 2437 } 2438 # filter auto "rogue ap" configuration lines 2439 /^rogue ap classify / && next; 2440 if (/^( set session-key (in|out)bound ah \d+ )/ && $filter_pwds >= 1) { 2441 ProcessHistory("","","","!$1<removed>\n"); 2442 next; 2443 } 2444 if (/^( set session-key (in|out)bound esp \d+ (authenticator|cypher) )/ 2445 && $filter_pwds >= 1) { 2446 ProcessHistory("","","","!$1<removed>\n"); 2447 next; 2448 } 2449 if (/^(\s*)password / && $filter_pwds >= 1) { 2450 ProcessHistory("LINE-PASS","","","!$1password <removed>\n"); 2451 next; 2452 } 2453 if (/^(\s*)secret / && $filter_pwds >= 2) { 2454 ProcessHistory("LINE-PASS","","","!$1secret <removed>\n"); 2455 next; 2456 } 2457 if (/^\s*(.*?neighbor.*?) (\S*) password / && $filter_pwds >= 1) { 2458 ProcessHistory("","","","! $1 $2 password <removed>\n"); 2459 next; 2460 } 2461 if (/^(\s*ppp .* hostname) .*/ && $filter_pwds >= 1) { 2462 ProcessHistory("","","","!$1 <removed>\n"); next; 2463 } 2464 if (/^(\s*ppp .* password) \d .*/ && $filter_pwds >= 1) { 2465 ProcessHistory("","","","!$1 <removed>\n"); next; 2466 } 2467 if (/^(ip ftp password) / && $filter_pwds >= 1) { 2468 ProcessHistory("","","","!$1 <removed>\n"); next; 2469 } 2470 if (/^( ip ospf authentication-key) / && $filter_pwds >= 1) { 2471 ProcessHistory("","","","!$1 <removed>\n"); next; 2472 } 2473 # isis passwords appear to be completely plain-text 2474 if (/^\s+isis password (\S+)( .*)?/ && $filter_pwds >= 1) { 2475 ProcessHistory("","","","!isis password <removed>$2\n"); next; 2476 } 2477 if (/^\s+(domain-password|area-password) (\S+)( .*)?/ 2478 && $filter_pwds >= 1) { 2479 ProcessHistory("","","","!$1 <removed>$3\n"); next; 2480 } 2481 # this is reversable, despite 'md5' in the cmd 2482 if (/^( ip ospf message-digest-key \d+ md5) / && $filter_pwds >= 1) { 2483 ProcessHistory("","","","!$1 <removed>\n"); next; 2484 } 2485 # this is also reversable, despite 'md5 encrypted' in the cmd 2486 if (/^( message-digest-key \d+ md5 (7|encrypted)) / 2487 && $filter_pwds >= 1) { 2488 ProcessHistory("","","","!$1 <removed>\n"); next; 2489 } 2490 if (/^((crypto )?isakmp key) (\d )?\S+ / && $filter_pwds >= 1) { 2491 ProcessHistory("","","","!$1 <removed> $'"); next; 2492 } 2493 # filter HSRP passwords 2494 if (/^(\s+standby \d+ authentication) / && $filter_pwds >= 1) { 2495 ProcessHistory("","","","!$1 <removed>\n"); next; 2496 } 2497 # this appears in "measurement/sla" images 2498 if (/^(\s+key-string \d?)/ && $filter_pwds >= 1) { 2499 ProcessHistory("","","","!$1 <removed>\n"); next; 2500 } 2501 if (/^( l2tp tunnel \S+ password)/ && $filter_pwds >= 1) { 2502 ProcessHistory("","","","!$1 <removed>\n"); next; 2503 } 2504 # l2tp-class secret 2505 if (/^( digest secret 7?)/ && $filter_pwds >= 1) { 2506 ProcessHistory("","","","!$1 <removed>\n"); next; 2507 } 2508 # i am told these are plain-text on the PIX 2509 if (/^(vpdn username (\S+) password)/) { 2510 if ($filter_pwds >= 1) { 2511 ProcessHistory("USER","keysort","$2","!$1 <removed>\n"); 2512 } else { 2513 ProcessHistory("USER","keysort","$2","$_"); 2514 } 2515 next; 2516 } 2517 # ASA/PIX keys in more system:running-config 2518 if (/^(( ikev2)? (local|remote)-authentication pre-shared-key ).*/ && 2519 $filter_pwds >= 1) { 2520 ProcessHistory("","","","!$1 <removed> $'"); next; 2521 } 2522 # ASA/PIX keys in more system:running-config 2523 if (/^(( ikev1)? pre-shared-key | key |failover key ).*/ && 2524 $filter_pwds >= 1) { 2525 ProcessHistory("","","","!$1 <removed> $'"); next; 2526 } 2527 # ASA/PIX keys in more system:running-config 2528 if (/(\s+ldap-login-password )\S+(.*)/ && $filter_pwds >= 1) { 2529 ProcessHistory("","","","!$1 <removed> $'"); next; 2530 } 2531 # filter WPA password such as on cisco 877W ISR 2532 if (/^\s+(wpa-psk ascii|hex \d) / && $filter_pwds >= 1) { 2533 ProcessHistory("","","","!$1 <removed>\n"); next; 2534 } 2535 # 2536 if (/^( cable shared-secret )/ && $filter_pwds >= 1) { 2537 ProcessHistory("","","","!$1 <removed>\n"); 2538 next; 2539 } 2540 /fair-queue individual-limit/ && next; 2541 # sort ip explicit-paths. 2542 if (/^ip explicit-path name (\S+)/) { 2543 my($key) = $1; 2544 my($expath) = $_; 2545 while (<$INPUT>) { 2546 tr/\015//d; 2547 last if (/^$prompt/ || ! /^(ip explicit-path name |[ !])/); 2548 if (/^ip explicit-path name (\S+)/) { 2549 ProcessHistory("EXPATH","keysort","$key","$expath"); 2550 $key = $1; 2551 $expath = $_; 2552 } else { 2553 $expath .= $_; 2554 } 2555 } 2556 ProcessHistory("EXPATH","keysort","$key","$expath"); 2557 } 2558 # sort route-maps 2559 if (/^route-map (\S+)/) { 2560 my($key) = $1; 2561 my($routemap) = $_; 2562 while (<$INPUT>) { 2563 tr/\015//d; 2564 last if (/^$prompt/ || ! /^(route-map |[ !])/); 2565 if (/^route-map (\S+)/) { 2566 ProcessHistory("ROUTEMAP","keysort","$key","$routemap"); 2567 $key = $1; 2568 $routemap = $_; 2569 } else { 2570 $routemap .= $_; 2571 } 2572 } 2573 ProcessHistory("ROUTEMAP","keysort","$key","$routemap"); 2574 } 2575 # filter out any RCS/CVS tags to avoid confusing local CVS storage 2576 s/\$(Revision|Id):/ $1:/; 2577 # order access-lists 2578 /^access-list\s+(\d\d?)\s+(\S+)\s+(\S+)/ && 2579 ProcessHistory("ACL $1 $2","$aclsort","$3","$_") && next; 2580 # order extended access-lists 2581 if ($aclfilterseq) { 2582 /^access-list\s+(\d\d\d)\s+(\S+)\s+(\S+)\s+host\s+(\S+)/ && 2583 ProcessHistory("EACL $1 $2","$aclsort","$4","$_") && next; 2584 /^access-list\s+(\d\d\d)\s+(\S+)\s+(\S+)\s+(\d\S+)/ && 2585 ProcessHistory("EACL $1 $2","$aclsort","$4","$_") && next; 2586 /^access-list\s+(\d\d\d)\s+(\S+)\s+(\S+)\s+any/ && 2587 ProcessHistory("EACL $1 $2","$aclsort","0.0.0.0","$_") && next; 2588 } 2589 if ($aclfilterseq) { 2590 /^ip(v6)? prefix-list\s+(\S+)\s+seq\s+(\d+)\s+(permit|deny)\s+(\S+)(.*)/ 2591 && ProcessHistory("PACL $2 $4","$aclsort","$5", 2592 "ip$1 prefix-list $2 $4 $5$6\n") 2593 && next; 2594 } 2595 # sort ipv{4,6} access-lists 2596 if ($aclfilterseq && /^ipv(4|6) access-list (\S+)\s*$/) { 2597 my($nlri, $key) = ($1, $2); 2598 my($seq, $cmd); 2599 ProcessHistory("ACL $nlri $key","","","$_"); 2600 while (<$INPUT>) { 2601 tr/\015//d; 2602 last if (/^$prompt/ || /^\S/); 2603 # ipv4 access-list name 2604 # remark NTP 2605 # deny ipv4 host 224.0.1.1 any 2606 # deny ipv4 239.0.0.0 0.255.255.255 any 2607 # permit udp any eq 123 any 2608 # permit ipv4 nnn.nnn.nnn.nnn/nn any 2609 # permit nnn.nnn.nnn.nnn/nn 2610 # ipv6 access-list name 2611 # permit ipv6 host 2001:nnnn::nnnn any 2612 # permit ipv6 2001:nnn::/nnn any 2613 # permit 2001:nnnn::/64 any 2614 # permit udp any eq 123 any 2615 # 2616 # line might begin with " sequence nnn permit ..." 2617 s/^\s+(sequence (\d+)) / /; 2618 my($seq) = $1; 2619 my($cmd, $resid) = ($_ =~ /^\s+(\w+) (.+)/); 2620 if ($cmd =~ /(permit|deny)/) { 2621 my($ip); 2622 my(@w) = ($resid =~ /(\S+) (\S+) (\S+\s)?(.+)/); 2623 for (my($i) = 0; $i < $#w; $i++) { 2624 if ($w[$i] eq "any") { 2625 if ($nlri eq "ipv4") { 2626 $ip = "255.255.255.255/32"; 2627 } else { 2628 $ip = "ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff/128"; 2629 } 2630 last; 2631 } elsif ($w[$i] =~ /^[:0-9]/ || 2632 $2[$i] =~ /^[a-fA-F]{1,4}:/) { 2633 $ip = $w[$i]; 2634 $ip =~ s/\s+$//; # trim trailing WS 2635 last; 2636 } 2637 } 2638 ProcessHistory("ACL $nlri $key $cmd", "$aclsort", "$ip", 2639 " $cmd $resid\n"); 2640 } else { 2641 ProcessHistory("ACL $nlri $key $cmd", "", "", 2642 " $cmd $resid\n"); 2643 } 2644 } 2645 } 2646 # order arp lists 2647 /^arp\s+(\d+\.\d+\.\d+\.\d+)\s+/ && 2648 ProcessHistory("ARP","$aclsort","$1","$_") && next; 2649 # order logging statements 2650 /^logging (\d+\.\d+\.\d+\.\d+)/ && 2651 ProcessHistory("LOGGING","ipsort","$1","$_") && next; 2652 # order/prune snmp-server host statements 2653 # we only prune lines of the form 2654 # snmp-server host a.b.c.d <community> 2655 if (/^snmp-server host (\d+\.\d+\.\d+\.\d+) /) { 2656 if ($filter_commstr) { 2657 my($ip) = $1; 2658 my($line) = "snmp-server host $ip"; 2659 my(@tokens) = split(' ', $'); 2660 my($token); 2661 while ($token = shift(@tokens)) { 2662 if ($token eq 'version') { 2663 $line .= " " . join(' ', ($token, shift(@tokens))); 2664 if ($token eq '3') { 2665 $line .= " " . join(' ', ($token, shift(@tokens))); 2666 } 2667 } elsif ($token eq 'vrf') { 2668 $line .= " " . join(' ', ($token, shift(@tokens))); 2669 } elsif ($token =~ /^(informs?|traps?|(no)?auth)$/) { 2670 $line .= " " . $token; 2671 } else { 2672 $line = "!$line " . join(' ', ("<removed>", 2673 join(' ',@tokens))); 2674 last; 2675 } 2676 } 2677 ProcessHistory("SNMPSERVERHOST","ipsort","$ip","$line\n"); 2678 } else { 2679 ProcessHistory("SNMPSERVERHOST","ipsort","$1","$_"); 2680 } 2681 next; 2682 } 2683 # For ASA version 8.x and higher, the format changed a little. It is 2684 # 'snmp-server host {interface {hostname | ip_address}} [trap | poll] 2685 # [community 0 | 8 community-string] [version {1 | 2c | 3 username}] 2686 # [udp-port port] ' 2687 if (/^(snmp-server .*community) ([08] )?(\S+)/) { 2688 if ($filter_commstr) { 2689 ProcessHistory("SNMPSERVERCOMM","keysort","$_", 2690 "!$1 <removed>$'") && next; 2691 } else { 2692 ProcessHistory("SNMPSERVERCOMM","keysort","$_","$_") && next; 2693 } 2694 } 2695 # prune tacacs/radius server keys 2696 if (/^((tacacs|radius)-server\s(\w*[-\s(\s\S+])*\s?key) (\d )?\S+/ 2697 && $filter_pwds >= 1) { 2698 ProcessHistory("","","","!$1 <removed>$'"); next; 2699 } 2700 # order clns host statements 2701 /^clns host \S+ (\S+)/ && 2702 ProcessHistory("CLNS","keysort","$1","$_") && next; 2703 # order alias statements 2704 /^alias / && ProcessHistory("ALIAS","keysort","$_","$_") && next; 2705 # delete ntp auth password - this md5 is a reversable too 2706 if (/^(ntp authentication-key \d+ md5) / && $filter_pwds >= 1) { 2707 ProcessHistory("","","","!$1 <removed>\n"); next; 2708 } 2709 # order ntp peers/servers 2710 if (/^ntp (server|peer) (\d+)\.(\d+)\.(\d+)\.(\d+)/) { 2711 my($sortkey) = sprintf("$1 %03d%03d%03d%03d",$2,$3,$4,$5); 2712 ProcessHistory("NTP","keysort",$sortkey,"$_"); 2713 next; 2714 } 2715 # order ip host statements 2716 /^ip host (\S+) / && 2717 ProcessHistory("IPHOST","keysort","$1","$_") && next; 2718 # order ip nat source static statements 2719 /^ip nat (\S+) source static (\S+)/ && 2720 ProcessHistory("IP NAT $1","ipsort","$2","$_") && next; 2721 # order atm map-list statements 2722 /^\s+ip\s+(\d+\.\d+\.\d+\.\d+)\s+atm-vc/ && 2723 ProcessHistory("ATM map-list","ipsort","$1","$_") && next; 2724 # order ip rcmd lines 2725 /^ip rcmd/ && ProcessHistory("RCMD","keysort","$_","$_") && next; 2726 2727 # system controller 2728 /^syscon address (\S*) (\S*)/ && 2729 ProcessHistory("","","","!syscon address $1 <removed>\n") && 2730 next; 2731 if (/^syscon password (\S*)/ && $filter_pwds >= 1) { 2732 ProcessHistory("","","","!syscon password <removed>\n"); 2733 next; 2734 } 2735 2736 /^ *Cryptochecksum:/ && next; 2737 2738 # catch anything that wasnt matched above. 2739 ProcessHistory("","","","$_"); 2740 # end of config. the ": " game is for the PIX 2741 if (/^(: +)?end$/) { 2742 $found_end = 1; 2743 return(0); 2744 } 2745 } 2746 # The ContentEngine lacks a definitive "end of config" marker. If we 2747 # know that it is a CE, SAN, or NXOS and we have seen at least 5 lines 2748 # of write term output, we can be reasonably sure that we have the config. 2749 if (($type eq "CE" || $type eq "SAN" || $type eq "NXOS") && $linecnt > 5) { 2750 $found_end = 1; 2751 return(0); 2752 } 2753 2754 return(0); 2755} 2756 27571; 2758