Skip to content

Instantly share code, notes, and snippets.

@ilyaevseev
Created January 21, 2016 05:09
Show Gist options
  • Save ilyaevseev/c24adcc3721b0b30511a to your computer and use it in GitHub Desktop.
Save ilyaevseev/c24adcc3721b0b30511a to your computer and use it in GitHub Desktop.
Xen vSwitch configuration sample.
#!/bin/sh
IP="/sbin/ip"
EXT_IFACE="$($IP route get 8.8.8.8 | grep ' src ' | sed -e 's,.* dev ,,' -e 's, .*,,')"
EXT_IPADDR="$($IP addr ls dev $EXT_IFACE | grep ' inet ' | sed -e 's,.* inet ,,' -e 's,/.*,,')"
# Default filter policy..
iptables -P INPUT ACCEPT
iptables -P OUTPUT ACCEPT
iptables -P FORWARD ACCEPT
# Cleanup current state..
iptables -F # ..flush all filtering chains
iptables -X # ..remove all user-defined filtering chains
iptables -F -t nat # ..the same for NAT
iptables -X -t nat
iptables -N INPUT_FROM_INET
iptables -A INPUT_FROM_INET -p icmp -j ACCEPT
iptables -A INPUT_FROM_INET -m state --state RELATED,ESTABLISHED -j ACCEPT
iptables -A INPUT_FROM_INET -m state --state NEW -p tcp --dport 22 -j ACCEPT
iptables -A INPUT_FROM_INET -m state --state NEW -p tcp --dport 443 -j ACCEPT
iptables -A INPUT_FROM_INET -j DROP
iptables -A INPUT -s "194.107.17.23" -j ACCEPT # ..backup asshole
iptables -A INPUT -i "$EXT_IFACE" -j INPUT_FROM_INET
iptables -t nat -A POSTROUTING -o "$EXT_IFACE" -j SNAT --to-source "$EXT_IPADDR"
## END ##
#!/bin/bash
#
# /etc/xapi.d/vif-hotplug
#
# Configure Xen Dom0 networking.
#
# HN => Networking => Properties => Custom Fields:
# - ISOLATED_LAN = any non-empty value, prevents direct guest-guest interactions
# - DOM0_IPADDRS = space-separated ip/mask list
#
# Based on http://code.metager.de/source/xref/citrix/xenserver/xs/cim/overlay/etc/xapi.d/vif-hotplug
# Written by ilya.evseev@gmail at Dec-2013
# (see also: http://hantim.ru/jobs/28262-nastroit-set-na-xenserver-6-2)
#
DEBUG_DIR="/var/log/vif-hotplug" # uncomment for debugging!
IP="/sbin/ip"
OFCTL="/usr/bin/ovs-ofctl"
BRCTL="/usr/sbin/brctl"
IPTABLES="/sbin/iptables"
IPTABLES_SAVE="/sbin/iptables-save"
EBTABLES="/sbin/ebtables"
EBTABLES_SAVE="/sbin/ebtables-save"
### DHCP settings..
DNSMASQ_CONFDIR="/etc/dnsmasq.d" # ..assign to non-existing for skip!
DHCP_FIRST="130"
DHCP_LAST="189"
logger -t "vif-hotplug" -- "cmdline: $*"
Warn() { logger -t "vif-hotplug" -p "user.warn" -- "$@"; }
Fail() { logger -t "vif-hotplug" -p "user.err" -- "$@"; exit 1; }
bridge_used_by_others() { "$BRCTL" show | grep -wA1 -- "^$bridge_name" | grep -qP -- '^\s' && return 0; return 1; }
dnsmasq_reload() { /sbin/service "dnsmasq" restart; }
initialize_ipaddrs() {
do_dhcp=
for a in $dom0_ipaddrs; do
$IP addr list dev "$bridge_name" | grep -q -- "inet ${a} " && continue
$IP addr add "$a" dev "$bridge_name" || Warn "Wrong IP ${a} on ${bridge_name}."
do_dhcp="1"
done
test -n "$do_dhcp" || return
test -d "$DNSMASQ_CONFDIR" || return
f="$DNSMASQ_CONFDIR/$bridge_name.conf"
test -f "$f" && return # ..do not overwrite existing!
echo "interface=$bridge_name" > "$f"
for a in $dom0_ipaddrs; do
echo "dhcp-range=${a%.*/*}.$DHCP_FIRST,${a%.*/*}.$DHCP_LAST" >> "$f"
done
dnsmasq_reload
}
cleanup_ipaddrs() {
bridge_used_by_others && return
f="$DNSMASQ_CONFDIR/$bridge_name.conf"
test -f "$f" && rm "$f" && dnsmasq_reload
}
isolate_on_openvswitch() {
port_info="$(ovs-ofctl dump-ports $bridge_name $vif_name)"
port_num="$(echo $port_info | sed -n '/port [0-9]/s/.* \([0-9][0-9]*\).*/\1/p')"
$OFCTL add-flow "$bridge_name" "priority=60000 dl_type=0x0806 action=normal" # ..ARP
$OFCTL add-flow "$bridge_name" "dl_src=$bridge_mac dl_dst=$vif_mac action=output:$port_num"
$OFCTL add-flow "$bridge_name" "dl_src=$vif_mac dl_dst=$bridge_mac action=LOCAL"
$OFCTL add-flow "$bridge_name" "dl_dst=$broadcast_mac action=LOCAL"
$OFCTL add-flow "$bridge_name" "priority=0,actions=drop"
}
cleanup_openvswitch() {
$OFCTL del-flows "$bridge_name" "dl_dst=$vif_mac"
$OFCTL del-flows "$bridge_name" "dl_src=$vif_mac"
}
isolate_lan() {
$IPTABLES_SAVE | grep -- "^-A FORWARD -i $bridge_name -o $bridge_name -j DROP $" ||
$IPTABLES -I "FORWARD" -i "$bridge_name" -o "$bridge_name" -j "DROP"
case "$backend" in
openvswitch ) isolate_on_openvswitch ;;
bridge ) $EBTABLES_SAVE | grep -q -- "^-A FORWARD --logical-in $bridge_name -j DROP$" ||
$EBTABLES -I "FORWARD" --logical-in "$bridge_name" -j "DROP"
;;
*) Warn "Unknown backend $backend" ;;
esac
}
cleanup_isolation() {
bridge_used_by_others || $IPTABLES -D "FORWARD" -i "$bridge_name" -o "$bridge_name" -j "DROP"
case "$backend" in
openvswitch ) cleanup_openvswitch ;;
bridge ) bridge_used_by_others ||
$EBTABLES -D "FORWARD" --logical-in "$bridge_name" -j "DROP"
;;
*) Warn "Unknown backend $backend" ;;
esac
}
main() {
test $# = 6 || exit 1
action="$2"
vif_uuid="$4"
vm_uuid="$6"
broadcast_mac="FF:FF:FF:FF:FF:FF"
backend="$(cat /etc/xensource/network.conf)"
network_uuid="$(xe vif-param-get uuid=$vif_uuid param-name=network-uuid)"
device_id="$(xe vif-param-get uuid=$vif_uuid param-name=device)"
vif_mac="$(xe vif-param-get uuid=$vif_uuid param-name=MAC)"
while : ; do
dom_id="$(xe vm-param-get uuid=$vm_uuid param-name=dom-id)"
test "$dom_id" -gt "-1" && break
sleep 1
done
vif_name="vif${dom_id}.${device_id}"
isolated_lan="$(xe network-param-get uuid=$network_uuid param-name=other-config param-key=XenCenter.CustomFields.ISOLATED_LAN 2>/dev/null)"
dom0_ipaddrs="$(xe network-param-get uuid=$network_uuid param-name=other-config param-key=XenCenter.CustomFields.DOM0_IPADDRS 2>/dev/null)"
bridge_name="$(xe network-param-get uuid=$network_uuid param-name=bridge)"
bridge_mac="$($IP link ls dev $bridge_name | awk '/link\/ether/ {print $2}')"
test -n "$bridge_name" || Fail "Cannot detect bridge name for vif=${vif_uuid}, net=${network_uuid}."
test -n "$bridge_mac" || Fail "Cannot detect MAC for bridge ${bridge_name}."
case "$action" in
"online" ) initialize_ipaddrs ; test -n "$isolated_lan" && isolate_lan ;;
"remove" ) cleanup_ipaddrs ; test -n "$isolated_lan" && cleanup_isolation ;;
esac
}
if test -z "$DEBUG_DIR"; then
main "$@"
elif mkdir -p "$DEBUG_DIR"; then
( set -x; main "$@" ) >> "$DEBUG_DIR/vif-hotplug-$(LANG=C date +%Y%m%d_%H%M%S).log" 2>&1
else
Fail "Cannot create $DEBUG_DIR"
fi
## END ##
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment