From 2e06f1d096f655b1533f7fc27e953ebcf921418a Mon Sep 17 00:00:00 2001 From: Daniel Golle Date: Tue, 24 Nov 2020 18:54:31 +0000 Subject: [PATCH] uqmi: use UUCP-style locking on control device Use UUCP-style locking to avoid interfering with running commands, eg. by running 'ifup wwan' while 'ifdown wwan' has not completed yet, multiple parallel instances of uqmi would occur and mess things up. Signed-off-by: Daniel Golle --- package/network/utils/uqmi/Makefile | 2 +- .../utils/uqmi/files/lib/netifd/proto/qmi.sh | 107 +++++++++++------- 2 files changed, 68 insertions(+), 41 deletions(-) diff --git a/package/network/utils/uqmi/Makefile b/package/network/utils/uqmi/Makefile index 02265d400c..e229db9048 100644 --- a/package/network/utils/uqmi/Makefile +++ b/package/network/utils/uqmi/Makefile @@ -1,7 +1,7 @@ include $(TOPDIR)/rules.mk PKG_NAME:=uqmi -PKG_RELEASE:=$(AUTORELEASE) +PKG_RELEASE:=3 PKG_SOURCE_PROTO:=git PKG_SOURCE_URL=$(PROJECT_GIT)/project/uqmi.git diff --git a/package/network/utils/uqmi/files/lib/netifd/proto/qmi.sh b/package/network/utils/uqmi/files/lib/netifd/proto/qmi.sh index c2c5fc1eca..bd895ebe6b 100755 --- a/package/network/utils/uqmi/files/lib/netifd/proto/qmi.sh +++ b/package/network/utils/uqmi/files/lib/netifd/proto/qmi.sh @@ -28,16 +28,19 @@ proto_qmi_init_config() { proto_config_add_defaults } -proto_qmi_setup() { +qmi_setup() { local interface="$1" + local device="$2" local dataformat connstat plmn_mode mcc mnc - local device apn auth username password pincode delay modes pdptype + local apn auth username password pincode delay modes pdptype local profile dhcp dhcpv6 autoconnect plmn timeout mtu $PROTO_DEFAULT_OPTIONS local ip4table ip6table local cid_4 pdh_4 cid_6 pdh_6 local ip_6 ip_prefix_length gateway_6 dns1_6 dns2_6 - json_get_vars device apn auth username password pincode delay modes + flock -x 1000 || return -1000 + + json_get_vars apn auth username password pincode delay modes json_get_vars pdptype profile dhcp dhcpv6 autoconnect plmn ip4table json_get_vars ip6table timeout mtu $PROTO_DEFAULT_OPTIONS @@ -45,35 +48,8 @@ proto_qmi_setup() { [ "$metric" = "" ] && metric="0" - [ -n "$ctl_device" ] && device=$ctl_device - - [ -n "$device" ] || { - echo "No control device specified" - proto_notify_error "$interface" NO_DEVICE - proto_set_available "$interface" 0 - return 1 - } - [ -n "$delay" ] && sleep "$delay" - device="$(readlink -f $device)" - [ -c "$device" ] || { - echo "The specified control device does not exist" - proto_notify_error "$interface" NO_DEVICE - proto_set_available "$interface" 0 - return 1 - } - - devname="$(basename "$device")" - devpath="$(readlink -f /sys/class/usbmisc/$devname/device/)" - ifname="$( ls "$devpath"/net )" - [ -n "$ifname" ] || { - echo "The interface could not be found." - proto_notify_error "$interface" NO_IFACE - proto_set_available "$interface" 0 - return 1 - } - [ -n "$mtu" ] && { echo "Setting MTU to $mtu" /sbin/ip link set dev $ifname mtu $mtu @@ -432,9 +408,50 @@ proto_qmi_setup() { } } +proto_qmi_setup() { + local device lock ret + json_get_vars device + + [ -n "$ctl_device" ] && device=$ctl_device + + [ -n "$device" ] || { + echo "No control device specified" + proto_notify_error "$interface" NO_DEVICE + proto_set_available "$interface" 0 + return 1 + } + + device="$(readlink -f $device)" + [ -c "$device" ] || { + echo "The specified control device does not exist" + proto_notify_error "$interface" NO_DEVICE + proto_set_available "$interface" 0 + return 1 + } + + devname="$(basename "$device")" + devpath="$(readlink -f /sys/class/usbmisc/$devname/device/)" + ifname="$( ls "$devpath"/net )" + [ -n "$ifname" ] || { + echo "The interface could not be found." + proto_notify_error "$interface" NO_IFACE + proto_set_available "$interface" 0 + return 1 + } + lock="/var/lock/..LCK.$(basename "$device")" + { + qmi_setup "$1" "$device" + } 1000>"$lock" + ret=$? + [ "$ret" != "-1000" ] && rm "$lock" + echo "exited with code $ret" + return $ret +} + qmi_wds_stop() { - local cid="$1" - local pdh="$2" + local device="$1" + local cid="$2" + local pdh="$3" [ -n "$cid" ] || return @@ -451,23 +468,33 @@ qmi_wds_stop() { --release-client-id wds > /dev/null 2>&1 } +qmi_wds_stop_all() { + local device="$1" + flock -x 1000 || return -1000 + json_load "$(ubus call network.interface.$interface status)" + json_select data + json_get_vars cid_4 pdh_4 cid_6 pdh_6 + qmi_wds_stop "$device" "$cid_4" "$pdh_4" + qmi_wds_stop "$device" "$cid_6" "$pdh_6" +} + proto_qmi_teardown() { local interface="$1" - local device cid_4 pdh_4 cid_6 pdh_6 + local device lock cid_4 pdh_4 cid_6 pdh_6 json_get_vars device [ -n "$ctl_device" ] && device=$ctl_device - echo "Stopping network $interface" - - json_load "$(ubus call network.interface.$interface status)" - json_select data - json_get_vars cid_4 pdh_4 cid_6 pdh_6 + device="$(readlink -f $device)" - qmi_wds_stop "$cid_4" "$pdh_4" - qmi_wds_stop "$cid_6" "$pdh_6" + echo "Stopping network $interface" + lock="/var/lock/..LCK.$(basename "$device")" + { + qmi_wds_stop_all "$device" + } 1000>"$lock" + [ "$?" != "-1000" ] && rm "$lock" proto_init_update "*" 0 proto_send_update "$interface" } -- 2.30.2