Борьба с зависанием МТС 3G модема ZTE MF192+ на Zyxel Keenetic giga

Материал из AlexNook
Перейти к: навигация, поиск

Развитие постепенно идёт и вроде как у нас теперь везде есть мега стабильный и быстрый интернет =)

Решил себе на даче создать свою сеть. Для чего решил использовать Zyxel keenetic giga и 3G модем от МТС. Качество связи, её надёжность, задержки и т. д. конечно ужасные, но и речь идёт не о ближнем подмосковье. В принципе всё можно стерпеть, но хардварные зависания модема совсем добили. Если модем зависает, то всё что может помочь это сброс питания на шине USB. Теоретически это можно реализовать на том же C, но важно, чтобы аппаратная начинка это поддерживала.

В моём случае единственным вариантом было просто отправлять роутер Keenetic в рестарт. Для проверки работоспособности модема было решено написать код на C, который бы, используя libusb, помог послать в модем AT команды и проверить отвечает ли он. На данный подход меня вдохновило обсуждение на сайте Gentoo вот тут. Этот подход мог не требовал остановки процесса pppd, который лочил файл устройства модема /dev/ttyACM0. Однако, тут уже нужно было общаться с устройством не через его файл, а через usb endpoint.

Тестировать программу решил на Gentoo box amd64, а потом уже собрать под Keenetic, благо вот тут есть шикарная инструкция по этому поводу. Но как я ни старался, ничего хорошего не вышло. Подробности и код можно посмотреть здесь.

Однако, позже я узнал, что в данной аппаратной ревизии кинетика нет полноценной реализации USB, и мой план так и так был обречён на провал.

Поэтому пришлось пойти по другому пути - останавливать pppd процесс, который лочил файл устройства /dev/ttyACM0 и потом уже отсылать нужные команды. Собственно скрипт с комментариями, который получился у меня приведён ниже.

File: modemcheck.sh
  1. #!/bin/sh
  2.  
  3. #Vars init
  4. addr=ya.ru              #change to your another address you like
  5. timestoping=50  #how many times we want to ping (remember 3G is very poor as a network connection :( )
  6. pathtolog=/media/DISK_A1/system/root/mts_modem_log
  7. logfile=`date +%y_%m_%d.log`
  8. timestamp=`date +%H-%M-%S`
  9.  
  10. ############################################
  11. #       Script checks MTS USB modem status
  12. #       If it hangs or stuck we need to reset power on usb port
  13. #       So have to do a reboot of the operating system
  14. #       Useful data saved in log files
  15. ############################################
  16.  
  17. #if log path doesn't exit, so create it
  18. if [[ ! -d "$pathtolog" ]]
  19. then
  20.         mkdir -p $pathtolog
  21. fi
  22.  
  23. #First check if we have internet connection and are on-line now
  24. packets=`ping -c ${timestoping} ${addr} | grep -o "\([0-9]\{1,\} packets received\)" | grep -o "\([0-9]\{1,\}\)"`
  25.  
  26. if [[ $packets -ge 1 ]]
  27. then
  28.         echo -e "\n${timestamp}\nPing to ${addr} was ok, recivied ${packets}" >> $pathtolog/$logfile
  29.         #we recivied at least one packet! Cool, now we can exit, because everything is fine
  30.         exit 1
  31. else
  32.         #Something went wrong and we did't get a reply from the external server
  33.         #have to do some additional checks
  34.         echo -e "\n${timestamp}\nThere were no responces from ${addr}, recivied zero packets" >> $pathtolog/$logfile
  35.         (pidof pppd) && (echo -e "Stopping pppd to unlock modem" >> $pathtolog/$logfile; /bin/sh /bin/pppd.sh disconnect)       #if pppd is running, so stop it
  36.         sleep 10        #Wait 10 seconds for pppd daemon stops
  37.         #Send basic AT command to modem. If it's OK and didn't hang, so there is nothing left to do and we may start pppd and exit
  38.         echo "Sending AT to modem" >> $pathtolog/$logfile
  39.         echo "AT" > /dev/ttyACM0
  40.         if [[ `head -n 4 /dev/ttyACM0 | grep OK` ]]
  41.         then
  42.                 echo -e "Recivied OK from modem\nTrying to raise pppd up again..." >> $pathtolog/$logfile
  43.                 #we recivied an answer from our modem, so just raise up a pppd deamon again
  44.                 /bin/sh /bin/pppd.sh connect
  45.                 sleep 10        #wait for pppd daemon to be 100 percent sure it was started up successfully
  46.                 #check for pppd is up, if it didn't, so modem hanging with "initializing..." glitch so reboot
  47.                 (pidof pppd) || (echo "Couldn't start pppd, modem hanging up, rebooting" >> $pathtolog/$logfile; reboot)
  48.         else
  49.                 #we are here now, so our modem state isn't satisfing, we have to reboot router
  50.                 echo "Modem didn't answer AT command, rebooting..." >> $pathtolog/$logfile
  51.                 reboot
  52.         fi
  53. fi

Помещаем наш скрипт по адресу /media/DISK_A1/system/bin/modemcheck.sh, после чего даём права на исполнение ему

chmod a+x /media/DISK_A1/system/bin/modemcheck.sh

Далее устанавливаем выполнение скрипта по крону 1 раз в 15 минут.

vi /media/DISK_A1/system/etc/crontabs/root
File: /media/DISK_A1/system/etc/crontabs/root
  1. #-----------------------MTS-3G-Modem-Check-------------------
  2. */15 * * * *    /media/DISK_A1/system/bin/modemcheck.sh > /dev/null 2>&1

Теперь осталось добавить крон в автозапуск, если это ещё не было сделано

cd /media/DISK_A1/system/etc/init.d
mv K02cron S02cron