Access Control List
Access Control List (ACL) is a list of rules that control access to an object. ACLs are used in various applications, often in active network devices, but also in operating systems for controlling access to objects (files). When someone requests access to an object, the ACL assigned to that object is first checked to see if the operation is allowed (or allowed for whom).
Cisco ACL
On Cisco active devices, ACLs are a feature of IOS. We can use them in several places, but the most common use is for controlling (limiting) network traffic, i.e., for packet filtering. There are many different types of ACLs, certain types of ACLs can be applied to various places, and there are also certain relationships. So we have, for example, IP Extended Named ACL. I've attempted to create a slightly less traditional, but for me more practical, list of ACL types.
- IP ACL – filters IPv4 traffic – IP, TCP, UDP, IGMP (multicast), ICMP
- Port ACL – for physical L2 interface (applied to port), inbound direction only
- Numbered Standard – numbered, source address only
- Numbered Extended – numbered, source and destination address and optionally port
- Named Standard – named standard
- Named Extended – named extended
- Router ACL – for L3 interface - SVI (switch virtual interfaces – L3 interface for VLAN), physical L3 interface (port – created using no switchport), L3 EtherChannel (combination of multiple ports); controls routed traffic, outbound or inbound direction
- Standard
- Extended
- Named
- VLAN map – checks all packets (routed and bridged = switched), we can control traffic between devices within one VLAN. Direction (outbound, inbound) is not considered, applied to VLAN.
- Standard
- Extended
- Named
- Port ACL – for physical L2 interface (applied to port), inbound direction only
- MAC ACL (Ethernet ACL) – non-IP traffic
- Port ACL
- Standard
- Extended
- Named Extended
- VLAN map
- Named Extended
- Port ACL
The main division is thus according to the type of addresses we use in the rules. The most common are IP and MAC ACLs, but also today (so far less used) IPv6 ACLs, which can be Port or Router and only Named. Prefixes are used in the configuration instead of Wildcard masks. Or the almost unused IPX ACLs.
Further division is according to where we apply the given ACL. We can apply it to L2 interface, L3 interface, or the special VLAN map. Then we have the actual ACL types, either standard, extended, or named.
In this article, I focus on ACLs in general, then more on IP ACLs, and finally on MAC ACLs. Regarding application, it's general, but more focused on Port ACLs. Router ACLs (more practically) are covered in another article Cisco IOS 18 - inter-VLAN routing and ACL - routing between VLANs. A specific case is VLAN maps, which will be covered in another article.
ACLs serve mainly to
- provide basic network security to block or allow (routed) traffic
- control bandwidth
- Policy Based Routing
- enforce network policies
- identify or classify traffic (for QoS, NAT, etc.)
Brief characteristics and properties
- ACL is a sequential (ordered) list of permit and deny rules, these rules are called ACEs (Access Control Entries).
- ACL can be identified by a number or a name (named ACLs).
- New rules are always added to the end of the list.
- The first-fit rule is used. The list is traversed from beginning to end, and if there's a match, it doesn't continue further.
- Every non-empty list has a default rule at the end that denies everything (deny any). An empty list allows everything.
- It's good to place more specific rules at the beginning and general ones (subnets, etc.) at the end.
- If deny is evaluated in the ACL, an ICMP host unreachable is sent.
- Filtering (using ACLs) slows down the device (costs computational power).
- Outbound rules (outbound filters) do not affect traffic that originates locally from the router (they only filter passing traffic).
If we want to modify an existing ACL, we must (in most cases) delete it and create it again. It's recommended to write the ACL in a text editor first and then copy it to CLI. Alternatively, Cisco Network Assistant has a tool for editing ACLs.
Note: Named ACLs are an exception, where certain modifications are possible.
- on an interface, we can combine IP ACL and MAC ACL to filter all traffic
- we can also use Port ACL, Router ACL, and VLAN map together, but Port ACL has the highest priority, then Router ACL, and finally VLAN map
Wildcard subnet mask
For ACLs, Cisco decided not to use traditional subnet masks, but so-called wildcard masks. It's a small complication, but it's not complex. It's just important not to forget this feature during configuration, as it could lead to a number of problems. This mask is also referred to as an inverse mask, which describes it better. It's actually the opposite mask to the traditional mask.
Calculating the inverse mask is simple, we take all four octets of the mask in turn and calculate 255 - octet. So for example, the mask 255.255.255.0 has an inverse version of 0.0.0.255 or 255.255.192.0 is 0.0.63.255.
Types of ACLs
The most common division of ACLs is into two types
- standard ACL - older and simpler version of ACL with fewer configuration options
- extended ACL - newer and more complex ACL with more options
There are also various special ACLs that are often derived from these two, such as dynamic ACL, context-based ACL, reflexive ACL, or named ACL.
Standard ACL
- uses numbers 1 - 99 and 1300 - 1999 in extended mode
- is simple to configure
- filters (looks) only by source address and is used as outbound
- is used to block traffic close to the destination
SWITCH(config)#access-list number {deny|permit} {host|source source-wildcard|any} [log]
Note: Configuration of standard and extended ACLs is done the same way, distinguished by the number used.
In place of deny|permit, we can also use the keyword remark and insert a description (comment) of the given rule.
The optional log attribute causes information about packets that meet the given criteria (given rule) to be sent to the console and log. It's useful for debugging, but for live traffic, it's too taxing on the device.
Example:
The following ACL with number 5 allows access to subnet 10.5.1.0/24 except for address 10.5.1.10, all other addresses are denied.
SWITCH(config)#access-list 5 deny host 10.5.1.10
SWITCH(config)#access-list 5 permit 10.5.1.10 0.0.0.255
SWITCH(config)#access-list 5 deny any
Note: The last rule is default and is not entered.
Extended ACL
- uses numbers 100 - 199 and 2000 - 2699 in extended mode
- looks at both source and destination IP addresses
- checks several items in the layer 3 and 4 headers (protocol, port, etc.)
- can block traffic anywhere (best close to the source)
Note: Other numeric ranges are used for other types of ACLs, such as IPX, AppleTalk, XNS, etc.
Extended ACL can check these parameters
- In Layer 3 of ISO/OSI, i.e., in the IP header, it checks: IP addresses, protocol, data from ToS (Type of Service - 802.1q priority and service).
- In Layer 4, it checks in the TCP header: ports and protocols, in the UDP header: ports, in the ICMP header message type.
Note: When using data from Layer 4 (i.e., ports), it's necessary to consider fragmented traffic, because during fragmentation, only the first packet contains data from Layer 4. We can use the keyword fragments in the rule.
SWITCH(config)#access-list number {deny|permit} protocol {host|source source-wildcard|any} [port] {host| destination destination-wildcard|any} [port]
The above notation of extended ACL is only simplified, it's possible to use a number of other parameters here and create, for example, a dynamic ACL or limit the validity of ACL by time.
As a protocol, you can use IP, TCP, ICMP, UDP, or many others. Depending on the chosen protocol, the parameters we can use in the ACL also change, for example, port can only be used with TCP and UDP.
Note: If we want to filter all protocols, we use IP, others fall under it.
Port restriction is specified using an operator, we can use operators eq (equals), neq (not equal), gt (greater than), lt (less than) and range (range). The operator with the port is entered after the source address or after the destination address, and the port is then applied to the source or destination.
It's important to carefully consider where to place the port check (whether at the source or destination), depending on whether we apply the ACL as inbound or outbound (described later). The following example shows two possibilities.
SWITCH(config)#access-list 105 permit tcp 10.1.0.0 0.0.0.255 any eq www SWITCH(config)#access-list 105 permit tcp 10.1.0.0 0.0.0.255 eq www any
Example:
ACL number 105 allows access to server 10.5.1.10 from anywhere, but only to port 80 (i.e., http) and ping.
SWITCH(config)#access-list 105 permit tcp any host 10.5.1.10 eq 80
SWITCH(config)#access-list 105 permit icmp any any echo
SWITCH(config)#access-list 105 permit icmp any any echo-reply
SWITCH(config)#access-list 105 deny ip any any
Note: The last rule is default and is not entered.
Named ACL
- we can use it for both standard and extended ACL
- allows editing or deleting individual rules in the ACL
- names are easier to remember
- we can use an "unlimited" number of named ACLs
- we can use a number as a name, but it must belong to the correct range
Note: Although named ACLs have certain advantages, Cisco recommends using regular ACLs in some materials. Named ACLs can't be used everywhere, but I haven't had any problems with them in practice.
Named ACLs are created differently. First, we create the ACL and simultaneously switch to the ACL configuration mode.
SWITCH(config)#ip access-list {standard|extended} name
Then we enter individual rules according to the ACL type and with the same options as for numbered ACLs. The line number (at the beginning of the command) is optional.
SWITCH(config-ext-nacl)#[line number] permit|deny ...
If we display the ACL, we'll see that individual lines are numbered. Using these numbers, we can delete rules and insert new rules at a specific place.
Note: Automatic line numbers are created in tens (first rule 10, then 20, 30 ...) and lines are numbered even for unnamed ACLs. If we enter our own numbers, they are used and we see them when displaying the ACL. However, if we look at the running-config, these numbers are not there and after restarting the switch, they are automatically renumbered.
Example:
SWITCH(config)#ip access-list extended name SWITCH(config-ext-nacl)#deny ip 192.168.190.100 0.0.0.1 host 192.168.190.200 SWITCH(config-ext-nacl)#permit ip any any
Small tips
- keyword host - instead of 10.0.5.2 0.0.0.0 we can use host 10.0.5.2
- keyword any - instead of 0.0.0.0 255.255.255.255 we use any
- You can't edit or change the order in regular ACLs, rules are added to the end. If we want to change something, we have to delete the entire ACL and create it again.
- When removing an ACL, it may happen that if it's still applied to an interface, it's replaced by a default denial of everything. However, correctly, everything should pass if the ACL doesn't exist.
ACL Configuration
ACL configuration is done in two steps
- creating the ACL - first we create rules according to the ACL type, see previous paragraphs
- applying the ACL to an interface - then we must assign this ACL to some object, in this case an interface, which is always done the same way
Applying ACL
By applying an ACL to an interface, we control packet access to this interface. ACL (in the range described in this article) can be applied to some interface, which can be a port, serial line, VLAN, etc.
We can apply only one ACL per interface, direction, and protocol. Protocol means IP, IPX, Apple Talk, etc. So for example, for one port in a TCP/IP network, we can apply a maximum of two ACLs (one inbound and one outbound).
When placing ACLs, it's necessary to think carefully to make the placement effective. If possible, it's good to choose as close to the source as possible to avoid burdening the network. However, we can only place ACLs on devices we control, so often it's necessary to set ACLs close to the destination.
Applying an ACL is simple. We switch to the given interface and use the ip access-group command to set the ACL of a certain number or name, along with specifying the direction.
SWITCH(config-if)#ip access-group {number|name of ACL} {in|out}
Note: In response to a reader's question, I read that the out direction is not supported on L2 interfaces (i.e., ports), but only on L3 (typically VLAN and routed port). And this applies only to L3 (C3750) and higher switches, L2 switch (C2960) has only in ACL. So we use the out direction only on routers and L3 switches. If we're dealing with port ACL and switch, we must convert the given port to routed, using no switchport and setting an IP address.
Example:
SWITCH(config)#interface serial0 SWITCH(config-if)#ip access-group 5 in
Determining direction
Determining the direction in which the ACL should act is not complicated. It's necessary to look at the switch where we apply it and decide whether we want to restrict packets that leave it (out) or right at the input, those that arrive (in).
Standard ACL is placed close to the destination and should therefore always be outgoing - out. In the following image, we restrict traffic that comes to the server.

Extended ACL we usually try to place as close to the source as possible, and in that case, the filter is inbound - in.

Checking ACL
A few show commands for checking ACL.
SWITCH#show ip interface // displays interface info and it's visible here if an ACL is applied SWITCH#show access-lists // list of ACLs (IP and MAC) with rules SWITCH#show ip access-lists // list of IP ACLs SWITCH#show running-config // ACLs and their applications are also visible in the running configuration
Another method for debugging ACLs is using logging. We can add the keyword log at the end of each rule, and then all packets that meet this rule are logged.
For example, if we want to see communication that isn't captured by any rule in the ACL and is therefore forbidden, we can add a rule at the end
SWITCH(config)#access-list 5 deny any log
ACL for VTY
Besides physical interfaces (such as ports), we also have virtual ones, e.g., Virtual Terminal (VTY, which we can access via telnet or ssh). We should apply only one ACL to VTY, even though multiple connections are created for multiple users (because we can't distinguish them - we don't know which one the user will connect through).
ACLs for VTY are created the same way, but application is done using the access-class command.
SWITCH(config)#line vty 0 4 SWITCH(config-line)#access-class 2 in
Named Extended MAC ACL
Just like IP ACLs, we can create MAC ACLs, which filter communication using MAC addresses and are used on second layer interfaces (according to the OSI model). Configuration and use are similar.
Note: We can use either numbered standard MAC ACLs (numbers 700 - 799), numbered extended MAC ACLs (numbers 1100 - 1199) or named extended MAC ACLs. However, on many switches, only named extended MAC ACLs are available.
SWITCH(config)#mac access-list extended name
This switches us to the extended MAC access-list configuration mode, where we define individual rules.
SWITCH(config-ext-macl)#[line number] {deny|permit} {host source MAC|source MAC mask|any} {host destination MAC|destination MAC mask|any}
Note: The above rule can also contain a number of optional parameters that determine, for example, EtherType or COS.
Example:
SWITCH(config)#mac access-list extended test
SWITCH(config-ext-macl)#permit host 0000.1111.2222 any
SWITCH(config-ext-macl)#deny any any
MAC ACL is applied to a layer 2 interface and we can apply only one MAC ACL per interface. The application can only be on input (in). For application, use the command:
SWITCH(config-if)#mac access-group ACL-name in
To display the application of MAC ACL on ports, we can use the command:
SWITCH#show mac access-group
Každý seznam má na konci defaultní pravidlo, které zakazuje vše (deny any). Toto pravidlo obsahuje i prázdný seznam.
Nemůžu souhlasit.
An interface with an empty access list applied to it permits all traffic. viz:http://www.cisco.com/en/US/products/ps6350/products_configuration_guide_chapter09186a008043105e.html
respond to [1]tomfi: :-) nikdo není dokonalý. Děkuji za opravu, vypadá to, že jsem to měl zafixované špatně.
Teorie je teorie. V každém případě musím kladně hodnotit všechny články Samuraje :-).
Dobry den,
diky za clanek, ale opravte si prosim preklep v adrese masky site:
255.255.196.0 neni maska site! Nejspis jste myslel 255.255.192.0 a ta ma pak inverzni masku 0.0.63.255.
Jinak ale diky za clanky, jsou velmi prinosne.
respond to [4]Anonym: Díky, opraveno.
Jen takovy maly dotaz: Jestli jsem to pochopil spravne, tak IP ACL umi jen L3 switche nebo routery, ale ne L2 switche? MAC ACL umi jak L3 tak i L2 switche?
Jinak diky za clanky, jsou velmi pekne a pochopitelne, jen houst.
respond to [6]Paja: Ne ne. I L2 switch se umí podívat do vyšších vrstev než L2, takže se na něm dají použít IP ACL, která se označují jako Port ACL. Nepodporuje ale Router ACL, která se aplikují při routovacím procesu.
Zdravím, můj dotaz zní, zda mohu kontolovat OUT komunikaci pro případ "skrytého" odesílání dat např. trojanem?
Ve vašem popisu je uvedena věta:
SWITCH(config-if)#ip access-group {číslo|jméno ACL} {in|out}
Já používám C3560 a zde je pouze možnost omezení příchozích paketů IN:
Switch(config-if)#ip access-group test ?
in inbound packets
Dík za odpověď!
respond to [8]Libor: Tak jsem kouknul do dokumentace a už vidím v čem je problém. Směr out není podporovaný na L2 interfacech (tzn. portech). Já používám v praxi ACL pouze na VLANách, takže jsem na to nenarazil. Bohužel :-(.
Moc pěkně udělané, diky :-). Malá připomínka k wildcard - nejde o pouhou masku naruby, i kdyz se tak nejcasteji opravdu pouziva. Totiz zatimco maska muze nabyt pouze nektere z osmi hodnot (mysleno na jednom oktetu), do wildcardu lze uvest libovolnou kombinaci osmi bitu. Ovšem kdo by toho chtěl z nějakého důvodu v plné míře využít, musí být velmi pečlivý ;-).
respond to [10]Pavel: Na sutazi NAG sme mali access-list kde trebalo napriklad oznacit kazdu neparnu adresu z hornej polovice adresneho prestoru napriklad 10.0.0.0/24, nieco na takyto sposob 10.0.0.129 0.0.0.126
SWITCH(config)#access-list 5 deny host 10.5.1.10
SWITCH(config)#access-list 5 permit 10.5.1.10 0.0.0.255
Otázka, nebyla ve druhém řádku myšlena sít 10.5.1.0(místo 10)? Podle wildcard by to odpovídalo.
respond to [12]Šikus: Ano správně, je to překlep. I když teoreticky by to mohlo fungovat i takto.
Dobrý den potřeboval bych radu.
Potřebuji nastavit ACL na routeru Cisco 1812 a je někde bota.
Když zadám příkazy:
Router(config)#access-list 102 permit tcp any any
Router(config)#interface fa0
Router(config-if)#ip access-group 102 in
Tak vše funguje perfektně
a
když zadám to samé rozšířené o port 25, tak to nefunguje.
Router(config)#access-list 102 permit tcp any any eq 25
Router(config)#interface fa0
Router(config-if)#ip access-group 102 in
Myslím si, že se to hádá se zapnutou jinou funkcí, nenapadá vás něco? Díky moc
respond to [14]Lukas: Jde o to, čeho chcete dosáhnout. Tohle ACL povolí pouze komunikaci na cílový port 25 (na daném interfacu).
Zdravim, nejak tu nemuzu najit variantu ktere moc nerozumim :)
# acess-list 102 permit tcp deny 10.0.2.0 0.0.0.255 established
¨jde mi prave o ten pridomek k prikazu a to o "established", potiz s nim je ta, ne nevim jde li o povoleni vsech prave probihajicich komunikaci na siti (je jedno jestli in nebo out) a nebo jde li o to, ze po aplikaci nepovoli navazani noveho spojeni. Abych to upresnil, pokud ulozim toto do startup-config nedojdek odriznuti routeru krom vyse povolenych pravidel (permit) stejne jako aplikaci tcp deny all ?
Jinak diky za ty clanky ;) , jsou velice uzitecne.
omlouvam se za ten spatne opsany prikaz :)
jisteze jde o permit ne deny (a uz vubec ne oboji :D )
#acess-list 102 permit tcp 10.0.2.0 0.0.0.255 established
respond to [17]N3utrin: že se pletu ke staré komunikaci: established jsou (jestli dobře chápu) navázaná spojení - tedy povolí odpovídat, pokud je někým vyzván (nebo nově po zápisu pravidla bude vyzván), ale nepovolí navázat vlastní spojení.