Iptables MAC Address Filtering

by on December 27, 2005 · 32 comments· LAST UPDATED December 15, 2010

in

LAN or wireless access can be filtered by using the MAC addresses of the devices transmitting within your network. A mac address is acronym for media access control address, is a unique address assigned to almost all-networking hardware such as Ethernet cards, routers, mobile phones, wireless cards and so on (see mac address at wikipedia for more information). This quick tutorial explains how to block or deny access using MAC address using iptables - Linux administration tool for IPv4 packet filtering and NAT.

Linux Iptables comes with the MAC module. This module matches packets traveling through the firewall based on their MAC (Ethernet hardware) address. It offers good protection against malicious users who spoof or change their IP address. Remember that mac filtering only makes sense for packets coming from an Ethernet device and entering the following chains:

  1. PREROUTING
  2. FORWARD
  3. INPUT

Examples: Access Restrictions Using MAC Address

Drop all connection coming from mac address 00:0F:EA:91:04:08 (add the following command to your firewall script):

 
/sbin/iptables -A INPUT -m mac --mac-source 00:0F:EA:91:04:08 -j DROP
 

Allow port 22 from mac address 00:0F:EA:91:04:07:

 
/sbin/iptables -A INPUT -p tcp --destination-port 22 -m mac --mac-source 00:0F:EA:91:04:07 -j ACCEPT
 

You can also use the interface name such as eth1:

 
/sbin/iptables -A INPUT -i eth1 -p tcp --destination-port 22 -m mac --mac-source 00:0F:EA:91:04:07 -j ACCEPT
 

You can also use FORWARD chain:

 
/sbin/iptables -A FORWARD -i ethX -m mac --mac-source YOUR-MAC-ADDRESS-HERE -j ACCEPT
 

You can also use NEW and other supported states as follows so that a known MAC address can be forwarded:

 
/sbin/iptables -A FORWARD -m state --state NEW -m mac --mac-source YOUR-MAC-ADDRESS-HERE -j ACCEPT
 

How Do I Skip Certain MAC Address?

Use the following syntax:

 
/sbin/iptables -A INPUT -p tcp --dport PORT -m mac ! --mac-source MAC-ADDRESS-HERE-TO-SKIP -j DROP
### Drop ssh access to all except our own MAC Address ###
/sbin/iptables -A INPUT -p tcp --dport 22 -m mac ! --mac-source YOUR-MAC-ADDRESS-HERE -j DROP
### Save rules ###
/sbin/service iptables save
 

The ! symbol means NOT. Your firewall will DROP packets destined to port 22 so long as they do NOT originate from your own computer with the desired MAC address.

Protecting MAC Address Spoofing From a Trusted Systems

Malicious user can spoof their MAC address with a trusted systems. To stop this kind of attacks use VLANS and/or static ARP entries.

See iptables man page for more information:
man 8 iptables

TwitterFacebookGoogle+PDF versionFound an error/typo on this page? Help us!

{ 32 comments… read them below or add one }

1 Anonymous January 7, 2006 at 8:58 am

Thanks!

Reply

2 Anonymous August 15, 2006 at 9:41 am

hello, how to blok ALL mac address, so i can permit only privileged mac adresses. thanks in advance

Reply

3 nixcraft August 15, 2006 at 3:23 pm

You can setup default policy to drop all packets and allow selected incoming packets from MAC based ip filtering.
Set default INPUT to deny all

# Setting default filter policy
iptables -P INPUT DROP
iptables -P OUTPUT ACCEPT
iptables -A INPUT -m mac –mac-source
00:0F:EA:91:04:08 -j ACCEPT

HTH

Reply

4 Michael Egan November 15, 2006 at 12:40 am

Does anybody know if this works on Suse 10.0? I need to filter a few MACs.

Reply

5 rick March 23, 2007 at 10:46 pm

Is there a way to get the MAC address of an attacker via iptable logging? All of the log levels that I’ve tried give me my server’s MAC address. I’d love to get the MAC of the person I’m blocking so I can block on their MAC in case they try using a proxy.

ex: -A RH-Firewall-1-INPUT -s ATTACKER_IP_HERE -j LOG –log-level 4 –log-prefix “DROP ATTACKER: ”

this results in logs such as…
Mar 21 13:38:41 server_name kernel: DROP ATTACKER: IN=eth0 OUT= MAC=MY_SERVER_MAC_ADDR_HERE SRC=ATTACKER_IP_HERE DST=MY_SERVER_IP LEN=48 TOS=0x00 PREC=0x00 TTL=114 ID=50714 DF PROTO=TCP SPT=39616 DPT=80 WINDOW=65535 RES=0x00 SYN URGP=0

Reply

6 irfan October 3, 2007 at 3:18 pm

hello i am using iptables

now i need that only those mac id can accept all other droped who can i do this

Reply

7 Catalin November 13, 2007 at 6:30 pm

Hello. I have a problem when i try to log with iptables. iptables v1.3.8: Unknown arg `LOG’
what should i do ?

Reply

8 zee November 19, 2007 at 2:50 pm

please i want to ban everyone of using my shell which is port 22 but keep their access on other ports and i owuld like only my PC to log to shell from my MAC address, anyone can help plz???

Reply

9 Lilian November 28, 2007 at 5:57 am

to ZEE

Allow an ip or network group to conect via SSH
/etc/host.allow

SSHD:192.168.0.4 or something like this 192.168.0.

Deny all conection on SSH
/etc/host.deny

SSHD:ALL

I think it will help you

Reply

10 Orvalho J Augusto May 7, 2008 at 2:32 am

Great!

You are good ones
Caveman

Reply

11 Shawn May 12, 2008 at 8:26 pm

Is there a way to use this in conjunction with the source IP. So that you can enforce a MAC address to only be allowed through if it is using a specific IP address?


Thanks
Shawn

Reply

12 nixCraft May 12, 2008 at 8:33 pm

Sure, you can use -s IP-address option. Verify source IP 192.168.1.200 along with MAC 00:0F:EA:91:04:08 and if both matched drop it:
iptables -A INPUT -p tcp -s 192.168.1.200 -m mac --mac-source 00:0F:EA:91:04:08 -j DROP

Reply

13 Luis July 8, 2008 at 4:07 pm

Could someone help.
I have to arm machines whit linux kernel 2.6
I wan’t to make a remote acess but i can’t…
one I have been defined a mac address ifconfig eth0 hw ether 0B:62:9D:6D:1A:34
I made ping suceful but when I try ftp ore telnet it refuse the conection…

Reply

14 coop March 26, 2009 at 1:46 pm

Hello

I wanna config a router with iptables for my WLAN. my problem, there is a database (mysql) there are all mac adresses, whitch have access…

is there a way to marry iptables with mysql??

best & THX coop

Reply

15 nixCraft March 26, 2009 at 4:07 pm

I don’t think so.. you need to take help of perl or python and send those IPs using system or exec or “ call to iptables.

Reply

16 Lillholm April 6, 2009 at 12:30 pm

Coop>
Here is a script i use to write my iptables.

#!/usr/bin/perl
use DBI;
$sql_user			= "dhcpd";
$sql_password			= "*******";
$sql_database			= "dhcpd";
$sql_hostname			= "localhost";
$sql_port			= "3306";
$dsn		= "DBI:mysql:database=$sql_database;host=$sql_hostname;port=$sql_port";
print "-----------------------------------------------\n";
print "      Building iptables config from mysql      \n";
print "-----------------------------------------------\n";
print "Getting information from  mysql database...";
$dbh = DBI->connect($dsn, $sql_user, $sql_password);
$getmac = $dbh->prepare("select mac from trusted order by ip");
$getip = $dbh->prepare("select ip from trusted order by ip");
$getmac->execute;
$getip->execute;
print "Done\n";
print "Creating temp file...";
#print `rm iptables.conf.temp`;
open (CONFIGFILE, '>>iptables.conf.temp');
print "Done\n";
print "Start writing configfile...\n-----------------------------------------------\n";
$count 		= 0;
while ( @getmac = $getmac->fetchrow_array, @getip = $getip->fetchrow_array ) {
    @mac[$count] = @getmac;
    @ip[$count] = @getip;
    $count++;
}
$dbh->disconnect;
$count = 0;
foreach (@mac) {
	print CONFIGFILE "iptables -A INPUT -p tcp -s @ip[$count] -m mac --mac-source @mac[$count] -j ACCEPT
" . 			 "";
	$count++;
	print "iptables -A INPUT -p tcp -s @ip[$count] -m mac --mac-source @mac[$count] -j ACCEPT" . "\n";
}
close (CONFIGFILE);
print "-----------------------------------------------\nDone.\n";
print `mv iptables.conf.temp iptables.conf`;
sleep(1);
#print `echo "do somthing here :)"`

I also made one for dhcpd so unknown mac’s logging on my wireless will be in a diffrent subnet.

Reply

17 nixCraft April 6, 2009 at 2:19 pm

Thanks for sharing perl script.

Reply

18 Atheya November 2, 2009 at 12:50 am

How do I execute this Perl script?

Reply

19 Zohaib Hussain February 22, 2010 at 6:22 am

Dear All,

please help me i have different prb facing i m running LAN network with LInux i m facing the prb of mac spoofing but some of users whom i blocked by my server they user mac address changer different softwares and by this software they detect any Online Active user mac address and just change the IP Address and use internet and when i try to block that mac address by iptables but i cant block that mac address because its mine online active users mac and who users blocked the connection of my LAN they do these things and use mac address changing software and get solid and valid legal mac address by network scanning. …. what i do i m much confused

Reply

20 Robert March 24, 2010 at 5:02 pm

Zohaib,

Sorry to say this but using Mac address filtering to control access to your network is like using a locked screen door to control access to your house. It keeps the generally honest out but doesn’t stop those who’s motives are less than pure. It’s a good general backup to the main security, but it is not a main security measure in and off itself. We use passwords and Mac filtering. Mac Address filtering makes it harder to use a stolen or hacked password.

Reply

21 zazuge March 26, 2010 at 2:41 pm

to Zohaib Hussain
if you have a proxy server then use password authentication
better if you have a managed switch
statically fix the ip address and MAC for every switch port
that way the only way to access the network is to use a certain IP address with the Original MAC address of the NIC while plugged to the correct switch port
and i don’t think that there is any way around this
check also VLAN

Reply

22 Tawfiq May 12, 2010 at 4:35 am

is it possible to put the info in a separate file and call it from your main firewall script?
lets say, there is a file called /root/scripts/ip-mac-list
where u have the info written as,
[code] 192.168.0.1 00:13:xx:xx:xx:xx
[/code]

Reply

23 raj June 17, 2010 at 10:59 am

Hi,

I want to block all MAC address except 1. Any clue.

I do not want to block TCP or UDP Traffic at all.

Thanks

Reply

24 Andy April 8, 2011 at 6:59 pm

Can I use this tutorial to create a MAC filter between a wireless network switch and the core? I need access to the network resources so I can’t use a router. What would you suggest?

Reply

25 Madhab June 6, 2011 at 2:28 pm

Hi,

I wanna block internet some computer PC with mac address which rule can do it

Reply

26 Jim August 26, 2011 at 9:41 pm

Is it possible to block all MACs except a range? For example, I want to allow all devices from a specific manufacturer such as 11.22.33.00.00.00 through 11.22.33.FF.FF.FF?

Reply

27 Dert October 22, 2011 at 1:07 am

Jim, i think no because i haven’t found in man special mac-adress diapason system support (like for IP-adresses)

Reply

28 Willy October 3, 2012 at 9:04 am

Hi,
someone knows why that command:

iptables -A INPUT -i eth0 -p tcp –dport 1234 -m mac –mac-source XX:XX:XX:XX:XX -j ACCEPT

works properly in a pc with iptables 1.4.4 and it give me this error:

iptables: No chain/target/match by that name.

on a pc with iptables 1.4.12.1


Willy

Reply

29 dp022 January 24, 2013 at 9:09 am

Hai,

Can anyone let me know how to block all the mac addresses except two mac addresses in the linux server..

Reply

30 Tom Boland June 24, 2013 at 5:19 pm

Warning on trying to use –mac-source when on a VM instance: It may not work.

For instance, in Hyper-V , the VM host machine’s IP address for the switch is what will *always* show as the source mac address, rather than the true mac address.

It may also be true for VMware, depending on configuration of the switch on the host.

Reply

31 John November 26, 2014 at 7:04 pm

Thanks for this post. I don’t really see this anywhere else in the IPTables documentation, though I could be missing it.
I wish a –match mac –mac-destination xx:xx:xx:xx:xx:xx had been implemented. It wouldn’t really stop a Man-in-the-Middle (MITM) attack but it would serve as a deterrent.
If one fails (maybe just forgets) to implement a prohibition on source routing (i.e. on a new install), it would be possible to source route (or partially source route) even an non-route-able packet to a destination in a LAN, ostensively from the IPTables protected host, and then to respond to that opened pinhole (related connection) in the IPTables firewall. I presently see rogue hosts, which are NOT DNS servers, sending unsolicited DNS responses (UDP/TCP port 53) to various hosts on my LAN (as well as faux ICMP responses) to try to open that pinhole to respond to. The ploy is almost as prevalent as MITM attacks, though, since it’s really difficult to detect good MITM attacks, how many MITM attacks can really be identified?

Reply

32 mahesh deshmukh December 2, 2014 at 5:59 am

by using the above commands i’m getting the following error..
iptables v1.4.12:ether
can any1 help pls?

Reply

Leave a Comment

Tagged as: , , , , , , , , , , , , , , , , , , , , ,

Previous post:

Next post: