1#!/usr/bin/env python3 2# 3# Copyright 2017 - Google, Inc. 4# 5# Licensed under the Apache License, Version 2.0 (the "License"); 6# you may not use this file except in compliance with the License. 7# You may obtain a copy of the License at 8# 9# http://www.apache.org/licenses/LICENSE-2.0 10# 11# Unless required by applicable law or agreed to in writing, software 12# distributed under the License is distributed on an "AS IS" BASIS, 13# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14# See the License for the specific language governing permissions and 15# limitations under the License. 16 17import logging 18import time 19from acts.libs.proc import job 20 21_BRCTL = 'brctl' 22BRIDGE_NAME = 'br-lan' 23CREATE_BRIDGE = '%s addbr %s' % (_BRCTL, BRIDGE_NAME) 24DELETE_BRIDGE = '%s delbr %s' % (_BRCTL, BRIDGE_NAME) 25BRING_DOWN_BRIDGE = 'ifconfig %s down' % BRIDGE_NAME 26 27 28class BridgeInterfaceConfigs(object): 29 """Configs needed for creating bridge interface between LAN and WLAN. 30 31 """ 32 33 def __init__(self, iface_wlan, iface_lan, bridge_ip): 34 """Set bridge interface configs based on the channel info. 35 36 Args: 37 iface_wlan: the wlan interface as part of the bridge 38 iface_lan: the ethernet LAN interface as part of the bridge 39 bridge_ip: the ip address assigned to the bridge interface 40 """ 41 self.iface_wlan = iface_wlan 42 self.iface_lan = iface_lan 43 self.bridge_ip = bridge_ip 44 45 46class BridgeInterface(object): 47 """Class object for bridge interface betwen WLAN and LAN 48 49 """ 50 def __init__(self, ap): 51 """Initialize the BridgeInterface class. 52 53 Bridge interface will be added between ethernet LAN port and WLAN port. 54 Args: 55 ap: AP object within ACTS 56 """ 57 self.ssh = ap.ssh 58 59 def startup(self, brconfigs): 60 """Start up the bridge interface. 61 62 Args: 63 brconfigs: the bridge interface config, type BridgeInterfaceConfigs 64 """ 65 66 logging.info('Create bridge interface between LAN and WLAN') 67 # Create the bridge 68 try: 69 self.ssh.run(CREATE_BRIDGE) 70 except job.Error: 71 logging.warning( 72 'Bridge interface {} already exists, no action needed'.format( 73 BRIDGE_NAME)) 74 75 # Enable 4addr mode on for the wlan interface 76 ENABLE_4ADDR = 'iw dev %s set 4addr on' % (brconfigs.iface_wlan) 77 try: 78 self.ssh.run(ENABLE_4ADDR) 79 except job.Error: 80 logging.warning('4addr is already enabled on {}'.format( 81 brconfigs.iface_wlan)) 82 83 # Add both LAN and WLAN interfaces to the bridge interface 84 for interface in [brconfigs.iface_lan, brconfigs.iface_wlan]: 85 ADD_INTERFACE = '%s addif %s %s' % (_BRCTL, BRIDGE_NAME, interface) 86 try: 87 self.ssh.run(ADD_INTERFACE) 88 except job.Error: 89 logging.warning('{} has alrady been added to {}'.format( 90 interface, BRIDGE_NAME)) 91 time.sleep(5) 92 93 # Set IP address on the bridge interface to bring it up 94 SET_BRIDGE_IP = 'ifconfig %s %s' % (BRIDGE_NAME, brconfigs.bridge_ip) 95 self.ssh.run(SET_BRIDGE_IP) 96 time.sleep(2) 97 98 # Bridge interface is up 99 logging.info('Bridge interface is up and running') 100 101 def teardown(self, brconfigs): 102 """Tear down the bridge interface. 103 104 Args: 105 brconfigs: the bridge interface config, type BridgeInterfaceConfigs 106 """ 107 logging.info('Bringing down the bridge interface') 108 # Delete the bridge interface 109 self.ssh.run(BRING_DOWN_BRIDGE) 110 time.sleep(1) 111 self.ssh.run(DELETE_BRIDGE) 112 113 # Bring down wlan interface and disable 4addr mode 114 BRING_DOWN_WLAN = 'ifconfig %s down' % brconfigs.iface_wlan 115 self.ssh.run(BRING_DOWN_WLAN) 116 time.sleep(2) 117 DISABLE_4ADDR = 'iw dev %s set 4addr off' % (brconfigs.iface_wlan) 118 self.ssh.run(DISABLE_4ADDR) 119 time.sleep(1) 120 logging.info('Bridge interface is down') 121