]> CyberLeo.Net >> Repos - FreeBSD/releng/9.2.git/blob - share/examples/netgraph/ether.bridge
- Copy stable/9 to releng/9.2 as part of the 9.2-RELEASE cycle.
[FreeBSD/releng/9.2.git] / share / examples / netgraph / ether.bridge
1 #!/bin/sh
2 # $FreeBSD$
3 # This script sets up an Ethernet bridging network across multiple
4 # Ethernet interfaces using the ng_bridge(4) and ng_ether(4) netgraph
5 # node types.
6 #
7 # To use this script:
8 #
9 # 0. Make your own copy of this example script.
10 #
11 # 1. Give your bridging network a name by editing the definition of
12 #    ${BRIDGE_NAME} below. It must be a valid netgraph node name.
13 #
14 # 2. Edit the definitions of ${BRIDGE_IFACES} and ${LOCAL_IFACES}
15 #    as described below to define your bridging interfaces.
16 #
17 # 3. Run this script with "start" as the command line argument.
18 #
19 # 4. Examine bridging statistics by running this script with "stats"
20 #    as the command line argument.
21 #
22 # 5. Stop bridging by running this script with "stop" as the
23 #    command line argument.
24 #
25 # To run multiple independent bridging networks, create multiple
26 # copies of this script with different variable definitions.
27 #
28 # To make a "brouted" network, with IP being routed and other protocols being
29 # bridged, add all the interface in the BRIDGE_IFACES to the LOCAL_IFACES.
30 # If you just want a normal bridge, just one will be enough.
31 # In some cases you may want some combination.
32 #
33
34 # Give each bridging network a unique name here.
35
36 BRIDGE_NAME="bnet0"
37
38 # List the names of the interfaces that you want to bridge across
39 # here in ${BRIDGE_IFACES}. If you want to include the local host
40 # machine as well then set ${LOCAL_IFACES} as well (they may also be
41 # listed in ${BRIDGE_IFACES}). Of course, any ${LOCAL_IFACE} must
42 # be ifconfig(8)ured separately. If you don't want a ${LOCAL_IFACE}
43 # then assign it the empty string.
44
45 BRIDGE_IFACES="de0 fxp0 fxp1"
46 LOCAL_IFACES="fxp0 fxp1"
47
48 #####################################################################
49 #### Everything below this point should not need to be modified. ####
50 #####################################################################
51
52 # Routine to verify node's existence.
53 bridge_verify() {
54         ngctl info ${BRIDGE_NAME}: >/dev/null 2>&1
55         if [ $? -ne 0 ]; then
56                 echo "${BRIDGE_NAME}: bridge network not found"
57                 exit 1
58         fi
59 }
60
61 # Routine to get and display link stats.
62 bridge_linkstats() {
63         STATS=`ngctl msg ${BRIDGE_NAME}: getstats $1`
64         if [ $? -ne 0 ]; then
65                 exit 1
66         fi
67         echo "${STATS}" | fmt 2 | awk '/=/ { fl=index($0, "="); \
68             printf "%20s = %s\n", substr($0, 0, fl - 1), substr($0, fl + 1); }'
69 }
70
71 # Start/restart routine.
72 bridge_start() {
73
74         # Load netgraph KLD's as necessary.
75         for KLD in ng_ether ng_bridge; do
76                 if ! kldstat -v | grep -qw ${KLD}; then
77                         echo -n "Loading ${KLD}.ko... "
78                         kldload ${KLD} || exit 1
79                         echo "done"
80                 fi
81         done
82
83         # Reset all interfaces.
84         bridge_stop
85
86         # Verify all interfaces exist.
87         for ETHER in ${BRIDGE_IFACES} ${LOCAL_IFACES}; do
88                 if ! ngctl info ${ETHER}: >/dev/null 2>&1; then
89                         echo "Error: interface ${ETHER} does not exist"
90                         exit 1
91                 fi
92                 ifconfig ${ETHER} up || exit 1
93         done
94
95         # Create new ng_bridge(4) node, attached to the first interface.
96         FIRSTIF=`echo ${BRIDGE_IFACES} | awk '{ print $1 }'`
97         ngctl mkpeer ${FIRSTIF}: bridge lower link0 || exit 1
98         ngctl name ${FIRSTIF}:lower ${BRIDGE_NAME} || exit 1
99
100         # Attach other interfaces as well.
101         LINKNUM=0
102         for ETHER in ${BRIDGE_IFACES}; do
103                 if [ ${LINKNUM} != 0 ]; then
104                         ngctl connect ${ETHER}: ${BRIDGE_NAME}: \
105                             lower link${LINKNUM} || exit 1
106                 fi
107                 LINKNUM=`expr ${LINKNUM} + 1`
108         done
109
110         # Hook up local interface, if any.
111         for LOCAL_IFACE in ${LOCAL_IFACES}; do
112                 ngctl connect ${LOCAL_IFACE}: ${BRIDGE_NAME}: \
113                     upper link${LINKNUM} || exit 1
114                 LINKNUM=`expr ${LINKNUM} + 1`
115         done
116
117         # Set all interfaces in promiscuous mode and don't overwrite src addr.
118         for ETHER in ${BRIDGE_IFACES}; do
119                 ngctl msg ${ETHER}: setpromisc 1 || exit 1
120                 ngctl msg ${ETHER}: setautosrc 0 || exit 1
121         done
122 }
123
124 # Stop routine.
125 bridge_stop() {
126         ngctl kill ${BRIDGE_NAME}: >/dev/null 2>&1
127         for ETHER in ${BRIDGE_IFACES} ${LOCAL_IFACES}; do
128                 ngctl kill ${ETHER}: >/dev/null 2>&1
129         done
130 }
131
132 # Stats routine.
133 bridge_stats() {
134
135         # Make sure node exists.
136         bridge_verify
137
138         echo ""
139         echo "Statistics for bridging network ${BRIDGE_NAME}:"
140         echo ""
141         LINKNUM=0
142         for ETHER in ${BRIDGE_IFACES}; do
143                 echo "Network interface ${ETHER}:"
144                 bridge_linkstats ${LINKNUM}
145                 LINKNUM=`expr ${LINKNUM} + 1`
146         done
147         for LOCAL_IFACE in ${LOCAL_IFACES}; do
148                 echo "Local host interface ${LOCAL_IFACE}:"
149                 bridge_linkstats ${LINKNUM}
150                 LINKNUM=`expr ${LINKNUM} + 1`
151         done
152 }
153
154 # Main entry point.
155 case $1 in
156         start)
157                 bridge_start
158                 ;;
159         stats)
160                 bridge_verify
161                 bridge_stats
162                 ;;
163         stop)
164                 bridge_verify
165                 bridge_stop
166                 ;;
167         *)
168                 echo "usage: $0 [ start | stop | stats ]"
169                 exit 1
170 esac