1#!/bin/sh 2# 3# 4# Copyright (C) 2014 The Android Open Source Project 5# 6# Licensed under the Apache License, Version 2.0 (the "License"); 7# you may not use this file except in compliance with the License. 8# You may obtain a copy of the License at 9# 10# http://www.apache.org/licenses/LICENSE-2.0 11# 12# Unless required by applicable law or agreed to in writing, software 13# distributed under the License is distributed on an "AS IS" BASIS, 14# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 15# See the License for the specific language governing permissions and 16# limitations under the License. 17# 18# 19# UDEV event helper script that restarts a hung network device. 20 21POWER_DOWN_TIME_SECONDS=1 22WLAN_POWER_UP_TIME_SECONDS=1 23WLAN_REINITIALIZE_TIME_SECONDS=5 24 25set -e 26 27error () { 28 logger -t $0 "Error: $1" 29 exit 1 30} 31 32if [ -n "${1}" ] ; then 33 eval $(udevadm info --query=property --path="/sys/class/net/${1}" | 34 egrep '^(DEVPATH|DEVTYPE|ID_BUS|INTERFACE|SUBSYSTEM)') 35 EVENT=device_hang 36fi 37 38if [ "${SUBSYSTEM}" != "net" -o \ 39 "${EVENT}" != "device_hang" -o \ 40 -z "${DEVPATH}" ] ; then 41 exit 0 42fi 43 44logger -t $0 "Restarting network interface ${INTERFACE}" 45 46# The DEVPATH for a network interface should look something like: 47# /devices/pci0000:00/0000:00:1c.0/0000:01:00.0/net/wlan0 48if [ $(basename $(dirname "${DEVPATH}")) != 'net' ] ; then 49 error "Device path for ${INTERFACE} (${DEVPATH}) is invalid." 50fi 51 52device_path=$(readlink -f "/sys${DEVPATH}/../..") 53module_name=$(basename $(readlink -f "/sys${DEVPATH}/device/driver/module")) 54 55rmmod "${module_name}" 56 57if [ "${ID_BUS}" = "pci" ] ; then 58 device_remove_path="${device_path}/remove" 59 bus_rescan_path=$(readlink -f "${device_path}/../rescan") 60 61 if [ ! -e "${device_remove_path}" ] ; then 62 error "Device remove path ${device_remove_path} does not exist" 63 fi 64 65 if [ ! -e "${bus_rescan_path}" ] ; then 66 error "Bus rescan path ${bus_rescan_path} does not exist" 67 fi 68 69 echo 1 > "${device_remove_path}" 70 if [ "${DEVTYPE}" = "wlan" ] ; then 71 ectool wireless 0xe # Disable wireless lan. 72 ectool wireless 0x6 # Power down wireless lan. 73 fi 74 75 sleep ${POWER_DOWN_TIME_SECONDS} 76 77 if [ "${DEVTYPE}" = "wlan" ] ; then 78 ectool wireless 0xe # Power up wireless lan. 79 sleep ${WLAN_POWER_UP_TIME_SECONDS} 80 ectool wireless 0xf # Enable wireless lan. 81 82 sleep ${WLAN_REINITIALIZE_TIME_SECONDS} 83 fi 84 85 echo 1 > "${bus_rescan_path}" 86elif [ "${ID_BUS}" = "usb" ] ; then 87 device_authorize_path=$(readlink -f "${device_path}/../authorized") 88 echo 0 > "${device_authorize_path}" 89 sleep ${POWER_DOWN_TIME_SECONDS} 90 echo 1 > "${device_authorize_path}" 91else 92 error "Bus type ${ID_BUS} is unknown" 93fi 94