freenet-router |
Subversion Repositories: |
Compare with Previous - Blame - Download
#! /bin/bash
# Firewall nove generace pro Czela Debian 3.1
# Autor: Mirek Slugen
# Spoluatori: Michal Perlik, Michal Vondracek, Jan Chmelensky, Adam Pribyl
# Vytvoreno: 06.11.2006
# Naposledy zmeneno: 08.2014
# Tento skript muzete volne sirit a upravovat.
# globĂĄlnĂ promÄnnĂĄ pro RO file systĂŠm
RO="no"
# ukonÄenĂ macguarda
macguard_stop() {
# StandardnÄ jakĂ˝koliv prĹŻchozĂ provoz skrze router povolĂme
$IPTABLES -P FORWARD ACCEPT
# VymaĹžeme obsah vĹĄech tĹĂd vytvoĹenĂ˝ch pro macguarda
$IPTABLES -F eth_accept
$IPTABLES -t nat -F valid_mac_pre
$IPTABLES -F valid_mac_fwd
# pĹedtĂm, neĹž vymaĹžeme tĹĂdy macguarda, musĂme zruĹĄit vĹĄechny pravidla na nÄ odkazujĂcĂ
for I in `iptables -L FORWARD -n -v --line-numbers | grep eth_accept | grep all | grep -v spt | grep -v dpt | awk '{print $1}' | sort -r -n`; do
$IPTABLES -D FORWARD $I
done
for I in `iptables -t nat -L PREROUTING -n -v --line-numbers | grep valid_mac_pre | grep all | grep -v spt | grep -v dpt | awk '{print $1}' | sort -r -n`; do
$IPTABLES -t nat -D PREROUTING $I
done
# vymaĹžeme dalĹĄĂ pravidla vytvoĹenĂĄ macguardem
for I in `iptables -L FORWARD -n -v --line-numbers | grep ACCEPT | grep all | grep -v spt | grep -v dpt | awk '{print $1}' | sort -r -n`; do
$IPTABLES -D FORWARD $I
done
for I in `iptables -t nat -L PREROUTING -n -v --line-numbers | grep ACCEPT | grep all | grep -v spt | grep -v dpt | awk '{print $1}' | sort -r -n`; do
$IPTABLES -t nat -D PREROUTING $I
done
# SmaĹžeme vĹĄechny tĹĂdy vytvoĹenĂŠ pro macguarda
$IPTABLES -X eth_accept
$IPTABLES -t nat -X valid_mac_pre
$IPTABLES -X valid_mac_fwd
}
# krĂĄtkodobÄ do dalĹĄĂ aktualizace povolĂme mac adresu, prvnĂ je IP, druhĂĄ MAC
macguard_allow_user() {
( [ "$1" == "" ] || [ "$2" == "" ] ) && return 0
if [ "$1" == "0" ]; then
while true; do
$IPTABLES -D FORWARD -s "$2" -j valid_mac_fwd 2>/dev/null
[ "$?" != "0" ] && break
done
while true; do
$IPTABLES -t nat -D PREROUTING -s "$2" -j valid_mac_pre 2>/dev/null
[ "$?" != "0" ] && break
done
else
$IPTABLES -t nat -L valid_mac_pre -n 1>/dev/null 2>/dev/null
[ "$?" != "0" ] && return 0
$IPTABLES -L valid_mac_fwd -n 1>/dev/null 2>/dev/null
[ "$?" != "0" ] && return 0
LINE_PRE=$((`$IPTABLES -t nat -L valid_mac_pre -n -v --line-numbers | grep MAC | awk '{print $1}' | tail -n 1` + 1))
$IPTABLES -t nat -I valid_mac_pre $LINE_PRE -s "$2" -m mac --mac-source "$1" -j ACCEPT 2>/dev/null
LINE_FWD=$((`$IPTABLES -L valid_mac_fwd -n -v --line-numbers | grep MAC | awk '{print $1}' | tail -n 1` + 1))
$IPTABLES -I valid_mac_fwd $LINE_FWD -s "$2" -m mac --mac-source "$1" -j ACCEPT 2>/dev/null
fi
}
# krĂĄtkodobÄ do dalĹĄĂ aktualizace zakĂĄĹžeme mac adresu
macguard_deny_user() {
( [ "$1" == "" ] || [ "$2" == "" ] ) && return 0
if [ "$1" == "0" ]; then
$IPTABLES -A FORWARD -s "$2" -j valid_mac_fwd
$IPTABLES -t nat -A PREROUTING -s "$2" -j valid_mac_pre
else
while true; do
$IPTABLES -t nat -D valid_mac_pre -s "$2" -m mac --mac-source "$1" -j ACCEPT 2>/dev/null
[ "$?" != "0" ] && break
done
while true; do
$IPTABLES -D valid_mac_fwd -s "$2" -m mac --mac-source "$1" -j ACCEPT 2>/dev/null
[ "$?" != "0" ] && break
done
fi
}
macguard_load_conf() {
local TYPE=""
local IP=""
local MAC=""
# Zpracujeme konfiguraÄnĂ soubor
while read TYPE MAC IP; do
if [ "$TYPE" == "ALLOW" ]; then
echo -n "Allowing mac $MAC with ip $IP..."
macguard_allow_user "$MAC" "$IP"
echo "done."
elif [ "$TYPE" == "DENY" ]; then
echo -n "Denying mac $MAC with ip $IP..."
macguard_deny_user "$MAC" "$IP"
echo "done."
fi
done < "/etc/firewall/macguard.conf"
}
# Otestujeme jestli je soubor moĹžnĂŠ uloĹžit, pokud ne, tak povolĂme zĂĄpis
# a nastavĂme RO na yes.
ro_test() {
local F_EXIST="no"
( [ "$1" == "" ] || [ "$1" == "/" ] ) && return 0
[ -e "$1" ] && F_EXIST="yes"
touch "$1" 2>/dev/null
if [ "$?" != "0" ]; then
/usr/local/sbin/rw 1>/dev/null
RO="yes"
fi
[ "$F_EXIST" != "yes" ] && rm -f "$1" 2>/dev/null
}
# UkonÄenĂ RO mĂłdu, pokud jsme disk odemkli, tak ho takĂŠ zkusĂme zamknout
ro_exit() {
[ "$RO" != "yes" ] && return 0
/usr/local/sbin/ro 1>/dev/null
RO="no"
}
# hlavnĂ implementace macguarda
macguard_start() {
# detekce rozhranĂ pro macguarda
I="0"
MACGUARD_DEV_YES=""
MACGUARD_DEV_NO=""
MACGUARD_DEV_DHCP=""
while [ "$I" -lt 15 ]; do
DEV=DEV${I}_IFACE
DEV=${!DEV}
MACGUARD_DEV=DEV${I}_MACGUARD
MACGUARD_DEV=${!MACGUARD_DEV}
MACGUARD_DHCP=DEV${I}_MACGUARD_DHCP
MACGUARD_DHCP=${!MACGUARD_DHCP}
if [ "$MACGUARD_DEV" == "yes" ] && [ "$DEV" != "" ]; then
if [ "$MACGUARD_DEV_YES" == "" ]; then
MACGUARD_DEV_YES="$DEV"
else
MACGUARD_DEV_YES="$MACGUARD_DEV_YES $DEV"
fi
elif [ "$MACGUARD_DEV" != "yes" ] && [ "$DEV" != "" ]; then
if [ "$MACGUARD_DEV_NO" == "" ]; then
MACGUARD_DEV_NO="$DEV"
else
MACGUARD_DEV_NO="$MACGUARD_DEV_NO $DEV"
fi
fi
if [ "$MACGUARD_DHCP" == "yes" ] && [ "$DEV" != "" ]; then
if [ "$MACGUARD_DEV_DHCP" == "" ]; then
MACGUARD_DEV_DHCP="$DEV"
else
MACGUARD_DEV_DHCP="$MACGUARD_DEV_DHCP $DEV"
fi
fi
((I++))
done
# Pro dalĹĄĂ prĂĄci potĹebujeme dummy a jeho ip adresu!
[ "$DUMMY_IFACE" == "" ] && DUMMY_IFACE="dummy0"
[ "$DUMMY_IP" == "" ] && DUMMY_IP="`$IP addr show $DUMMY_IFACE | grep inet | grep -v inet6 | awk '{print \$2}' | cut -d \"/\" -f1`"
# zavedenĂ zĂĄkladnĂch pravidel pro macguarda
# podmĂnky spuĹĄtÄnĂ:
# 1. pokud mĂĄme nÄjakĂŠ rozhranĂ na kterĂŠm bÄŞà macguard
# 2. pokud neprovĂĄdĂme jen aktualizaci dat
if [ "$MACGUARD_DEV_YES" != "" ] && [ "$1" != "update" ]; then
echo -n "Starting macguard on:"
# StandardnÄ jakĂ˝koliv prĹŻchozĂ provoz skrze router zahazujeme
$IPTABLES -P FORWARD DROP
# VytvoĹĂme tĹĂdy pro macguarda
$IPTABLES -N eth_accept
$IPTABLES -t nat -N valid_mac_pre
$IPTABLES -N valid_mac_fwd
# pokud pouĹžĂvĂĄme ACCOUNT, tak ho znovu zavedeme i pĹi zavedenĂ zĂĄkladnĂch pravidel pro macguarda
[ "$ACCOUNT" == "yes" ] && account_start
# vygenerujeme zĂĄkladnĂ pravidla pro danĂĄ rozhranĂ
for DEV in $MACGUARD_DEV_YES; do
# zĂĄkladnĂ ochrana pĹed ĹĄpatnÄ zadanĂ˝m, nebo neaktivnĂm rozhranĂm
$IP addr show $DEV 1>/dev/null 2>/dev/null
[ "$?" != "0" ] && continue
# oznĂĄmĂme Ĺže zpracovĂĄvĂĄme danĂŠ rozhranĂ
echo -n " $DEV"
# zĂskĂĄme adresu IP a masku rozhranĂ
DEV_IP="`ip addr show $DEV | grep -v inet6 | grep inet | grep -v : | awk '{print \$2}' | cut -d \"/\" -f1`"
DEV_IP1="`echo $DEV_IP | cut -d. -f1`"
DEV_IP2="`echo $DEV_IP | cut -d. -f2`"
DEV_IP3="`echo $DEV_IP | cut -d. -f3`"
DEV_IP4="`echo $DEV_IP | cut -d. -f4`"
# netmask
NETMASK="`ip addr show $DEV | grep -v inet6 | grep inet | grep -v : | awk '{print \$2}' | cut -d \"/\" -f2`"
# vygenerujeme masku na zĂĄkladÄ netmask
if let $(((32-${NETMASK}) > 0)); then
MASK_IP4=$(((255 << (32-${NETMASK})) & 255))
else
MASK_IP4=255
fi
if let $(((24-${NETMASK}) > 0)); then
MASK_IP3=$(((255 << (24-${NETMASK})) & 255))
else
MASK_IP3=255
fi
if let $(((16-${NETMASK}) > 0)); then
MASK_IP2=$(((255 << (16-${NETMASK})) & 255))
else
MASK_IP2=255
fi
if let $(((8-${NETMASK}) > 0)); then
MASK_IP1=$(((255 << (8-${NETMASK})) & 255))
else
MASK_IP1=255
fi
MASK="$MASK_IP1.$MASK_IP2.$MASK_IP3.$MASK_IP4"
# network
NETWORK_IP1="$(($DEV_IP1 & $MASK_IP1))"
NETWORK_IP2="$(($DEV_IP2 & $MASK_IP2))"
NETWORK_IP3="$(($DEV_IP3 & $MASK_IP3))"
NETWORK_IP4="$(($DEV_IP4 & $MASK_IP4))"
NETWORK="$NETWORK_IP1.$NETWORK_IP2.$NETWORK_IP3.$NETWORK_IP4"
# NezakĂĄĹžeme prĹŻchod Äehokoliv co nejde z rozsahu na danĂŠm rozhranĂ, abychom neblokovali
# IP adresy pĹipojenĂŠ na danĂ˝ router skrze dalĹĄĂ router.
$IPTABLES -t nat -A PREROUTING -i $DEV ! -s "$NETWORK/$NETMASK" -j ACCEPT
$IPTABLES -A FORWARD -i $DEV ! -s "$NETWORK/$NETMASK" -j ACCEPT
# VĹĄe ostatnĂ jde do tĹĂdy valid_mac_pre kde bude ovÄĹeno jestli je pro danou MAC adresu
# a IP adresu povolen pĹĂstup na internet.
$IPTABLES -t nat -A PREROUTING -i $DEV -j valid_mac_pre
$IPTABLES -A FORWARD -i $DEV -j eth_accept
done
# povolĂme pĹĂchozĂ provoz na rozhranĂch, kde nenĂ aktivnĂ macguad
for DEV in $MACGUARD_DEV_NO; do
$IPTABLES -A FORWARD -i $DEV -j ACCEPT
done
# default politika pro eth_accept je ACCEPT
$IPTABLES -A eth_accept -j valid_mac_fwd
$IPTABLES -A eth_accept -j ACCEPT
# odchozĂ provoz skrze rozhranĂ povolĂme
for DEV in $MACGUARD_DEV_YES $MACGUARD_DEV_NO; do
$IPTABLES -A FORWARD -o $DEV -j ACCEPT
done
echo ""
fi
# hlavnĂ ÄĂĄst macguarda
# podmĂnky spuĹĄtÄnĂ:
# 1. pokud mĂĄme nÄjakĂŠ rozhranĂ na kterĂŠm bÄŞà macguard, nebo dhcp server
# 2. pokud nechceme dÄlat jen klasickĂ˝ update, nebo existuje semafor, nebo chceme dÄlat vynucenĂ˝ uprade, nebo neexistuje csv tabulka
if ( [ "$MACGUARD_DEV_YES" != "" ] || [ "$MACGUARD_DEV_DHCP" != "" ] ) && ( [ "$1" != "update" ] || [ -e "$MACGUARD_DIR/semafor" ] || [ "$2" == "force" ] || [ ! -e "$MACGUARD_DIR/table-$DUMMY_IP.csv" ] ); then
# nahlĂĄsĂme do logu udĂĄlost
logger "updating macguard settings"
# semafor
[ -e "$MACGUARD_DIR/semafor" ] && MACGUARD_SEMAFOR="on"
rm -f "$MACGUARD_DIR/semafor"
# pokud neexistuje csv tabulka, nebo dÄlĂĄme vynucenĂ˝ update, tak zkusĂme stĂĄhnout novĂĄ data
if [ ! -e "$MACGUARD_DIR/table-$DUMMY_IP.csv" ] || [ "$2" == "force" ]; then
# neexistujĂ-li klĂÄe pro ssh uĹživatele safe, tak je vygenerujeme
if [ ! -e "/home/safe/.ssh/id_dsa" ] || [ ! -e "/home/safe/.ssh/id_dsa.pub" ]; then
ro_test "/home/safe/.ssh/id_dsa"
# soubory musĂme radÄji odstranit
rm -f "/home/safe/.ssh/id_dsa"* 2>/dev/null
# generovĂĄnĂ klĂÄĹŻ
echo -n "Generating ssh keys for user safe..."
su safe -c "/usr/bin/ssh-keygen -q -P \"\" -t dsa -f /home/safe/.ssh/id_dsa"
chown safe:safe "/home/safe/.ssh/id_dsa"
chown safe:safe "/home/safe/.ssh/id_dsa.pub"
echo "done."
echo ""
echo "Nyni musite nahrat verejny klic /home/safe/.ssh/id_dsa.pub na macguard server"
echo "do souboru /home/safe/.ssh/authorized_keys, pokud nemate pristup kontaktujte"
echo "spravce serveru. Bez tohoto kroku nebude mozne stahnout aktualni data pro"
echo "macguarda ze serveru na tento router!!"
echo ""
sleep 2
# zruĹĄeno kvĹŻli vyĹazeni ssmtp a mail ze zĂĄkladnĂ instalace
#echo -n "Chcete zaslat verejny klic spravci macguard serveru [`tput setaf 2`ano`tput op`/ne] "
#read x
#if [ "$x" != "ne" ]; then
# zatim si klic necham posilat jen sobe
#cat "/home/safe/.ssh/id_dsa.pub" | mail -s "Verejny klic uzivatele safe z routeru `hostname`" thunder.m@czela.net
#fi
fi
# pokusĂme se stĂĄhnout tabulku
echo -n "Downloading new table for macguard..."
su safe -c "mkdir -p $MACGUARD_DIR" 1>/dev/null 2>/tmp/firewall.err
su safe -c "scp -B safe@${MACGUARD_SERVER}:/home/safe/macguard-centrala/table-${DUMMY_IP}.* $MACGUARD_DIR" 1>/dev/null 2>/tmp/firewall.err
if [ "$?" == "0" ]; then
echo "done."
logger "downloading new macguard table: done"
MACGUARD_STATUS="on"
else
echo "failed."
# zobrazĂme chybovou hlĂĄĹĄku
cat "/tmp/firewall.err"
logger "downloading new macguard table: failed!"
logger "`cat /tmp/firewall.err`"
MACGUARD_STATUS="off"
# pokud se nĂĄm nepodaĹilo zĂskat data z macguard serveru, tak zkusĂme pouĹžĂt
# naposledy uloĹženou tabulku
if [ -e "/usr/share/macguard/table-${DUMMY_IP}.csv" ] && [ ! -e "$MACGUARD_DIR/table-${DUMMY_IP}.csv" ]; then
cp -ax "/usr/share/macguard/table-${DUMMY_IP}."* "$MACGUARD_DIR"
fi
fi
# vymaĹžeme chybovou hlĂĄĹĄku
rm -rf "/tmp/firewall.err"
fi
# UdÄlĂĄme zĂĄlohu staĹženĂŠ tabulky, abychom pĹi restartu mÄli okamĹžitÄ k dispozici
# alespoĹ ÄĂĄsteÄnÄ aktuĂĄlnĂ data.
MACGUARD_UPDATE_BACKUP="no"
if ( [ "$MACGUARD_STATUS" == "on" ] || [ "$MACGUARD_SEMAFOR" == "on" ] ) && [ -e "$MACGUARD_DIR/table-$DUMMY_IP.csv" ]; then
if [ -e "/usr/share/macguard/table-${DUMMY_IP}.csv" ]; then
# soubory sice existujĂ, ale liĹĄĂ se, takĹže je aktuĂĄlnĂ soubor nejspĂĹĄ novÄjĹĄĂ
if [ "`diff \"$MACGUARD_DIR/table-${DUMMY_IP}.csv\" \"/usr/share/macguard/table-${DUMMY_IP}.csv\"`" != "" ]; then
MACGUARD_UPDATE_BACKUP="yes"
fi
else
MACGUARD_UPDATE_BACKUP="yes"
fi
fi
# Aktualizujeme zĂĄlohu tabulky, aktualizace dat nesmĂme provĂĄdÄt zase moc Äasto,
# jinak tĂm niÄĂme flash disky.
if [ "$MACGUARD_UPDATE_BACKUP" == "yes" ]; then
SKIP_RO="no"
touch "/usr/share/macguard.testfile" 2>/dev/null
if [ "$?" != "0" ]; then
# staÄĂ odemknout jednou tĂ˝dnÄ, pokud neodemkneme uzamÄenĂ˝ FS, nezapĂĹĄou se novĂĄ data
if [ -e "$MACGUARD_DIR/table-${DUMMY_IP}.csv" ] && [ ! -e "/usr/share/macguard/table-${DUMMY_IP}.csv" ]; then
/usr/local/sbin/rw 1>/dev/null
RO="yes"
elif [ -e "$MACGUARD_DIR/table-${DUMMY_IP}.csv" ] && [ -e "/usr/share/macguard/table-${DUMMY_IP}.csv" ]; then
if [ "`expr \`ls $MACGUARD_DIR/table-${DUMMY_IP}.csv -l --time-style=+%s | awk '{print \$6}'\` - \`ls /usr/share/macguard/table-${DUMMY_IP}.csv -l --time-style=+%s | awk '{print \$6}'\``" -gt "604800" ]; then
/usr/local/sbin/rw 1>/dev/null
RO="yes"
fi
else
SKIP_RO="yes"
fi
fi
rm -f "/usr/share/macguard.testfile" 2>/dev/null
if [ "$SKIP_RO" != "yes" ]; then
echo -n "Creating backup of macguard table..."
mkdir -p "/usr/share/macguard"
cp -ax "$MACGUARD_DIR/table-${DUMMY_IP}."* "/usr/share/macguard/"
echo "done."
fi
fi
# Pokud jsme nestahovali novĂĄ data a tudĂĹž nevĂme jestli je dostupnĂ˝ macguard server,
# tak ovÄĹĂme jeho dostupnost pingem, jestli je nedostupnĂ˝, tak pozdÄji povolĂme vĹĄechny
# IP.
if [ "$MACGUARD_STATUS" == "" ]; then
I_STATUS="0"
J_STATUS="0"
while true; do
ping -q -c 1 $MACGUARD_SERVER >/dev/null 2>/dev/null
if [ "$?" != "0" ]; then
((I_STATUS++))
else
((J_STATUS++))
fi
# pokud je ĹĄpatnĂ˝ch vĂce jak 1 a dobrĂ˝ch mĂŠnÄ neĹž 2, tak je server nedostupnĂ˝
if [ "$I_STATUS" -gt "1" ] && [ "$J_STATUS" -lt "2" ]; then
MACGUARD_STATUS="off"
break
# pokud je dobrĂ˝ch vĂce jak 1 a ĹĄpatnĂ˝ch mĂŠnÄ neĹž 2, tak je server dostupnĂ˝
elif [ "$J_STATUS" -gt "1" ] && [ "$I_STATUS" -lt "2" ]; then
MACGUARD_STATUS="on"
break
fi
done
fi
# generovĂĄnĂ pravidel pro iptables na zĂĄkladÄ csv tabulky
# podmĂnky spuĹĄtÄnĂ:
# 1. pokud mĂĄme nÄjakĂŠ rozhranĂ na kterĂŠm bÄŞà macguard
# 2. pokud existuje csv tabulka
# 3. pokud je dostupnĂ˝ macguard server, nebo byla nahrĂĄna novĂĄ tabulka
if [ "$MACGUARD_DEV_YES" != "" ] && [ -e "$MACGUARD_DIR/table-$DUMMY_IP.csv" ] && [ "$MACGUARD_STATUS" == "on" ]; then
# VymaĹžeme vĹĄechna pravidla v danĂŠ tĹĂdÄ
$IPTABLES -t nat -F valid_mac_pre 2>/dev/null
$IPTABLES -F valid_mac_fwd 2>/dev/null
# zpracujeme csv tabulku
while read USER_IP B USER_MAC D USER_NAME F USER_VS H USER_ROUTER K USER_ROUTER_MAC L USER_SUBNET; do
# podmĂnka pro netransparentnĂ zaĹĂzenĂ jako napĹĂklad ovislinky na wifi
if [ "$USER_ROUTER" == "$DUMMY_IP" ]; then
$IPTABLES -t nat -A valid_mac_pre -s "$USER_IP" -m mac --mac-source "$USER_MAC" -j ACCEPT
$IPTABLES -A valid_mac_fwd -s "$USER_IP" -m mac --mac-source "$USER_MAC" -j ACCEPT
else
$IPTABLES -t nat -A valid_mac_pre -s "$USER_IP" -m mac --mac-source "$USER_ROUTER_MAC" -j ACCEPT
$IPTABLES -A valid_mac_fwd -s "$USER_IP" -m mac --mac-source "$USER_ROUTER_MAC" -j ACCEPT
fi
# rozĹĄĂĹenĂ o subnet, kterĂ˝ uĹživatel mĹŻĹže vyuĹžĂvat
if [ "`echo $USER_SUBNET | grep -F .`" != "" ]; then
# otazka je jak tyto routy mazat po vypnuti macguarda, nebo firewallu?
$IP route del "$USER_SUBNET" 2>/dev/null
$IP route add "$USER_SUBNET" via "$USER_IP" 2>/dev/null
fi
done < "$MACGUARD_DIR/table-$DUMMY_IP.csv"
# Nahrajeme speciĂĄlnĂ konfiguraÄnĂ soubor
macguard_load_conf
# povolĂme ssh, web, mail a dns na vnitĹnĂ adresy i pro ostatnĂ IP
$IPTABLES -A valid_mac_fwd -p tcp -d $INTERNAL_IP --dport 22 -j ACCEPT
$IPTABLES -A valid_mac_fwd -p tcp -d $INTERNAL_IP --dport 25 -j ACCEPT
$IPTABLES -A valid_mac_fwd -p udp -d $INTERNAL_IP --dport 25 -j ACCEPT
$IPTABLES -A valid_mac_fwd -p tcp -d $INTERNAL_IP --dport 53 -j ACCEPT
$IPTABLES -A valid_mac_fwd -p udp -d $INTERNAL_IP --dport 53 -j ACCEPT
$IPTABLES -A valid_mac_fwd -p tcp -d $INTERNAL_IP --dport 80:81 -j ACCEPT
# PĹesmÄrujeme jakĂ˝koliv dotaz na http port nevnitĹnĂ IP na macguard server, port 81,
# kde by mÄla bĂ˝t vysvÄtlujĂcĂ http strĂĄnka s informacemi proÄ je uĹživatel zablokovĂĄn
# pĹĂpadnÄ jak vyĹeĹĄit nefunkÄnĂ pĹipojenĂ.
$IPTABLES -t nat -A valid_mac_pre ! -d $INTERNAL_IP -p tcp --dport 80 -j DNAT --to ${MACGUARD_SERVER}:81
# ostatnĂ MAC adresy zakĂĄĹžeme
$IPTABLES -A valid_mac_fwd -j REJECT
else
# VymaĹžeme vĹĄechna pravidla v danĂŠ tĹĂdÄ
$IPTABLES -t nat -F valid_mac_pre 2>/dev/null
$IPTABLES -F valid_mac_fwd 2>/dev/null
fi
# ÄĂĄst pro generovĂĄnĂ a spouĹĄtÄnĂ dhcp serveru, o dhcp server se starĂĄ macguard,
# proto nenĂ tĹeba speciĂĄlnÄ upravovat soubor /etc/init.d/isc-dhcp-server
# podmĂnky spuĹĄtÄnĂ:
# 1. pokud mĂĄme nÄjakĂŠ rozhranĂ, kde spouĹĄtĂme dhcp server
# 2. nebÄĹžĂ-li dhcp server, nebo existuje-li cvs tabulka
# 3. nebÄĹžĂ-li dhcp server, nebo jsme dostali novou csv tabulku
if [ "$MACGUARD_DEV_DHCP" != "" ] && ( [ "`ps -e | grep dhcpd`" == "" ] || [ -e "$MACGUARD_DIR/table-$DUMMY_IP.csv" ] ) && ( [ "`ps -e | grep dhcpd`" == "" ] || [ "$MACGUARD_STATUS" == "on" ] ); then
# dhcp server musĂme zastavit aby nĂĄm pĹi generovĂĄnĂ nepĹepsal dhcpd.leases
[ "`ps -e | grep dhcpd`" != "" ] && /etc/init.d/isc-dhcp-server stop
# -------------------------- generovĂĄnĂ dhcpd.conf -----------------------------
# naÄteme promÄnnou INTERFACES
[ -e "/etc/default/isc-dhcp-server" ] && . /etc/default/isc-dhcp-server
# vynulujeme generovĂĄnĂ souboru /etc/default/isc-dhcp-server
INTERFACES_NEW=""
# vyÄistĂme dhcp soubory
rm -f "$MACGUARD_DIR/dhcpd.conf"
rm -f "/var/lib/dhcp/dhcpd.leases"*
touch "/var/lib/dhcp/dhcpd.leases" # isc-dhcp-server vyzaduje existenci tohoto souboru
# datum ve formĂĄtu pro dhcpd.leases
DHCP_START_DATE="`date -u \"+%w %Y/%m/%d %H:%d:%M\"`"
DHCP_END_DATE="`date -u \"+%w %Y/%m/%d %H:%d:%M\" -d \"+2 year\"`"
# zĂĄklad dhcpd.conf
echo "# Created by firewall script for macguard" >> "$MACGUARD_DIR/dhcpd.conf"
echo "" >> "$MACGUARD_DIR/dhcpd.conf"
echo "authoritative;" >> "$MACGUARD_DIR/dhcpd.conf"
echo "log-facility local7;" >> "$MACGUARD_DIR/dhcpd.conf"
echo "default-lease-time 43200; # 12 hours" >> "$MACGUARD_DIR/dhcpd.conf"
echo "max-lease-time 2678400; # 31 days" >> "$MACGUARD_DIR/dhcpd.conf"
echo "option domain-name \"$DOMAIN\";" >> "$MACGUARD_DIR/dhcpd.conf"
echo "option domain-name-servers $DNS_PRIMARY, $DNS_SECONDARY;" >> "$MACGUARD_DIR/dhcpd.conf"
echo "option netbios-name-servers $NETBIOS;" >> "$MACGUARD_DIR/dhcpd.conf"
echo "option T150 code 150 = string;" >> "$MACGUARD_DIR/dhcpd.conf"
echo "use-host-decl-names on;" >> "$MACGUARD_DIR/dhcpd.conf"
echo "allow booting;" >> "$MACGUARD_DIR/dhcpd.conf"
echo "allow bootp;" >> "$MACGUARD_DIR/dhcpd.conf"
echo "" >> "$MACGUARD_DIR/dhcpd.conf"
# generovĂĄnĂ ip adres pro jednotlivĂĄ rozhranĂ
for DEV in $MACGUARD_DEV_DHCP; do
# zĂĄkladnĂ ochrana pĹed ĹĄpatnÄ zadanĂ˝m, nebo neaktivnĂm rozhranĂm
$IP addr show $DEV 1>/dev/null 2>/dev/null
[ "$?" != "0" ] && continue
# Pokud schĂĄzĂ v /etc/default/isc-dhcp-server danĂŠ rozhranĂ, tak musĂme vygenerovat
# novĂ˝ soubor obsahujĂcĂ toto rozhranĂ.
[ "`echo $INTERFACES | tr \" \" \"\n\" | grep -x \"$DEV\"`" != "$DEV" ] && INTERFACES_NEW="yes"
# spojenĂ vĹĄech zaĹĂzenĂ do formĂĄtu pro soubor /etc/default/isc-dhcp-server
if [ "$INTERFACES_INTERNAL" != "" ]; then
INTERFACES_INTERNAL="$INTERFACES_INTERNAL $DEV"
else
INTERFACES_INTERNAL="$DEV"
fi
# zĂskĂĄme adresu IP a masku rozhranĂ
DEV_IP="`ip addr show $DEV | grep -v inet6 | grep inet | grep -v : | awk '{print \$2}' | cut -d \"/\" -f1`"
DEV_IP1="`echo $DEV_IP | cut -d. -f1`"
DEV_IP2="`echo $DEV_IP | cut -d. -f2`"
DEV_IP3="`echo $DEV_IP | cut -d. -f3`"
DEV_IP4="`echo $DEV_IP | cut -d. -f4`"
# netmask
NETMASK="`ip addr show $DEV | grep -v inet6 | grep inet | grep -v : | awk '{print \$2}' | cut -d \"/\" -f2`"
# vygenerujeme masku na zĂĄkladÄ netmask
if let $(((32-${NETMASK}) > 0)); then
MASK_IP4=$(((255 << (32-${NETMASK})) & 255))
else
MASK_IP4=255
fi
if let $(((24-${NETMASK}) > 0)); then
MASK_IP3=$(((255 << (24-${NETMASK})) & 255))
else
MASK_IP3=255
fi
if let $(((16-${NETMASK}) > 0)); then
MASK_IP2=$(((255 << (16-${NETMASK})) & 255))
else
MASK_IP2=255
fi
if let $(((8-${NETMASK}) > 0)); then
MASK_IP1=$(((255 << (8-${NETMASK})) & 255))
else
MASK_IP1=255
fi
MASK="$MASK_IP1.$MASK_IP2.$MASK_IP3.$MASK_IP4"
# network
NETWORK_IP1="$(($DEV_IP1 & $MASK_IP1))"
NETWORK_IP2="$(($DEV_IP2 & $MASK_IP2))"
NETWORK_IP3="$(($DEV_IP3 & $MASK_IP3))"
NETWORK_IP4="$(($DEV_IP4 & $MASK_IP4))"
NETWORK="$NETWORK_IP1.$NETWORK_IP2.$NETWORK_IP3.$NETWORK_IP4"
# broadcast
BROADCAST_IP1="$((($DEV_IP1 & $MASK_IP1) + (255 - $MASK_IP1)))"
BROADCAST_IP2="$((($DEV_IP2 & $MASK_IP2) + (255 - $MASK_IP2)))"
BROADCAST_IP3="$((($DEV_IP3 & $MASK_IP3) + (255 - $MASK_IP3)))"
BROADCAST_IP4="$((($DEV_IP4 & $MASK_IP4) + (255 - $MASK_IP4)))"
BROADCAST="$BROADCAST_IP1.$BROADCAST_IP2.$BROADCAST_IP3.$BROADCAST_IP4"
# zapĂĹĄeme danĂ˝ subnet
echo "subnet $NETWORK netmask $MASK {" >> "$MACGUARD_DIR/dhcpd.conf"
# nejmensi subnet pro ktery umime udelat dynamic-bootp je s maskou 255.255.255.252
if [ "$MASK_IP4" -le "252" ]; then
# oÄekĂĄvĂĄme Ĺže brĂĄna mĂĄ prvnĂ dostupnou adresu danĂŠ sĂtÄ!
HIGHEST_IP4=0
if [ -e "$MACGUARD_DIR/table-$DUMMY_IP.csv" ]; then
HIGHEST_IP4=`grep $NETWORK_IP1\.$NETWORK_IP2\.$NETWORK_IP3\. "$MACGUARD_DIR/table-$DUMMY_IP.csv" | cut -d\; -f1 | cut -d\. -f4| sort -g | awk -v BIP4=$BROADCAST_IP4 '$1<BIP4' | awk -v NIP4=$NETWORK_IP4 '$1>NIP4' | tail -1`
if [ -z "$HIGHEST_IP4" ]; then
HIGHEST_IP4=$(($NETWORK_IP4 + 2))
else
HIGHEST_IP4=$(($HIGHEST_IP4 + 1))
fi
fi
if [ $HIGHEST_IP4 -ge $(($BROADCAST_IP4 - 1)) ]; then
echo "DHCP pro $DEV nema volny dynamicky rozsah"
HIGHEST_IP4=$(($NETWORK_IP4 + 2))
fi
echo " range dynamic-bootp $NETWORK_IP1.$NETWORK_IP2.$NETWORK_IP3.$HIGHEST_IP4 $BROADCAST_IP1.$BROADCAST_IP2.$BROADCAST_IP3.$(($BROADCAST_IP4 - 1));" >> "$MACGUARD_DIR/dhcpd.conf"
fi
# jako default gateway je ip adresa rozhranĂ
echo " option routers $DEV_IP;" >> "$MACGUARD_DIR/dhcpd.conf"
# pĹĂklad startu ze sĂtÄ pomocĂ pxelinuxu, pouze pro node nĂĄdraŞà a rozsah na ethernetu
if [ "$DEV_IP" == "10.93.49.193" ]; then
echo " server-name \"10.93.49.250\";" >> "$MACGUARD_DIR/dhcpd.conf"
echo " next-server 10.93.49.250;" >> "$MACGUARD_DIR/dhcpd.conf"
echo " filename \"/tftpboot/pxelinux/pxelinux.0\";" >> "$MACGUARD_DIR/dhcpd.conf"
fi
echo "" >> "$MACGUARD_DIR/dhcpd.conf"
# pokud existuje csv soubor, tak ho naÄteme
if [ -e "$MACGUARD_DIR/table-$DUMMY_IP.csv" ]; then
# NaÄĂtĂĄme soubor tolikrĂĄt, kolik je k dispozici rozhranĂ, nenĂ moc efektivnĂ.
while read USER_IP A USER_MAC B USER_NAME C; do
IFS=$';. \t\n'
USER_IP_POM=( $USER_IP )
IFS=$' \t\n'
USER_IP1=${USER_IP_POM[0]}
USER_IP2=${USER_IP_POM[1]}
USER_IP3=${USER_IP_POM[2]}
USER_IP4=${USER_IP_POM[3]}
if ( [ $USER_IP1 == $DEV_IP1 ] || ( [ $USER_IP1 -gt $NETWORK_IP1 ] && [ $USER_IP1 -lt $BROADCAST_IP1 ] ) ) && \
( [ $USER_IP2 == $DEV_IP2 ] || ( [ $USER_IP2 -gt $NETWORK_IP2 ] && [ $USER_IP2 -lt $BROADCAST_IP2 ] ) ) && \
( [ $USER_IP3 == $DEV_IP3 ] || ( [ $USER_IP3 -gt $NETWORK_IP3 ] && [ $USER_IP3 -lt $BROADCAST_IP3 ] ) ) && \
( [ $USER_IP4 == $DEV_IP4 ] || ( [ $USER_IP4 -gt $NETWORK_IP4 ] && [ $USER_IP4 -lt $BROADCAST_IP4 ] ) ) && \
( [ "$DEV_IP" != "$USER_IP" ] ); then
# NovÄ jsou definice hostĹŻ v isc-dhcp-serveru od verze 3.1.1 globĂĄlnĂ, takĹže nenĂ nutnĂŠ
# udĂĄvat je do rozsahu danĂŠho rozhranĂ, zĂĄroveĹ je tĹeba oĹĄetĹit vĂce stejnĂ˝ch mac adres
# o ty se dnes starĂĄ netadmin, kterĂ˝ by nemÄl dovolit uĹživatelĹŻm zadat stejnou mac adresu,
# to se vĹĄak v budoucnu mĹŻĹže zmÄnit!
echo " host $USER_NAME { hardware ethernet $USER_MAC; fixed-address $USER_IP; }" >> "$MACGUARD_DIR/dhcpd.conf"
# isc-dhcp-server od verze 3.1.1 obsahuje takĂŠ jednu velkou mouchu, pokud jsou fixnĂ adresy
# definovanĂ˝ch hostĹŻ v rozsahu range, tak je klidnÄ nabĂzĂ dĂĄle, existujĂ 3 moĹžnĂĄ ĹeĹĄenĂ:
# 1. sjednotit a seĹadit ip adresy, tak aby nezasahovaly do rozsahu range
# 2. pouĹžĂvat starĹĄĂ verzi isc-dhcp-serveru 3.0.4, kterĂĄ funguje sprĂĄvnÄ
# 3. generovat jeĹĄtÄ dhcpd.leases, kde nastavĂme velmi dlouhĂŠ doby pĹidÄlenĂ adres
echo "lease $USER_IP {" >> "/var/lib/dhcp/dhcpd.leases"
echo " starts $DHCP_START_DATE;" >> "/var/lib/dhcp/dhcpd.leases"
echo " ends $DHCP_END_DATE;" >> "/var/lib/dhcp/dhcpd.leases"
echo " tstp $DHCP_END_DATE;" >> "/var/lib/dhcp/dhcpd.leases"
echo " binding state active;" >> "/var/lib/dhcp/dhcpd.leases"
echo " hardware ethernet $USER_MAC;" >> "/var/lib/dhcp/dhcpd.leases"
echo "}" >> "/var/lib/dhcp/dhcpd.leases"
fi
done < "$MACGUARD_DIR/table-$DUMMY_IP.csv"
fi
echo "}" >> "$MACGUARD_DIR/dhcpd.conf"
echo "" >> "$MACGUARD_DIR/dhcpd.conf"
done
# ----------------------- konec generovĂĄnĂ dhcpd.conf ---------------------------
# doĹĄlo ke zmÄnÄ INTERFACES pro soubor /etc/default/isc-dhcp-server
if [ "$INTERFACES_NEW" == "yes" ]; then
ro_test "/etc/default/isc-dhcp-server"
if [ ! -e "/etc/default/isc-dhcp-server.no_macguard" ] && [ -e "/etc/default/isc-dhcp-server" ]; then
mv "/etc/default/isc-dhcp-server" "/etc/default/isc-dhcp-server.no_macguard"
fi
echo "# Created by firewall script for macguard" > /etc/default/isc-dhcp-server
echo "INTERFACES=\"$INTERFACES_INTERNAL\"" >> /etc/default/isc-dhcp-server
fi
# symlink na dhcp soubor neodpovĂdĂĄ souboru kam macguard uklĂĄdĂĄ dhcp data
if [ "`readlink /etc/dhcp/dhcpd.conf`" != "$MACGUARD_DIR/dhcpd.conf" ]; then
ro_test "/etc/dhcp/dhcpd.conf.old"
if [ -e "/etc/dhcp/dhcpd.conf" ]; then
mv "/etc/dhcp/dhcpd.conf" "/etc/dhcp/dhcpd.conf.old"
fi
ln -s "$MACGUARD_DIR/dhcpd.conf" "/etc/dhcp/dhcpd.conf"
fi
# isc-dhcp-server nenĂ spouĹĄtÄn po startu
if [ "`find /etc/rc* -name \"*isc-dhcp-server\"`" == "" ]; then
ro_test "/etc/rc.test"
# v novĂŠ verzi Debiana uĹž nenĂ isc-dhcp-server v rc0.d a rc6.d!
ln -s "../init.d/isc-dhcp-server" "/etc/rc1.d/K40isc-dhcp-server"
ln -s "../init.d/isc-dhcp-server" "/etc/rc2.d/S40isc-dhcp-server"
ln -s "../init.d/isc-dhcp-server" "/etc/rc3.d/S40isc-dhcp-server"
ln -s "../init.d/isc-dhcp-server" "/etc/rc4.d/S40isc-dhcp-server"
ln -s "../init.d/isc-dhcp-server" "/etc/rc5.d/S40isc-dhcp-server"
fi
# neexistuje konfigurace pro dhcp bez macguarda
if [ ! -e "/etc/dhcp/dhcpd.conf.no_macguard" ] && [ -e "$MACGUARD_DIR/dhcpd.conf" ]; then
ro_test "/etc/dhcp/dhcpd.conf.no_macguard"
cp "$MACGUARD_DIR/dhcpd.conf" "/etc/dhcp/dhcpd.conf.no_macguard"
fi
# OpÄt spustĂme dhcp server, nemÄli bychom ho spouĹĄtÄt v rc.S, pokud vĂme Ĺže
# bude dhcp server spuĹĄtÄn nĂĄslednÄ z rc.2, detekce runlevelu je vĹĄak sloĹžitĂĄ.
/etc/init.d/isc-dhcp-server start
fi
# pokud neexistuej skript pro automatickou aktualizaci macguarda, tak ho vytvoĹĂme
if [ ! -e "/etc/cron.d/macguard" ]; then
ro_test "/etc/cron.d/macguard"
echo "# Created by firewall script for macguard" > /etc/cron.d/macguard
echo "*/10 * * * * root /etc/init.d/firewall macguard_update" >> /etc/cron.d/macguard
fi
fi
# pokud jsme odemkli disk pro zĂĄpis, tak ho musĂme takĂŠ uzamknout
ro_exit
}