963 lines
24 KiB
Bash
Executable File
963 lines
24 KiB
Bash
Executable File
#!/bin/sh
|
||
# Copyright (C) 2023 Siriling <siriling@qq.com>
|
||
|
||
#脚本目录
|
||
SCRIPT_DIR="/usr/share/modem"
|
||
|
||
#运行目录
|
||
MODEM_RUNDIR="/var/run/modem"
|
||
MODEM_PID_FILE="${MODEM_RUNDIR}/modem.pid"
|
||
MODEM_CDC_WDM_CACHE="${MODEM_RUNDIR}/cdc_wdm.cache"
|
||
MODEM_PHYSICAL_DEVICE_CACHE="${MODEM_RUNDIR}/physical_device.cache"
|
||
MODEM_EVENTS_CACHE="${MODEM_RUNDIR}/events.cache"
|
||
|
||
#导入组件工具
|
||
source "/lib/functions.sh"
|
||
source "/lib/netifd/netifd-proto.sh"
|
||
source "${SCRIPT_DIR}/modem_debug.sh"
|
||
|
||
#日志
|
||
# $1:日志等级
|
||
m_log()
|
||
{
|
||
local level="$1";
|
||
logger -p "daemon.${level}" -t "Modem[$$]" "hotplug: $*"
|
||
}
|
||
|
||
#生成16进制数
|
||
generate_hex() {
|
||
echo "$(openssl rand -hex 1)"
|
||
}
|
||
|
||
#生成随机MAC地址
|
||
generate_mac_address() {
|
||
local mac=""
|
||
for i in $(seq 1 6); do
|
||
mac="${mac}$(generate_hex)"
|
||
if [[ $i != 6 ]]; then
|
||
mac="${mac}:"
|
||
fi
|
||
done
|
||
echo "$mac"
|
||
}
|
||
|
||
#上报USB事件
|
||
# $1:事件行为(add,remove,bind)
|
||
# $2:类型
|
||
# $3:名称或设备ID
|
||
# $4:路径
|
||
m_report_event()
|
||
{
|
||
local action="$1"
|
||
local type="$2"
|
||
local name="$3"
|
||
local physical_path="$4"
|
||
|
||
#缓存事件信息
|
||
echo "${action},${type},${name},${physical_path}" >> "${MODEM_EVENTS_CACHE}"
|
||
#输出事件处理日志
|
||
m_log "debug" "event reported: action=${action}, type=${type}, name=${name}"
|
||
}
|
||
|
||
#模组预设
|
||
# $1:AT串口
|
||
# $2:连接定义
|
||
# $3:制造商
|
||
m_modem_presets()
|
||
{
|
||
local at_port="$1"
|
||
local define_connect="$2"
|
||
local manufacturer="$3"
|
||
|
||
#运营商选择设置
|
||
local at_command='AT+COPS=0,0'
|
||
at "${at_port}" "${at_command}"
|
||
|
||
#PDP设置
|
||
at_command="AT+CGDCONT=${define_connect},\"IPV4V6\",\"\""
|
||
at "${at_port}" "${at_command}"
|
||
|
||
#制造商私有预设
|
||
case $manufacturer in
|
||
"quectel") quectel_presets ;;
|
||
"fibocom") fibocom_presets ;;
|
||
"meig") meig_presets ;;
|
||
"simcom") simcom_presets ;;
|
||
"huawei") huawei_presets ;;
|
||
"tdtech") tdtech_presets ;;
|
||
esac
|
||
}
|
||
|
||
#获取设备物理路径
|
||
# $1:网络设备路径
|
||
m_get_device_physical_path()
|
||
{
|
||
local tmp_path="$1"
|
||
|
||
while true; do
|
||
tmp_path=$(dirname "${tmp_path}")
|
||
|
||
#跳出循环条件
|
||
[ -z "${tmp_path}" ] || [ "${tmp_path}" = "/" ] && return
|
||
|
||
#USB设备
|
||
[ -f "${tmp_path}"/idVendor ] && [ -f "${tmp_path}"/idProduct ] && {
|
||
tmp_path=$(readlink -f "$tmp_path")
|
||
echo "${tmp_path}"
|
||
return
|
||
}
|
||
|
||
#PCIE设备
|
||
[ -f "${tmp_path}"/vendor ] && [ -f "${tmp_path}"/device ] && {
|
||
tmp_path=$(readlink -f "$tmp_path")
|
||
echo "${tmp_path}"
|
||
return
|
||
}
|
||
done
|
||
}
|
||
|
||
#删除物理路径状态
|
||
# $1:设备物理路径
|
||
m_del_physical_path_status()
|
||
{
|
||
# local network="$1"
|
||
local physical_path="$1"
|
||
|
||
#删除网络设备
|
||
# [ -f "${MODEM_PHYSICAL_DEVICE_CACHE}" ] && {
|
||
# #删除
|
||
# sed -i "/${network}/d" "${MODEM_PHYSICAL_DEVICE_CACHE}"
|
||
# }
|
||
|
||
#通过物理路径删除
|
||
local escaped_physical_path
|
||
[ -f "${MODEM_PHYSICAL_DEVICE_CACHE}" ] && {
|
||
# escape '/', '\' and '&' for sed...
|
||
escaped_physical_path=$(echo "$physical_path" | sed -e 's/[\/&]/\\&/g')
|
||
#删除
|
||
sed -i "/${escaped_physical_path}/d" "${MODEM_PHYSICAL_DEVICE_CACHE}"
|
||
}
|
||
}
|
||
|
||
#获取设备物理路径状态
|
||
# $1:设备物理路径
|
||
m_get_physical_path_status()
|
||
{
|
||
local physical_path="$1"
|
||
|
||
[ -f "${MODEM_PHYSICAL_DEVICE_CACHE}" ] || return
|
||
|
||
#获取状态(不包含注释并且包含physical_path的行,获取以,分割的第二个字符串)
|
||
awk -v physical_path="${physical_path}" -F',' '!/^#/ && $0 ~ physical_path { print $2 }' "${MODEM_PHYSICAL_DEVICE_CACHE}"
|
||
}
|
||
|
||
#设置设备物理路径状态
|
||
# $1:设备物理路径
|
||
# $2:状态
|
||
m_set_physical_path_status()
|
||
{
|
||
local physical_path="$1"
|
||
local status="$2"
|
||
|
||
#删除物理路径状态
|
||
m_del_physical_path_status "${physical_path}"
|
||
|
||
#缓存物理路径状态
|
||
echo "${physical_path},${status}" >> "${MODEM_PHYSICAL_DEVICE_CACHE}"
|
||
}
|
||
|
||
#缓存cdc-wdm
|
||
# $1:网络设备
|
||
m_cdc_wdm_cache()
|
||
{
|
||
local network="$1"
|
||
|
||
#获取cdc-wdm
|
||
local cdc_wdm=$(ls "/sys/class/net/${network}/device/usbmisc/")
|
||
[ -z "${cdc_wdm}" ] && return
|
||
|
||
#缓存
|
||
echo "${network},${cdc_wdm}" >> "${MODEM_CDC_WDM_CACHE}"
|
||
|
||
echo "${cdc_wdm}"
|
||
}
|
||
|
||
#取消缓存cdc-wdm
|
||
# $1:网络设备
|
||
m_cdc_wdm_del_cache()
|
||
{
|
||
local wwan="$1"
|
||
|
||
[ -f "${MODEM_CDC_WDM_CACHE}" ] || return
|
||
|
||
#获取cdc-wdm(不包含注释并且包含network的行,获取以,分割的第二个字符串)
|
||
local cdc_wdm=$(awk -v network="${network}" -F',' '!/^#/ && $0 ~ network { print $2 }' "${MODEM_CDC_WDM_CACHE}")
|
||
[ -n "${cdc_wdm}" ] || return
|
||
|
||
#取消缓存
|
||
sed -i "/${network},${cdc_wdm}/d" "${MODEM_CDC_WDM_CACHE}"
|
||
|
||
echo "${cdc_wdm}"
|
||
}
|
||
|
||
#cdc-wdm处理
|
||
# $1:事件行为(add,remove,bind)
|
||
# $2:名称
|
||
# $3:路径
|
||
m_cdc_wdm()
|
||
{
|
||
local action="$1"
|
||
local name="$2"
|
||
local physical_path="$4"
|
||
|
||
#获取cdc-wdm
|
||
local cdc_wdm=""
|
||
#操作缓存
|
||
case "${action}" in
|
||
"add") cdc_wdm=$(m_cdc_wdm_cache "${name}") ;;
|
||
"remove") cdc_wdm=$(m_cdc_wdm_del_cache "${name}") ;;
|
||
esac
|
||
|
||
if [ -n "${cdc_wdm}" ]; then
|
||
#输出cdc-wdm事件处理日志
|
||
m_log "${action} cdc interface ${cdc_wdm}: cdc-wdm event processed"
|
||
#上报cdc-wdm事件
|
||
m_report_event "${action}" "usbmisc" "${cdc_wdm}" "/sys${physical_path}"
|
||
fi
|
||
}
|
||
|
||
#添加USB模组ID
|
||
# $1:制造商ID
|
||
# $2:产品ID
|
||
m_add_usb_id()
|
||
{
|
||
local manufacturer_id="$1"
|
||
local product_id="$2"
|
||
|
||
local new_id_path="/sys/bus/usb-serial/drivers/generic/new_id"
|
||
|
||
#如果已经添加则返回
|
||
grep -q "${manufacturer_id} ${product_id}" "${new_id_path}" && return
|
||
|
||
while true; do
|
||
if [ -f "$new_id_path" ]; then
|
||
#添加ID
|
||
echo "${manufacturer_id} ${product_id}" >> "${new_id_path}"
|
||
break
|
||
fi
|
||
sleep 5s
|
||
done
|
||
}
|
||
|
||
#设置模组硬件配置
|
||
# $1:物理路径
|
||
m_set_modem_hardware_config()
|
||
{
|
||
local physical_path="$1"
|
||
|
||
#获取设备数据接口
|
||
local data_interface
|
||
if [[ "$physical_path" = *"usb"* ]]; then
|
||
data_interface="usb"
|
||
else
|
||
data_interface="pcie"
|
||
fi
|
||
|
||
# [ "$data_interface" = "usb" ] && {
|
||
# #不存在网络接口
|
||
# local net_count="$(find ${physical_path} -name net | wc -l)"
|
||
# if [ "$net_count" -le "0" ]; then
|
||
# #撤销
|
||
# uci revert modem
|
||
# return
|
||
# fi
|
||
# }
|
||
|
||
#是否是第一次添加(初始化模组)
|
||
local count=$(grep -o "processed" ${MODEM_PHYSICAL_DEVICE_CACHE} | wc -l)
|
||
#是否开启手动配置
|
||
local manual_configuration=$(uci -q get modem.@global[0].manual_configuration)
|
||
[ "$count" = "0" ] && [ "$manual_configuration" = "0" ] && {
|
||
#模组配置初始化
|
||
sh "${SCRIPT_DIR}/modem_init.sh"
|
||
}
|
||
|
||
#设置物理路径状态
|
||
m_set_physical_path_status "${physical_path}" "processed"
|
||
|
||
#获取模组序号
|
||
local modem_no=$(uci -q get modem.@global[0].modem_number)
|
||
#增加模组计数
|
||
local modem_number=$((modem_no + 1))
|
||
uci set modem.@global[0].modem_number="${modem_number}"
|
||
|
||
#设置模组硬件配置
|
||
uci set modem.modem${modem_no}="modem-device"
|
||
uci set modem.modem${modem_no}.data_interface="${data_interface}"
|
||
uci set modem.modem${modem_no}.path="${physical_path}"
|
||
|
||
uci commit modem
|
||
}
|
||
|
||
#删除模组配置
|
||
# $1:物理路径
|
||
m_del_modem_config()
|
||
{
|
||
local physical_path="$1"
|
||
|
||
#获取模组数量
|
||
local modem_number=$(uci -q get modem.@global[0].modem_number)
|
||
#获取模组序号
|
||
local modem_no
|
||
for i in $(seq 0 $((modem_number-1))); do
|
||
local modem_path=$(uci -q get modem.modem${i}.path)
|
||
if [ "$modem_path" = "$physical_path" ]; then
|
||
modem_no="$i"
|
||
break
|
||
fi
|
||
done
|
||
|
||
[ -z "$modem_no" ] && return
|
||
|
||
#删除该模组的配置
|
||
uci -q del modem.modem${modem_no}
|
||
uci -q set modem.@global[0].modem_number=$((modem_number-1))
|
||
uci commit modem
|
||
|
||
#删除物理路径状态
|
||
m_del_physical_path_status "${physical_path}"
|
||
|
||
#打印日志
|
||
m_log "info" "Modem${modem_no} (${physical_path}) removed"
|
||
}
|
||
|
||
#设置USB设备
|
||
# $1:事件行为(add,remove,bind)
|
||
# $2:制造商ID
|
||
# $3:产品ID
|
||
# $4:物理路径
|
||
m_set_usb_device()
|
||
{
|
||
local action="$1"
|
||
local manufacturer_id="$2"
|
||
local product_id="$3"
|
||
local physical_path="$4"
|
||
|
||
if [ "$action" = "add" ]; then
|
||
#添加USB模组ID
|
||
m_add_usb_id "${manufacturer_id}" "${product_id}"
|
||
|
||
#设置模组配置
|
||
# m_set_modem_hardware_config "${physical_path}"
|
||
|
||
elif [ "$action" = "remove" ]; then
|
||
|
||
#手动配置
|
||
local manual_configuration=$(uci -q get modem.@global[0].manual_configuration)
|
||
[ "${manual_configuration}" = "1" ] && return
|
||
|
||
#删除模组配置
|
||
m_del_modem_config "${physical_path}"
|
||
fi
|
||
}
|
||
|
||
#处理特殊的模组名称
|
||
# $1:模组名称
|
||
handle_special_modem_name()
|
||
{
|
||
local modem_name="$1"
|
||
|
||
#FM350-GL-00 5G Module
|
||
[[ "$modem_name" = *"fm350-gl"* ]] && {
|
||
modem_name="fm350-gl"
|
||
}
|
||
|
||
#SRM825-PV
|
||
[[ "$modem_name" = *"srm825-pv"* ]] && {
|
||
modem_name="srm825"
|
||
}
|
||
|
||
echo "$modem_name"
|
||
}
|
||
|
||
#重新尝试设置模组
|
||
# $1:模组序号
|
||
# $2:AT串口
|
||
# $3:模组支持列表
|
||
retry_set_modem_config()
|
||
{
|
||
local modem_no="$1"
|
||
local at_port="$2"
|
||
local modem_support="$3"
|
||
|
||
local time=0
|
||
while true; do
|
||
|
||
#打印日志
|
||
m_log "info" "Try again to configure the Modem${modem_no}"
|
||
|
||
[ "$time" = "2" ] && break
|
||
|
||
#获取模组名称
|
||
local at_command="AT+CGMM?"
|
||
local modem_name=$(at ${at_port} ${at_command} | grep "+CGMM: " | awk -F'"' '{print $2}' | tr 'A-Z' 'a-z')
|
||
|
||
#再一次获取模组名称
|
||
[ -z "$modem_name" ] && {
|
||
at_command="AT+CGMM"
|
||
modem_name=$(at ${at_port} ${at_command} | grep "+CGMM: " | awk -F': ' '{print $2}' | sed 's/\r//g' | tr 'A-Z' 'a-z')
|
||
}
|
||
|
||
#再一次获取模组名称
|
||
[ -z "$modem_name" ] && {
|
||
at_command="AT+CGMM"
|
||
modem_name=$(at ${at_port} ${at_command} | sed -n '2p' | sed 's/\r//g' | tr 'A-Z' 'a-z')
|
||
}
|
||
|
||
#处理特殊的模组名称
|
||
[ -n "$modem_name" ] && {
|
||
modem_name="$(handle_special_modem_name ${modem_name})"
|
||
}
|
||
|
||
#获取模组信息
|
||
local data_interface=$(uci -q get modem.modem${modem_no}.data_interface)
|
||
local modem_info=$(echo ${modem_support} | jq '.modem_support.'$data_interface'."'$modem_name'"')
|
||
|
||
[ -n "$modem_name" ] && [ "$modem_info" != "null" ] && {
|
||
|
||
#获取制造商
|
||
local manufacturer=$(echo ${modem_info} | jq -r '.manufacturer')
|
||
#获取平台
|
||
local platform=$(echo ${modem_info} | jq -r '.platform')
|
||
#获取连接定义
|
||
local define_connect=$(echo ${modem_info} | jq -r '.define_connect')
|
||
#获取支持的拨号模式
|
||
local modes=$(echo ${modem_info} | jq -r '.modes[]')
|
||
|
||
uci set modem.modem${modem_no}.name="${modem_name}"
|
||
uci set modem.modem${modem_no}.manufacturer="${manufacturer}"
|
||
uci set modem.modem${modem_no}.platform="${platform}"
|
||
uci set modem.modem${modem_no}.define_connect="${define_connect}"
|
||
uci -q del modem.modem${modem_no}.modes #删除原来的拨号模式列表
|
||
for mode in $modes; do
|
||
uci add_list modem.modem${modem_no}.modes="${mode}"
|
||
done
|
||
|
||
#设置模组预设
|
||
m_modem_presets "${at_port}" "${define_connect}" "${manufacturer}"
|
||
|
||
#打印日志
|
||
m_log "info" "Successfully retrying to configure the Modem ${modem_name}"
|
||
|
||
break
|
||
}
|
||
|
||
time=$((time+1))
|
||
sleep 5s
|
||
done
|
||
}
|
||
|
||
#设置模组配置
|
||
# $1:模组序号
|
||
# $2:物理路径
|
||
m_set_modem_config()
|
||
{
|
||
local modem_no="$1"
|
||
local physical_path="$2"
|
||
|
||
#获取AT串口
|
||
local at_port=$(uci -q get modem.modem${modem_no}.at_port)
|
||
|
||
#获取模组名称
|
||
local modem_name=$(uci -q get modem.modem${modem_no}.name)
|
||
[ -z "$modem_name" ] && {
|
||
local at_command="AT+CGMM?"
|
||
modem_name=$(at ${at_port} ${at_command} | grep "+CGMM: " | awk -F'"' '{print $2}' | tr 'A-Z' 'a-z')
|
||
}
|
||
|
||
#获取模组支持列表
|
||
local modem_support=$(cat ${SCRIPT_DIR}/modem_support.json)
|
||
#获取模组信息
|
||
local data_interface=$(uci -q get modem.modem${modem_no}.data_interface)
|
||
local modem_info=$(echo ${modem_support} | jq '.modem_support.'$data_interface'."'$modem_name'"')
|
||
|
||
local manufacturer
|
||
local platform
|
||
local define_connect
|
||
local modes
|
||
local log_message
|
||
if [ -z "$modem_name" ] || [ "$modem_info" = "null" ]; then
|
||
modem_name="unknown"
|
||
manufacturer="unknown"
|
||
platform="unknown"
|
||
define_connect="1"
|
||
modes="qmi gobinet ecm mbim rndis ncm"
|
||
#设置日志信息
|
||
log_message="An unknown Modem${modem_no} (${physical_path}) was found"
|
||
else
|
||
#获取制造商
|
||
manufacturer=$(echo ${modem_info} | jq -r '.manufacturer')
|
||
#获取平台
|
||
platform=$(echo ${modem_info} | jq -r '.platform')
|
||
#获取连接定义
|
||
define_connect=$(echo ${modem_info} | jq -r '.define_connect')
|
||
#获取支持的拨号模式
|
||
modes=$(echo ${modem_info} | jq -r '.modes[]')
|
||
#设置日志信息
|
||
log_message="Configuration Modem${modem_no} ${modem_name} (${physical_path}) successful"
|
||
fi
|
||
|
||
uci set modem.modem${modem_no}.name="${modem_name}"
|
||
uci set modem.modem${modem_no}.manufacturer="${manufacturer}"
|
||
uci set modem.modem${modem_no}.define_connect="${define_connect}"
|
||
uci set modem.modem${modem_no}.platform="${platform}"
|
||
uci -q del modem.modem${modem_no}.modes #删除原来的拨号模式列表
|
||
for mode in $modes; do
|
||
uci add_list modem.modem${modem_no}.modes="${mode}"
|
||
done
|
||
|
||
#设置模组预设
|
||
m_modem_presets "${at_port}" "${define_connect}" "${manufacturer}"
|
||
|
||
#打印日志
|
||
m_log "info" "${log_message}"
|
||
|
||
#重新尝试设置模组
|
||
[ "$modem_name" = "unknown" ] && {
|
||
retry_set_modem_config "${modem_no}" "${at_port}" "${modem_support}"
|
||
}
|
||
}
|
||
|
||
#设置USB AT串口
|
||
# $1:模组序号
|
||
# $2:串口
|
||
# $3:物理路径
|
||
m_set_usb_at_port()
|
||
{
|
||
local modem_no="$1"
|
||
local port="$2"
|
||
local physical_path="$3"
|
||
|
||
local modem_at_port=$(uci -q get modem.modem${modem_no}.at_port)
|
||
[ -z "$modem_at_port" ] && {
|
||
local response="$(at ${port} 'ATI')"
|
||
local str1="No" #No response from modem.
|
||
local str2="failed"
|
||
if [[ "$response" != *"$str1"* ]] && [[ "$response" != *"$str2"* ]] && [ -n "$response" ]; then
|
||
#原先的AT串口会被覆盖掉(是否需要加判断)
|
||
uci set modem.modem${modem_no}.at_port="${port}"
|
||
|
||
#设置模组配置
|
||
m_set_modem_config "${modem_no}" "${physical_path}"
|
||
uci commit modem
|
||
fi
|
||
}
|
||
}
|
||
|
||
#设置PCIE AT串口
|
||
# $1:模组序号
|
||
# $2:串口
|
||
# $3:物理路径
|
||
m_set_pcie_at_port()
|
||
{
|
||
local modem_no="$1"
|
||
local port="$2"
|
||
local physical_path="$3"
|
||
|
||
#设置AT串口
|
||
uci set modem.modem${modem_no}.at_port="${port}"
|
||
|
||
#设置模组配置
|
||
m_set_modem_config "${modem_no}" "${physical_path}"
|
||
uci commit modem
|
||
}
|
||
|
||
#设置ttyUSB设备
|
||
# $1:事件行为(add,remove,bind)
|
||
# $2:物理路径
|
||
m_set_tty_device()
|
||
{
|
||
local action="$1"
|
||
local physical_path="$2"
|
||
|
||
if [ "$action" = "bind" ]; then
|
||
|
||
#获取模组数量
|
||
local modem_number=$(uci -q get modem.@global[0].modem_number)
|
||
#获取模组序号
|
||
local modem_no
|
||
for i in $(seq 0 $((modem_number-1))); do
|
||
local modem_path=$(uci -q get modem.modem${i}.path)
|
||
if [[ "$physical_path" = *"$modem_path"* ]]; then
|
||
modem_no="${i}"
|
||
break
|
||
fi
|
||
done
|
||
|
||
[ -z "$modem_no" ] && return
|
||
|
||
#获取ttyUSB
|
||
local tty_usb=$(find ${physical_path} -type d -name ttyUSB* | sed -n '1p')
|
||
#不存在tty,退出
|
||
[ -z "$tty_usb" ] && return
|
||
local port="/dev/$(basename ${tty_usb})"
|
||
|
||
#添加串口
|
||
uci add_list modem.modem${modem_no}.ports="${port}"
|
||
uci commit modem
|
||
|
||
#设置AT串口
|
||
m_set_usb_at_port "${modem_no}" "${port}" "${physical_path}"
|
||
fi
|
||
}
|
||
|
||
#检查USB设备
|
||
# $1:事件行为(add,remove,bind)
|
||
# $2:设备号
|
||
# $2:设备ID
|
||
# $3:物理路径
|
||
m_check_usb_device()
|
||
{
|
||
local action="$1"
|
||
local device_num="$2"
|
||
local device_id="$3"
|
||
local physical_path="$4"
|
||
|
||
#获取制造商ID
|
||
local manufacturer_id=$(echo "$device_id" | awk -F'/' '{printf "%04s", $1}' | tr ' ' '0')
|
||
#获取产品ID
|
||
local product_id=$(echo "$device_id" | awk -F'/' '{printf "%04s", $2}' | tr ' ' '0')
|
||
|
||
#获取模组支持列表
|
||
local modem_support=$(cat ${SCRIPT_DIR}/modem_support.json)
|
||
|
||
[[ "$modem_support" = *"$manufacturer_id"* ]] && {
|
||
#上报USB事件
|
||
m_report_event "${action}" "usb" "${manufacturer_id}:${product_id}" "${physical_path}"
|
||
|
||
if [ -n "$device_num" ]; then
|
||
#设置USB设备
|
||
m_set_usb_device "${action}" "${manufacturer_id}" "${product_id}" "${physical_path}"
|
||
# else
|
||
#设置ttyUSB设备
|
||
# m_set_tty_device "${action}" "${physical_path}"
|
||
fi
|
||
}
|
||
}
|
||
|
||
#设置模组网络配置
|
||
# $1:网络设备
|
||
# $2:物理路径
|
||
m_set_network_config()
|
||
{
|
||
local network="$1"
|
||
local physical_path="$2"
|
||
|
||
#获取模组数量
|
||
local modem_number=$(uci -q get modem.@global[0].modem_number)
|
||
#获取模组序号
|
||
local modem_no
|
||
for i in $(seq 0 $((modem_number-1))); do
|
||
local modem_path=$(uci -q get modem.modem${i}.path)
|
||
if [ "$modem_path" = "$physical_path" ]; then
|
||
modem_no="${i}"
|
||
break
|
||
fi
|
||
done
|
||
|
||
#没有模组时跳过
|
||
[ -z "$modem_no" ] && return
|
||
|
||
#判断地址是否为net
|
||
# local path=$(basename "$physical_path")
|
||
# if [ "$path" = "net" ]; then
|
||
# return
|
||
# fi
|
||
|
||
#获取网络接口
|
||
local net_path="$(find ${physical_path} -name net | sed -n '1p')"
|
||
local net_net_interface_path="${net_path}"
|
||
|
||
#子目录下存在网络接口
|
||
local net_count="$(find ${physical_path} -name net | wc -l)"
|
||
if [ "$net_count" = "2" ]; then
|
||
net_net_interface_path="$(find ${physical_path} -name net | sed -n '2p')"
|
||
fi
|
||
local network_interface=$(ls ${net_net_interface_path})
|
||
|
||
#设置模组网络配置
|
||
uci set modem.modem${modem_no}.network="${network}"
|
||
uci set modem.modem${modem_no}.network_interface="${network_interface}"
|
||
uci commit modem
|
||
|
||
#打印日志
|
||
m_log "info" "Configuration Modem${modem_no} Network ${network} (${physical_path}) successful"
|
||
}
|
||
|
||
#启用拨号
|
||
# $1:网络设备
|
||
enable_dial()
|
||
{
|
||
local network="$1"
|
||
|
||
local i=0
|
||
while true; do
|
||
#查看该网络设备的配置是否启用
|
||
local modem_network=$(uci -q get modem.@dial-config[${i}].network)
|
||
[ -z "$modem_network" ] && break
|
||
if [ "$network" = "$modem_network" ]; then
|
||
local enable=$(uci -q get modem.@dial-config[${i}].enable)
|
||
if [ "$enable" = "1" ]; then
|
||
service modem reload
|
||
break
|
||
fi
|
||
fi
|
||
i=$((i+1))
|
||
done
|
||
}
|
||
|
||
#禁用拨号
|
||
# $1:网络设备
|
||
disable_dial()
|
||
{
|
||
local network="$1"
|
||
|
||
local i=0
|
||
while true; do
|
||
#查看该网络设备的配置是否启用
|
||
local modem_network=$(uci -q get modem.@dial-config[${i}].network)
|
||
[ -z "$modem_network" ] && break
|
||
if [ "$network" = "$modem_network" ]; then
|
||
local enable=$(uci -q get modem.@dial-config[${i}].enable)
|
||
if [ "$enable" = "1" ]; then
|
||
uci set modem.@dial-config[${i}].enable=0
|
||
uci commit modem
|
||
service modem reload
|
||
break
|
||
fi
|
||
fi
|
||
i=$((i+1))
|
||
done
|
||
}
|
||
|
||
#设置模组串口
|
||
# $1:物理路径
|
||
m_set_modem_port()
|
||
{
|
||
local physical_path="$1"
|
||
|
||
#获取模组数量
|
||
local modem_number=$(uci -q get modem.@global[0].modem_number)
|
||
#获取模组序号
|
||
local modem_no
|
||
for i in $(seq 0 $((modem_number-1))); do
|
||
local modem_path=$(uci -q get modem.modem${i}.path)
|
||
if [ "$modem_path" = "$physical_path" ]; then
|
||
modem_no="${i}"
|
||
break
|
||
fi
|
||
done
|
||
|
||
#没有模组时跳过
|
||
[ -z "$modem_no" ] && return
|
||
|
||
#获取当前路径下所有的串口
|
||
local data_interface=$(uci -q get modem.modem${modem_no}.data_interface)
|
||
local all_port
|
||
if [ "$data_interface" = "usb" ]; then
|
||
all_port=$(find ${physical_path} -name ttyUSB*)
|
||
else
|
||
local mhi_hwip=$(find ${physical_path} -name mhi_hwip*)
|
||
if [ -n "$mhi_hwip" ]; then
|
||
all_port=$(find ${physical_path} -name wwan*)
|
||
all_port=$(echo "$all_port" | sed '1,2d')
|
||
else
|
||
all_port=$(find ${physical_path} -name mhi_*)
|
||
fi
|
||
fi
|
||
|
||
#不存在串口,返回
|
||
[ -z "${all_port}" ] && return
|
||
|
||
#删除原串口
|
||
uci -q del modem.modem${modem_no}.ports
|
||
#设置串口
|
||
local port_cache
|
||
for port_path in $all_port; do
|
||
|
||
local port_tmp="$(basename ${port_path})"
|
||
local port="/dev/${port_tmp}"
|
||
|
||
#跳过重复的串口
|
||
[ "$port" = "$port_cache" ] && continue
|
||
#跳过多余串口(PCIE)
|
||
[[ "$port" = *"mhi_uci_q"* ]] && continue
|
||
[[ "$port" = *"mhi_cntrl_q"* ]] && continue
|
||
|
||
#添加串口
|
||
uci add_list modem.modem${modem_no}.ports="${port}"
|
||
uci commit modem
|
||
|
||
#设置AT串口
|
||
if [ "$data_interface" = "usb" ]; then
|
||
m_set_usb_at_port "${modem_no}" "${port}" "${physical_path}"
|
||
elif [[ "$port" = *"at"* ]]; then
|
||
m_set_pcie_at_port "${modem_no}" "${port}" "${physical_path}"
|
||
elif [[ "$port" = *"DUN"* ]]; then
|
||
m_set_pcie_at_port "${modem_no}" "${port}" "${physical_path}"
|
||
fi
|
||
|
||
#缓存当前串口
|
||
port_cache="${port}"
|
||
done
|
||
}
|
||
|
||
#设置物理设备
|
||
# $1:事件行为(add,remove,bind,scan)
|
||
# $2:网络设备
|
||
# $3:物理路径
|
||
m_set_physical_device()
|
||
{
|
||
local action="$1"
|
||
local network="$2"
|
||
local physical_path="$3"
|
||
|
||
if [ "$action" = "add" ]; then
|
||
|
||
#已经添加过路径,退出
|
||
local physical_path_status=$(m_get_physical_path_status ${physical_path})
|
||
[ "$physical_path_status" = "processed" ] && return
|
||
|
||
#设置模组硬件配置
|
||
m_set_modem_hardware_config "${physical_path}"
|
||
|
||
#设置模组网络配置
|
||
m_set_network_config "${network}" "${physical_path}"
|
||
|
||
#设置模组串口
|
||
m_set_modem_port "${physical_path}"
|
||
|
||
elif [ "$action" = "remove" ]; then
|
||
#删除模组配置
|
||
m_del_modem_config "${physical_path}"
|
||
elif [ "$action" = "scan" ]; then
|
||
|
||
#设置模组硬件配置
|
||
m_set_modem_hardware_config "${physical_path}"
|
||
|
||
#设置模组网络配置
|
||
m_set_network_config "${network}" "${physical_path}"
|
||
|
||
#设置模组串口
|
||
m_set_modem_port "${physical_path}"
|
||
fi
|
||
}
|
||
|
||
#设置网络设备
|
||
# $1:事件行为(add,remove,bind)
|
||
# $2:网络设备
|
||
# $3:物理路径
|
||
# $4:数据接口
|
||
m_set_network_device()
|
||
{
|
||
local action="$1"
|
||
local network="$2"
|
||
local network_path="$3"
|
||
local data_interface="$4"
|
||
|
||
#只处理最上级的网络设备
|
||
local count=$(echo "${network_path}" | grep -o "/net" | wc -l)
|
||
[ "$count" -ge "2" ] && return
|
||
|
||
#判断路径是否带有usb(排除其他eth网络设备)
|
||
if [[ "$network" = *"eth"* ]] && [[ "$network_path" != *"usb"* ]]; then
|
||
return
|
||
fi
|
||
|
||
#上报事件
|
||
m_report_event "${action}" "net" "${network}" "${network_path}"
|
||
|
||
#手动配置
|
||
local manual_configuration=$(uci -q get modem.@global[0].manual_configuration)
|
||
[ "${manual_configuration}" = "1" ] && return
|
||
|
||
if [ "$action" = "add" ]; then
|
||
|
||
if [ "$data_interface" = "usb" ]; then
|
||
#获取物理路径
|
||
local device_physical_path=$(m_get_device_physical_path ${network_path})
|
||
#设置USB网络设备
|
||
# m_set_network_config "${network}" "${device_physical_path}"
|
||
#设置物理设备
|
||
m_set_physical_device "${action}" "${network}" "${device_physical_path}"
|
||
else
|
||
#获取物理路径
|
||
local device_physical_path=$(m_get_device_physical_path ${network_path})
|
||
#设置物理设备
|
||
m_set_physical_device "${action}" "${network}" "${device_physical_path}"
|
||
fi
|
||
#启用拨号
|
||
# sleep 60s
|
||
enable_dial "${network}"
|
||
|
||
elif [ "$action" = "remove" ]; then
|
||
|
||
#USB设备通过USB事件删除
|
||
[ "$data_interface" = "pcie" ] && {
|
||
#获取物理路径
|
||
local device_physical_path=$(m_get_device_physical_path ${network_path})
|
||
#设置物理设备
|
||
m_set_physical_device "${action}" "${network}" "${device_physical_path}"
|
||
}
|
||
|
||
#停止拨号
|
||
# disable_dial "${network}"
|
||
|
||
#打印日志
|
||
m_log "info" "Network ${network} (${network_path}) removed"
|
||
fi
|
||
}
|
||
|
||
#测试Net热插拔
|
||
test_net_hotplug()
|
||
{
|
||
echo ACTION:"$ACTION" >> /root/test
|
||
echo DEVICENAME:"$DEVICENAME" >> /root/test
|
||
echo PATH:"$PATH" >> /root/test
|
||
echo DEVPATH:"$DEVPATH" >> /root/test
|
||
echo DEVTYPE:"$DEVTYPE" >> /root/test
|
||
echo INTERFACE:"$INTERFACE" >> /root/test
|
||
echo PRODUCT:"$PRODUCT" >> /root/test
|
||
}
|
||
|
||
#测试USB热插拔
|
||
test_usb_hotplug()
|
||
{
|
||
echo ACTION:"$ACTION" >> /root/test
|
||
echo DEVICENAME:"$DEVICENAME" >> /root/test
|
||
echo DEVPATH:"$DEVPATH" >> /root/test
|
||
echo DEVNUM:"$DEVNUM" >> /root/test
|
||
echo DRIVER:"$DRIVER" >> /root/test
|
||
echo TYPE:"$TYPE" >> /root/test
|
||
echo PRODUCT:"$PRODUCT" >> /root/test
|
||
echo SEQNUM:"$SEQNUM" >> /root/test
|
||
echo BUSNUM:"$BUSNUM" >> /root/test
|
||
echo MAJOR:"$MAJOR" >> /root/test
|
||
echo MINOR:"$MINOR" >> /root/test
|
||
}
|
||
|
||
#测试tty热插拔
|
||
test_tty_hotplug()
|
||
{
|
||
echo ACTION:"$ACTION" >> /root/test
|
||
echo DEVICENAME:"$DEVICENAME" >> /root/test
|
||
echo DEVPATH:"$DEVPATH" >> /root/test
|
||
echo DEVNUM:"$DEVNUM" >> /root/test
|
||
echo DRIVER:"$DRIVER" >> /root/test
|
||
echo TYPE:"$TYPE" >> /root/test
|
||
echo PRODUCT:"$PRODUCT" >> /root/test
|
||
echo SEQNUM:"$SEQNUM" >> /root/test
|
||
echo BUSNUM:"$BUSNUM" >> /root/test
|
||
echo MAJOR:"$MAJOR" >> /root/test
|
||
echo MINOR:"$MINOR" >> /root/test
|
||
} |