Exemple #1
0
def CISC_L2_000150(existingConfiguration):
    #Description: The Cisco switch must have Dynamic Address Resolution Protocol (ARP) Inspection (DAI) enabled on all user VLANs.
    test = "CISC_L2_000130"
    print_title(test)
    vlansList = defaultdict(list)
    commandToTest = ['ip arp inspection']
    shouldExist = True
    exactMatch = False

    lineByLineComparison(existingConfiguration, commandToTest, shouldExist, test, exactMatch)

    for key, values in existingConfiguration.items():
        for v in values:
            for x in v:
                currentLine = x
                if currentLine.startswith("ip arp inspection"):
                    arpInspection = True
                    tempString = currentLine.replace('ip arp inspection vlan ', '')
                    arpInspectionVlans = tempString.split(',')
                    vlansList = vlanParser(arpInspectionVlans)
                #collect current interface
                if currentLine.startswith("interface"):
                    interface = currentLine
                if currentLine.startswith(" switchport access vlan "):
                    filterString = currentLine.replace(' switchport access vlan ', '')
                    splitString = filterString.split(',')
                    vlansOnAccessInterface = vlanParser(splitString)
                    if (set(vlansOnAccessInterface).issubset(set(vlansList)) == False):
                        testResult = interface + " is an access interface with VLANs that are not being inspected by Dynamic ARP Inspection. Please remediate."
                        resultDictionary[key][test].append(testResult)
Exemple #2
0
def CISC_L2_000180(existingConfiguration):
    #Description: The Cisco switch must implement Rapid STP where VLANs span multiple switches with redundant links.
    test = "CISC_L2_000180"
    print_title(test)
    commandToTest = ['spanning-tree mode rapid-pvst']
    shouldExist = True
    lineByLineComparison(existingConfiguration, commandToTest, shouldExist, test)
Exemple #3
0
def CISC_L2_000160(existingConfiguration):
    test = "CISC_L2_000160"
    print_title(test)
    commandToTest = 'storm-control unicast'
    checkInterface(existingConfiguration, commandToTest, test)
    commandToTest = 'storm-control broadcast'
    checkInterface(existingConfiguration, commandToTest, test)
Exemple #4
0
def CISC_L2_000110(existingConfiguration):
    #Description: The Cisco switch must have STP Loop Guard enabled.
    loopGuard = ['spanning-tree loopguard default']
    shouldExist = True
    test = "CISC_L2_000110"
    print_title(test)
    lineByLineComparison(existingConfiguration, loopGuard, shouldExist, test)
Exemple #5
0
def CISC_L2_000130(existingConfiguration):
    #Description: The Cisco switch must have DHCP snooping for all user VLANs to validate DHCP messages from untrusted sources
    test = "CISC_L2_000130"
    print_title(test)
    vlansList = defaultdict(list)
    commandToTest = ['ip dhcp snooping']
    shouldExist = True
    exactMatch = False

    lineByLineComparison(existingConfiguration, commandToTest, shouldExist, test, exactMatch)

    for key, values in existingConfiguration.items():
        for v in values:
            for x in v:
                currentLine = x
                if currentLine.startswith("ip dhcp snooping"):
                    dhcpSnooping = True
                    tempString = currentLine.replace('ip dhcp snooping vlan ', '')
                    dhcpSnoopingVlans = tempString.split(',')
                    vlansList = vlanParser(dhcpSnoopingVlans)
                #collect current interface
                if currentLine.startswith("interface"):
                    interface = currentLine
                if currentLine.startswith(" switchport access vlan "):
                    filterString = currentLine.replace(' switchport access vlan ', '')
                    splitString = filterString.split(',')
                    vlansOnAccessInterface = vlanParser(splitString)
                    if (set(vlansOnAccessInterface).issubset(set(vlansList)) == False):
                        testResult = interface + " is an access interface with VLANs that are not being snooped. Please remediate."
                        resultDictionary[key][test].append(testResult)
Exemple #6
0
def CISC_L2_000040(existingConfiguration):
    #Description: The Cisco switch must have STP Loop Guard enabled.
    qos = ['mls qos']
    shouldExist = True
    test = "CISC_L2_000040"
    print_title(test)
    lineByLineComparison(existingConfiguration, qos, shouldExist, test)
Exemple #7
0
def main():
    # passphrase = getpass.getpass('Please enter CA key Passphrase')
    passphrase = 'fred'
    if os.path.isfile('./ssl/ca_key.pem') is False and os.path.isfile(
            './ssl/ca_cert.pem') is False:
        ca_key = cry.create_key()
        cry.save_key(ca_key, './ssl/ca_key.pem', passphrase)
        ca_csr = cry.create_csr(ca_key,
                                country_name='GB',
                                locality='London',
                                organisation='Tactical Networks',
                                common_name='CA.tactical-net.co.uk',
                                is_ca=True)
        ca_cert = cry.create_cert(ca_key,
                                  csr=ca_csr,
                                  lifetime=3650,
                                  is_ca=True)
        cry.save_cert(ca_cert, './ssl/ca_cert.pem')
    else:
        ca_key = cry.load_key('./ssl/ca_key.pem', passphrase)
        ca_cert = cry.load_cert('./ssl/ca_cert.pem')

    print_title("Playbook to configure the network")
    nr = InitNornir(config_file='config.yaml', dry_run=False)
    # result = nr.run(task=disable_api, name='Disable API Task')
    # print_result(result, severity_level=logging.INFO)
    # nr = nr.filter(platform='nxos')
    result = nr.run(task=task_wrangler,
                    name='Main Task Wrangler',
                    ca_key=ca_key,
                    ca_cert=ca_cert)
    print_result(result, severity_level=logging.INFO)
Exemple #8
0
def CISC_L2_000020(existingConfiguration):
    #Description: Verify if the switch configuration has 802.1x authentication implemented for all access switch ports connecting to LAN outlets (i.e., RJ-45 wall plates) or devices not located in the telecom room, wiring closets, or equipment rooms. MAC Authentication Bypass (MAB) must be configured on those switch ports connected to devices that do not support an 802.1x supplicant.
    test = "CISC_L2_000020"
    print_title(test)
    hasBoth = 0 #this will keep a count per interface to see if both critieria are met
    for key, values in existingConfiguration.items():
        for v in values:
            for current_line in v:
                interface = current_line
                hasBoth = 0 #reset counter for hasBoth
                if interface.startswith("interface"):
                    #find the index position within the configuration to check for dot1x configuration
                    index_element = v.index(interface)
                    while v[index_element] != '!':
                        #for the comparison we are using a leading because the config contains a space for indentation
                        if v[index_element] == ' authentication port-control auto' or v[index_element] == ' dot1x pae authenticator':
                            hasBoth += 1 #increment if a match is found
                        if hasBoth == 2:
                            break
                        index_element += 1 #check the next line until reaching the end of interface configuration
                    if hasBoth < 2:
                        testResult = str(interface) + " is missing do1x configuration. Please remediate"
                        resultDictionary[key][test].append(testResult)

    #Verify 802.1x configuration on the switch
    checkContent = [
    'aaa new-model',
    'aaa group server radius',
    'server name',
    'aaa authentication do1x default group',
    'dot1x system-auth-control'
    ]

    shouldExist = True
    lineByLineComparison(existingConfiguration, checkContent, shouldExist, test)
Exemple #9
0
def CISC_L2_000220(existingConfiguration):
    #Description: The Cisco switch must not have the default VLAN assigned to any host-facing switch ports.
    test = "CISC_L2_000220"
    print_title(test)
    output = access_switches.run(task=networking.napalm_cli, commands=['show vlan brief'])

    configDictionary = defaultdict(list)

    #build a datastructure with host: result pairings
    for h, l in zip(hostKeys, listOfKeys):
        filtered_output = output[l].result
        someString = filtered_output['show vlan brief']
        stringList = someString.split('\n')
        for x in stringList:
            if '1    default' in x:
                line = x
                tempString = " ".join(line.split())
                stringList = tempString.split(' ')
                #if the last element in the stringList array is a description rather than
                #an interface we know that no interfaces are assigned here
                if stringList[-1] == 'active' or stringList[-1] == 'inactive':
                    continue
                else:
                    testResult = stringList[-1] + " on host " +  h + " has access interfaces in the default VLAN. Please remediate."
                    resultDictionary[h][test].append(testResult)
Exemple #10
0
def CISC_L2_000230(existingConfiguration):
    #Description: The Cisco switch must have the default VLAN pruned from all trunk ports that do not require it.
    test = "CISC_L2_000230"
    print_title(test)
    output = access_switches.run(task=networking.napalm_cli, commands=['show int trunk'])

    configDictionary = defaultdict(list)

    #build a datastructure with host: result pairings
    for h, l in zip(hostKeys, listOfKeys):
        filtered_output = output[l].result
        someString = filtered_output['show int trunk']
        stringList = someString.split('\n')
        for x in stringList:
            line = x
            if 'Vlans allowed on trunk' in line:
                index_element = stringList.index(line)
                index_element +=1 #iterate to the next line of the output which will contain ports and their allowed vlans on trunk
                while stringList[index_element].startswith('Port') == False:
                    currentLine = stringList[index_element]
                    interface = currentLine.split(' ') #grab the interface name
                    if('1,') in currentLine or ('1-') in currentLine: #check the current line for VLAN1 in the interface trunking
                        testResult = "VLAN1 is not being pruned from " + interface[0] + " on host " + h + ". Please remediate."
                        resultDictionary[h][test].append(testResult)
                    index_element +=1
Exemple #11
0
def CISC_L2_000170(existingConfiguration):
    #Description: The Cisco switch must have IGMP or MLD Snooping configured on all VLANs.
    test = "CISC_L2_000170"
    print_title(test)
    commandToTest = ['no ip igmp snooping']
    shouldExist = False
    exactMatch = False
    lineByLineComparison(existingConfiguration, commandToTest, shouldExist, test, exactMatch)
Exemple #12
0
 def main() -> None:
     clean_up = "rm -r ospfdiff ospf-current"
     os.system(clean_up)
     os.system(clear_command)
     nr = InitNornir(config_file="config.yaml")
     output = nr.run(task=clean_ospf)
     print_title("REVERSING OSPF CONFIGURATION BACK INTO DESIRED STATE")
     print_result(output)
Exemple #13
0
def CISC_L2_000270(existingConfiguration):
    #Description: The Cisco switch must not have any switchports assigned to the native VLAN.
    test = "CISC_L2_000270"
    print_title(test)
    checkContent = ['native vlan']
    shouldExist = False
    exactMatch = False
    lineByLineComparison(existingConfiguration, checkContent, shouldExist, test, exactMatch)
Exemple #14
0
 def save_config(self, task):
     config, site = self.render_config(task)
     print_title(f"Saving configuration to: output/{site}.conf.")
     try:
         with open(f'output/{site}.conf', "a") as file:
             file.write(config)
             file.close()
         print("[+] Done")
     except Exception as e:
         print(f"[-] An Error occured: {e}")
Exemple #15
0
def process_tasks(task):
    if task.failed:
        print_result(task)
        print("Exiting script before we break anything else!")
        sys.exit(1)
    else:
        print_title('Processing results')
        for host in dc1.inventory.hosts:
            host_lldp = cumulus_lldp(dc1.inventory.hosts[host]['lldp'], host)
        print(f"Task {task.name} completed successfully!")
Exemple #16
0
 def main() -> None:
     clear_command = "clear"
     clean_up = "rm -r vlandiff vlan-current"
     os.system(clean_up)
     os.system(clear_command)
     nr = InitNornir(config_file="config.yaml")
     targets = nr.filter(device="switch")
     result = targets.run(task=deploy_vlan)
     output = targets.run(task=show_vlan)
     print_title("REVERSING VLAN CONFIGURATION BACK INTO DESIRED STATE")
     print_result(output)
Exemple #17
0
 def render_config(self, task):
     site = task.host["site"]
     config_data = self.open_config(task)
     templateLoader = jinja2.FileSystemLoader(searchpath="templates/")
     templateEnv = jinja2.Environment(loader=templateLoader)
     t = self.template
     template = templateEnv.get_template(t)
     print_title(f"Rendering configuration: {self.template} on {site}.")
     config = template.render(config_data)
     print(config)
     return config, site
Exemple #18
0
 def deploy_config(self, task):
     config, site = self.render_config(task)
     print_title(f"Configuring {self.template} on {site}.")
     try:
         task.run(task=networking.napalm_configure,
                  name="Loading Configuration on the device",
                  replace=False,
                  configuration=config)
         print("[+] Done")
     except Exception as e:
         print(f"[-] An Error occured: {e}")
Exemple #19
0
def CISC_L2_000190(existingConfiguration):
    #Description: The Cisco switch must enable Unidirectional Link Detection (UDLD) to protect against one-way connections.
    test = "CISC_L2_000190"
    print_title(test)
    commandToTest = ['udld enable']
    shouldExist = True
    lineByLineComparison(existingConfiguration, commandToTest, shouldExist, test)

    #This will check on a per interface basis. We should consider modifying line by line to a boolean return...
    commandToTest = 'udld port'
    checkInterface(existingConfiguration, commandToTest, test)
Exemple #20
0
def CISC_L2_000210(existingConfiguration):
    #Description: The Cisco switch must have all disabled switch ports assigned to an unused VLAN.
    test = "CISC_L2_000210"
    print_title(test)
    output = access_switches.run(task=networking.napalm_cli, commands=['show interfaces switchport'])
    activeVlansOnHost = defaultdict(list)

    configDictionary = defaultdict(list)
    #Setting a flag to determine if TrunkAll is set. We need at least one VLAN disabled/not trunking to have an attempt at passing this rule
    trunkAll = False
    c = set()
    #build a datastructure with host: result pairings
    for l in hostKeys:
        filtered_output = output[l].result
        someString = filtered_output['show interfaces switchport']
        stringList = someString.split('\n')
        for x in stringList:
            activeVlans = []
            if 'Name: ' in x:
                currentInterface = x
            if 'Trunking VLANs Enabled: ALL' in x:
                testResult = "Interface" + currentInterface + " on host " +  l + " is trunking ALL VLANs. Please disable at least one VLAN."
                trunkAll = True
                resultDictionary[l][test].append(testResult)
                break
            if 'Trunking VLANs Enabled: ' in x and trunkAll == False:
                tempString = x.replace('Trunking VLANs Enabled: ', '')
                numbers = tempString.split(',')
                activeVlans = vlanParser(numbers)
                activeVlansOnHost[l] += activeVlans

    for key, values in existingConfiguration.items():
        for v in values:
            for current_line in v:
                interface = current_line
                if interface.startswith("interface"):
                        index_element = v.index(interface)
                        interfaceConfigurationBlock = []
                        vlansOnInterfaceConfiguration = []
                        while v[index_element] != '!':
                            currentLine = v[index_element]
                            interfaceConfigurationBlock.append(currentLine)
                            if 'switchport access vlan' in currentLine:
                                temporaryString = currentLine.replace(' switchport access vlan ', '')
                                remainingVlans = temporaryString.split(',')
                                vlansOnInterfaceConfiguration = vlanParser(remainingVlans)
                            index_element += 1

                        if ' switchport mode access' in interfaceConfigurationBlock and ' shutdown' in interfaceConfigurationBlock and (set(activeVlansOnHost[key]).intersection(set(vlansOnInterfaceConfiguration)) != c):
                            testResult = interface + " is shutdown in a VLAN that is in use. Please remediate"
                            resultDictionary[key][test].append(testResult)
Exemple #21
0
def main():
    nr = InitNornir(config_file="config.yml")
    ios = nr.inventory.groups['cisco-ios']['img']

    # Task: SCP file to device
    print_title(f'Sending {ios} via SCP')
    output = nr.run(scp_file)
    print_result(output)

    # Task: Check that file was installed
    print_title(f'Verifying {ios} was installed')
    output = nr.run(check_file_exists)
    print_result(output)

    # Task: Set boot variable to new ios img
    print_title('Setting boot variable')
    output = nr.run(set_boot_var)
    print_result(output)

    # Task: Reload devices to install new img
    print_title('Reloading devices')
    output = nr.run(reload)
    print_result(output)

    print('Reloading...')
Exemple #22
0
def CISC_L2_000240(existingConfiguration):
    #Description: The Cisco switch must not use the default VLAN for management traffic.
    test = "CISC_L2_000240"
    print_title(test)

    for key, values in existingConfiguration.items():
        for v in values:
            for current_line in v:
                interface = current_line
                if interface == 'interface Vlan1':
                    #find the index position within the configuration to check for dot1x configuration
                    index_element = v.index(interface)
                    index_element += 1
                    if 'Management' or 'MGMT' in v[index_element]:
                        testResult = "The management VLAN is using VLAN1. Please remediate."
                        resultDictionary[key][test].append(testResult)        
Exemple #23
0
def main():
    nr = InitNornir(
        config_file="nornir_config.yaml",
        core={
            'num_workers':10
        }
    )
    # register the ncclient connection plugin so that host-connections have access to it
    Connections.register("ncclient", Ncclient)

    nr2 = nr.filter(name='sr1.lab')

    results = nr.run(task=validate_intent, intent_dir="intents")
#    results = nr2.run(task=validate_intent, intent_dir="intents")

    print_title("Runbook to push intent")
    print_result(results, vars = "diff")
Exemple #24
0
def CISC_L2_000030(existingConfiguration):
    #Description: The Cisco switch must authenticate all VLAN Trunk Protocol (VTP) messages with a hash function using the most secured cryptographic algorithm available.
    test = "CISC_L2_000030"
    print_title(test)
    output = access_switches.run(task=networking.napalm_cli, commands=['show vtp password'])

    configDictionary = defaultdict(list)
    #build a datastructure with host: result pairings
    for h, l in zip(hostKeys, listOfKeys):
        filtered_output = output[l].result
        someString = filtered_output['show vtp password']
        if 'not configured' in someString:
            testResult = "Host " +  h + " does not have a VTP password. Please set one."
            resultDictionary[h][test].append(testResult)
        configDictionary[h].append(someString)
        filtered_output = None
        someString = None
Exemple #25
0
def CISC_L2_000200(existingConfiguration):
    #Description: The Cisco switch must have all trunk links enabled statically.
    test = "CISC_L2_000200"
    print_title(test)
    output = access_switches.run(task=networking.napalm_cli, commands=['show interfaces switchport'])

    configDictionary = defaultdict(list)

    #build a datastructure with host: result pairings
    for h, l in zip(hostKeys, listOfKeys):
        filtered_output = output[l].result
        someString = filtered_output['show interfaces switchport']
        stringList = someString.split('\n')
        for x in stringList:
            if 'Name: ' in x:
                currentInterface = x
            if 'Negotiation of Trunking: On' in x:
                testResult = "Interface" + currentInterface + " on host " +  h + " is using auto negotiation of trunking. Please remediate."
                resultDictionary[h][test].append(testResult)
Exemple #26
0
def CISC_L2_000260(existingConfiguration):
    #Description: The Cisco switch must have the native VLAN assigned to an ID other than the default VLAN for all 802.1q trunk links.
    test = "CISC_L2_000260"
    print_title(test)
    output = access_switches.run(task=networking.napalm_cli, commands=['show interfaces switchport'])

    configDictionary = defaultdict(list)

    #build a datastructure with host: result pairings
    for h, l in zip(hostKeys, listOfKeys):
        filtered_output = output[l].result
        someString = filtered_output['show interfaces switchport']
        stringList = someString.split('\n')
        for x in stringList:
            if 'Name: ' in x:
                tempString = x
                currentInterface = tempString.replace("Name: ", '')
            if 'Trunking Native Mode VLAN: 1 (default)' in x:
                testResult = "Interface " + currentInterface + " on host " +  h + " is trunking the native VLAN. Please remediate."
                resultDictionary[h][test].append(testResult)
def main():

    # Create a Nornir object
    nr = InitNornir(core={"num_workers": 100},
                    inventory={
                        "plugin":
                        "nornir.plugins.inventory.simple.SimpleInventory",
                        "options": {
                            "host_file": "inventory/hosts.yaml",
                            "group_file": "inventory/groups.yaml"
                        }
                    })

    # Run Nornir task (here getting the ARP table of the devices)
    result = nr.run(task=networking.napalm_get,
                    name=" ARP table ",
                    getters=["arp_table"])

    # Display the result
    print_title("Display ARP table of the network devices")
    print_result(result)
Exemple #28
0
def main():
    nr = InitNornir(config_file="nornir_config.yaml", core={'num_workers': 10})
    # register the ncclient connection plugin so that host-connections have access to it
    Connections.register("ncclient", Ncclient)

    nr2 = nr.filter(name='sr1.lab')

    print_title("Loading Service Intents")
    results = nr.run(task=load_service_intents,
                     name="Load Service Intents",
                     directory="intent2/services/eline/vars")
    print_result(results, vars="stdout")

    print_title("Updating inventory host data (partial)")
    resources_to_load = set()
    for _, host in nr.inventory.hosts.items():
        resources_needed = host.get("rsc_to_populate", None)
        if resources_needed:
            for rsc in resources_needed:
                resources_to_load.add(rsc)
    results = nr.run(task=download_configs,
                     name="Load relevant configs into Inventory",
                     resources=resources_to_load)
    print_result(results, vars="stdout")

    print_title("Ensuring Service Intents")
    results = nr.run(task=ensure_services, intent_dir="intent2/services")
    print_result(results, vars="diff")
Exemple #29
0
def CISC_L2_000010(existingConfiguration):
    #Description: The Cisco switch must be configured to disable non-essential capabilities.
    test = "CISC_L2_000010"
    checkContent = [
    'boot network',
    'ip boot server',
    'ip bootp server',
    'ip dns server',
    'ip identd',
    'ip finger',
    'ip http server',
    'ip rcmd rcp-enable',
    'ip rcmd rsh-enable service config',
    'service finger'
    'service tcp-small-servers',
    'service udp-small-servers',
    'service pad'
    ]

    shouldExist = False
    print_title(test)
    lineByLineComparison(existingConfiguration, checkContent, shouldExist, test)
def main():

    nr = InitNornir(core={"num_workers": 100},
                    inventory={
                        "plugin":
                        "nornir.plugins.inventory.simple.SimpleInventory",
                        "options": {
                            "host_file": "inventory/hosts.yaml",
                            "group_file": "inventory/groups.yaml"
                        }
                    })

    hosts = nr.filter(type="network_device")

    result = hosts.run(task=networking.napalm_get,
                       name=" Get facts ",
                       getters=["facts", "interfaces", "environment"])

    print_title("Display info about network devices")
    print_result(result)

    print(result["device1"][0].result.get("facts").get("os_version"))