Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Կարանտինի ժամանակ ինձ առաջարկեցին մասնակցել մի քանի բջջային օպերատորների համար LTE մոդեմների արագությունը չափող սարքի մշակմանը։

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Հաճախորդը ցանկանում էր գնահատել հեռահաղորդակցության տարբեր օպերատորների արագությունը տարբեր աշխարհագրական վայրերում, որպեսզի կարողանար հասկանալ, թե որ բջջային օպերատորն է իր համար ամենաօպտիմալը LTE կապի միջոցով սարքավորումներ տեղադրելիս, օրինակ, տեսահեռարձակումների համար: Ընդ որում, խնդիրը պետք է լուծվեր հնարավորինս պարզ և էժան՝ առանց թանկարժեք սարքավորումների։

Անմիջապես կասեմ, որ առաջադրանքն ամենապարզն ու գիտելիքատարը չէ, ես ձեզ կասեմ, թե ինչ խնդիրների եմ հանդիպել և ինչպես եմ դրանք լուծել: Այսպիսով, եկեք գնանք:

Նշում

LTE կապի արագությունը չափելը շատ բարդ խնդիր է. անհրաժեշտ է ընտրել ճիշտ սարքավորում և չափման տեխնիկա, ինչպես նաև լավ պատկերացում ունենալ բջջային ցանցի տոպոլոգիայի և աշխատանքի մասին: Բացի այդ, արագության վրա կարող են ազդել մի քանի գործոններ՝ բջջի բաժանորդների թիվը, եղանակային պայմանները, նույնիսկ բջիջից բջիջ արագությունը կարող է կտրուկ տարբերվել ցանցի տոպոլոգիայի պատճառով: Ընդհանուր առմամբ, սա հսկայական թվով անհայտների խնդիր է, և միայն հեռահաղորդակցության օպերատորը կարող է այն ճիշտ լուծել:

Սկզբում հաճախորդը պարզապես ցանկանում էր սուրհանդակը վարել օպերատորների հեռախոսներով, չափումներ անել անմիջապես հեռախոսով, ապա արագության չափման արդյունքները գրել նոթատետրում: lte ցանցերի արագությունը չափելու իմ լուծումը, թեև իդեալական չէ, բայց լուծում է խնդիրը։

Ժամանակի սղության պատճառով որոշումներ եմ կայացրել ոչ թե հարմարության կամ գործնականության, այլ զարգացման արագության օգտին։ Օրինակ, հակադարձ ssh-ն օգտագործվել է հեռավոր մուտքի համար, ավելի գործնական VPN-ի փոխարեն՝ սերվերի և յուրաքանչյուր առանձին հաճախորդի տեղադրման վրա ժամանակ խնայելու համար:

Տեխնիկական առաջադրանք

Ինչպես նշված է հոդվածում Առանց տեխնիկական բնութագրերի. ինչու հաճախորդը դա չի ուզում: Մի աշխատեք առանց տեխնիկական բնութագրերի: Երբեք, ոչ մի տեղ!

Տեխնիկական առաջադրանքը բավականին պարզ էր, ես մի փոքր կընդլայնեմ այն ​​վերջնական օգտագործողի հասկանալու համար: Տեխնիկական լուծումների և սարքավորումների ընտրությունը թելադրել է հաճախորդը։ Այսպիսով, տեխնիկական բնութագրումն ինքնին, բոլոր հաստատումներից հետո.

Հիմնված է մեկ տախտակային համակարգչի վրա vim2 H մոդեմների միջոցով lte միացումների արագության ստուգիչ սարքեքuawei e3372h - 153 մի քանի հեռահաղորդակցության օպերատորներ (մեկից մինչև n): Անհրաժեշտ է նաև կոորդինատներ ստանալ UART-ի միջոցով միացված GPS ընդունիչից։ Կատարեք արագության չափումներ՝ օգտագործելով ծառայությունը www.speedtest.net և դրանք դնել աղյուսակի մեջ, ինչպիսին է.

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Աղյուսակ csv ձևաչափով: Այնուհետև 6 ժամը մեկ ուղարկեք այս նշանը էլեկտրոնային փոստով: Սխալների դեպքում թարթեք LED-ը, որը միացված է GPIO-ին:

Ես նկարագրեցի տեխնիկական բնութագրերը անվճար ձևով, բազմաթիվ հաստատումներից հետո: Բայց առաջադրանքի իմաստն արդեն տեսանելի է։ Ամեն ինչի համար մեկ շաբաթ է տրվել։ Բայց իրականում դա տեւեց երեք շաբաթ։ Սա հաշվի առնելով այն հանգամանքը, որ ես դա արել եմ միայն իմ հիմնական աշխատանքից հետո և հանգստյան օրերին։

Այստեղ ես ուզում եմ ևս մեկ անգամ ուշադրություն հրավիրել այն փաստի վրա, որ հաճախորդը նախապես պայմանավորվել է արագության չափման ծառայության և սարքավորումների օգտագործման վերաբերյալ, ինչը մեծապես սահմանափակել է իմ հնարավորությունները: Բյուջեն նույնպես սահմանափակ էր, ուստի առանձնահատուկ ոչինչ չգնվեց։ Այսպիսով, մենք պետք է խաղայինք այս կանոններով:

Ճարտարապետություն և զարգացում

Սխեման պարզ է և ակնհայտ: Ուստի կթողնեմ առանց հատուկ մեկնաբանությունների։

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Ես որոշեցի ամբողջ նախագիծն իրականացնել python-ով, չնայած այն հանգամանքին, որ ընդհանրապես այս լեզվով զարգացնելու փորձ չունեի։ Ես ընտրեցի այն, քանի որ կային պատրաստի օրինակներ և լուծումներ, որոնք կարող էին արագացնել զարգացումը: Ուստի բոլոր պրոֆեսիոնալ ծրագրավորողներին խնդրում եմ չշտկել python-ում զարգանալու իմ առաջին փորձը, և ես միշտ ուրախ եմ լսել կառուցողական քննադատություն՝ իմ հմտությունները բարելավելու համար:

Ընթացքում ես նաև հայտնաբերեցի, որ python-ն ունի երկու գործող 2 և 3 տարբերակներ, արդյունքում ես կանգ առա երրորդի վրա:

Սարքավորման հանգույցներ

Մեկ ափսե vim2

Ինձ տրվեց մեկ տախտակով համակարգիչ՝ որպես հիմնական մեքենա vim2

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Գերազանց, հզոր մեդիա պրոցեսոր խելացի տան և SMART-TV-ի համար, բայց չափազանց անհամապատասխան այս առաջադրանքի համար, կամ, ասենք, վատ պիտանի: Օրինակ, նրա հիմնական ՕՀ-ն Android-ն է, իսկ Linux-ը երկրորդական ՕՀ է, և համապատասխանաբար ոչ ոք չի երաշխավորում Linux-ի տակ գտնվող բոլոր հանգույցների և դրայվերների բարձրորակ աշխատանքը։ Եվ ես ենթադրում եմ, որ որոշ խնդիրներ կապված են եղել այս հարթակի USB դրայվերների հետ, ուստի մոդեմները չեն աշխատել այնպես, ինչպես սպասվում էր այս տախտակի վրա: Այն նաև ունի շատ վատ և ցրված փաստաթղթեր, ուստի յուրաքանչյուր գործողություն շատ ժամանակ էր պահանջում նավահանգիստները փորելու համար: Նույնիսկ սովորական աշխատանքը GPIO-ի հետ շատ արյուն խլեց։ Օրինակ, ինձանից մի քանի ժամ պահանջվեց LED-ը տեղադրելու համար: Բայց օբյեկտիվ լինելու համար սկզբունքորեն կարեւոր չէր, թե դա ինչ սինգլ տախտակ էր, գլխավորն այն էր, որ աշխատում էր, ու USB պորտեր կային։

Նախ, ես պետք է տեղադրեմ Linux-ը այս տախտակի վրա: Որպեսզի բոլորի, ինչպես նաև նրանց համար, ովքեր կզբաղվեն այս մեկ տախտակային համակարգով, չփչացնեմ փաստաթղթերի մոլուցքը, ես գրում եմ այս գլուխը:

Linux-ը տեղադրելու երկու տարբերակ կա՝ արտաքին SD քարտի կամ ներքին MMC-ի վրա: Ես մի երեկո անցկացրի՝ փորձելով պարզել, թե ինչպես այն աշխատի քարտի հետ, ուստի որոշեցի տեղադրել այն MMC-ի վրա, չնայած, անկասկած, շատ ավելի հեշտ կլիներ աշխատել արտաքին քարտի հետ:

Որոնվածի մասին այստեղ ծուռ ասվեց. Թարգմանում եմ տարօրինակից ռուսերեն։ Տախտակը բռնկելու համար պետք է միացնեմ ապարատային UART-ը։ Միացրեց այն հետեւյալ կերպ.

  • Գործիքի ամրացում GND՝ <—> VIM-ների GPIO-ի Pin17
  • Գործիքի փին TXD՝ <—> VIM-ի GPIO-ի PIN18 (Linux_Rx)
  • Գործիքի փին RXD՝ <—> PIN19 VIM-ի GPIO-ի (Linux_Tx)
  • Գործիքի ամրացում VCC՝ <—> VIM-ների GPIO-ի Pin20

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Որից հետո ես ներբեռնեցի որոնվածը ուստի. Որոնվածի հատուկ տարբերակ VIM1_Ubuntu-server-bionic_Linux-4.9_arm64_EMMC_V20191231.

Այս որոնվածը վերբեռնելու համար ինձ անհրաժեշտ են կոմունալ ծառայություններ: Այս մասին ավելի մանրամասն այստեղ. Ես չեմ փորձել այն թարթել Windows-ի տակ, բայց պետք է մի քանի խոսք ասեմ Linux-ի տակ որոնվածի մասին: Նախ, ես կտեղադրեմ կոմունալ ծառայությունները հրահանգների համաձայն:

git clone https://github.com/khadas/utils
cd /path/to/utils
sudo ./INSTALL

Աաաանդ... Ոչինչ չի ստացվում: Ես մի քանի ժամ ծախսեցի տեղադրման սկրիպտները խմբագրելու վրա, որպեսզի ինձ մոտ ամեն ինչ ճիշտ տեղադրվի։ Ես չեմ հիշում, թե ինչ եմ արել այնտեղ, բայց կար նաև այդ կրկեսը ձիերով։ Ուստի զգույշ եղեք։ Բայց առանց այս կոմունալ ծառայությունների իմաստ չկա ավելի խոշտանգել vim2-ին: Ավելի լավ է ընդհանրապես չխառնվեք նրա հետ։

Դժոխքի յոթ շրջանակներից, սցենարի կազմաձևումից և տեղադրումից հետո ես ստացա աշխատանքային կոմունալ ծառայությունների փաթեթ: Ես USB-ի միջոցով միացրի տախտակը իմ Linux համակարգչին, ինչպես նաև միացրի UART-ը վերը նշված գծապատկերի համաձայն:
Ես տեղադրում եմ իմ սիրելի minicom տերմինալը 115200 արագությամբ, առանց ապարատային և ծրագրային սխալների վերահսկման: Եվ եկեք սկսենք:

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

VIM2-ը UART տերմինալում բեռնելիս ես սեղմում եմ ստեղն, օրինակ՝ բացատ, բեռնումը դադարեցնելու համար: Գիծը հայտնվելուց հետո

kvim2# 

Ես մուտքագրում եմ հրամանը.

kvim2# run update

Հոսթի վրա, որից մենք բեռնում ենք, ես կատարում եմ.

burn-tool -v aml -b VIM2 -i  VIM2_Ubuntu-server-bionic_Linux-4.9_arm64_EMMC_V20191231.img

Վերջ, ֆու: Ստուգեցի, տախտակի վրա Linux կա։ Մուտք/գաղտնաբառ khadas:khadas.

Դրանից հետո որոշ աննշան նախնական պարամետրեր: Հետագա աշխատանքի համար ես անջատում եմ sudo-ի գաղտնաբառը (այո, ոչ անվտանգ, բայց հարմար):

sudo visudo

Ես խմբագրում եմ տողը ձևի մեջ և պահում

# Allow members of group sudo to execute any command
%sudo ALL=(ALL:ALL) NOPASSWD: ALL

Հետո փոխում եմ ներկայիս լոկալը, որ ժամը լինի Մոսկվայում, հակառակ դեպքում՝ Գրինվիչում։

sudo timedatectl set-timezone Europe/Moscow

կամ

ln -s /usr/share/zoneinfo/Europe/Moscow /etc/localtime

Եթե ​​դժվարանում եք, ապա մի օգտագործեք այս տախտակը, Raspberry Pi-ն ավելի լավն է: Անկեղծ ասած.

Huawei e3372h մոդեմ – 153

Այս մոդեմն ինձ համար արյան զգալի աղբյուր էր, և, փաստորեն, դարձավ ամբողջ նախագծի խցանումը: Ընդհանուր առմամբ, այս սարքերի «մոդեմ» անվանումը բացարձակապես չի արտացոլում աշխատանքի էությունը. սա հզոր կոմբինատ է, այս սարքաշարն ունի կոմպոզիտային սարք, որը ձևացնում է որպես CD-ROM՝ դրայվերներ տեղադրելու համար, այնուհետև անցնում է ցանցային քարտի ռեժիմին:

Ճարտարապետական ​​տեսանկյունից Linux օգտատիրոջ տեսանկյունից բոլոր կարգավորումներից հետո այն կարծես այսպիսին է՝ մոդեմը միացնելուց հետո ես ունեմ eth* ցանցային ինտերֆեյս, որը dhcp-ի միջոցով ստանում է IP հասցեն 192.168.8.100 և լռելյայն gateway։ կազմում է 192.168.8.1:

Եվ ամենակարևոր պահը. Մոդեմի այս մոդելը չի ​​կարող աշխատել մոդեմի ռեժիմում, որը կառավարվում է AT հրամաններով. Ամեն ինչ շատ ավելի պարզ կլիներ, յուրաքանչյուր մոդեմի համար ստեղծեք PPP կապեր և աշխատեք դրանցով: Բայց իմ դեպքում «ինքն» (ավելի ճիշտ՝ Linux-ի սուզորդը udev կանոնների համաձայն), ստեղծում է eth ինտերֆեյս և dhcp-ի միջոցով դրան IP հասցե է հատկացնում։

Հետագա շփոթությունից խուսափելու համար առաջարկում եմ մոռանալ «մոդեմ» բառը և ասել ցանցային քարտ և դարպաս, քանի որ, ըստ էության, դա նման է նոր ցանցային քարտը դարպասի հետ կապելուն:
Երբ կա մեկ մոդեմ, դա որևէ հատուկ խնդիր չի առաջացնում, բայց երբ կա մեկից ավելի, այն է՝ n-հատ, առաջանում է ցանցի հետևյալ պատկերը.

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Այսինքն՝ n ցանցային քարտեր՝ նույն IP հասցեով, յուրաքանչյուրը՝ նույն լռելյայն դարպասով։ Բայց իրականում նրանցից յուրաքանչյուրը միացված է իր օպերատորին։

Սկզբում ես ունեի մի պարզ լուծում՝ օգտագործելով ifconfig կամ ip հրամանը, անջատեք բոլոր ինտերֆեյսները և պարզապես հերթով միացրեք մեկը և փորձարկեք այն: Լուծումը լավ էր բոլորի համար, միայն թե միացման պահերին չէի կարողանում միանալ սարքին։ Եվ քանի որ անցումը հաճախակի է և արագ, ես իրականում ընդհանրապես հնարավորություն չունեի միանալու:

Հետևաբար, ես ընտրեցի մոդեմների IP հասցեները ձեռքով փոխելու և այնուհետև երթևեկության կարգավորումների միջոցով երթևեկությունը վարելու ուղին:

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Սրանով մոդեմների հետ կապված իմ խնդիրները չավարտվեցին՝ հոսանքի հետ կապված խնդիրների դեպքում դրանք թափվում էին, և USB հանգույցի լավ կայուն սնուցում էր պահանջվում։ Ես լուծեցի այս խնդիրը՝ հզորությունը կոշտ զոդելով անմիջապես հանգույցին: Մեկ այլ խնդիր, որը ես հանդիպեցի, և որը փչացրեց ամբողջ նախագիծը. սարքի վերագործարկումից կամ սառը գործարկումից հետո ոչ բոլոր մոդեմները հայտնաբերվեցին և ոչ միշտ, և ես չկարողացա որոշել, թե ինչու դա տեղի ունեցավ և ինչ ալգորիթմով: Բայց առաջին հերթին առաջինը:

Որպեսզի մոդեմը ճիշտ աշխատի, ես տեղադրել եմ usb-modeswitch փաթեթը։

sudo apt update
sudo apt install -y usb-modeswitch

Որից հետո միանալուց հետո մոդեմը ճիշտ կհայտնաբերվի և կկարգավորվի udev ենթահամակարգի կողմից։ Ստուգում եմ՝ ուղղակի միացնելով մոդեմը և համոզվելով, որ ցանցը հայտնվում է։
Մեկ այլ խնդիր, որը ես չկարողացա լուծել՝ ինչպե՞ս կարող եմ այս մոդեմից ստանալ օպերատորի անունը, որի հետ մենք աշխատում ենք: Օպերատորի անունը պարունակվում է մոդեմի վեբ ինտերֆեյսում 192.168.8.1 հասցեում: Սա դինամիկ վեբ էջ է, որը տվյալներ է ստանում Ajax-ի հարցումների միջոցով, ուստի էջը պարզեցնելը և անունը վերլուծելը չի ​​աշխատի: Այսպիսով, ես սկսեցի նայել, թե ինչպես զարգացնել վեբ էջ և այլն, և հասկացա, որ ինչ-որ անհեթեթություն եմ անում: Արդյունքում նա թքեց, և օպերատորը սկսեց ստանալ՝ օգտագործելով Speedtest API-ն:

Շատ ավելի հեշտ կլիներ, եթե մոդեմը մուտք ունենար AT հրամանների միջոցով: Հնարավոր կլինի վերակարգավորել այն, ստեղծել ppp կապ, նշանակել IP, ստանալ հեռահաղորդակցության օպերատոր և այլն: Բայց ավաղ, ես աշխատում եմ նրանով, ինչ ինձ տրվել է:

GPS

Ինձ տրված GPS ընդունիչն ուներ UART ինտերֆեյս և հզորություն: Դա լավագույն լուծումը չէր, բայց այն դեռ գործունակ էր և պարզ: Ընդունիչն այսպիսի տեսք ուներ.

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Ճիշտն ասած, ես առաջին անգամ էի աշխատում GPS ընդունիչով, բայց ինչպես սպասում էի, մեզ համար ամեն ինչ վաղուց էր մտածված։ Այսպիսով, մենք պարզապես օգտագործում ենք պատրաստի լուծումներ:

Նախ, ես միացնում եմ uart_AO_B (UART_RX_AO_B, UART_TX_AO_B) GPS-ը միացնելու համար:

khadas@Khadas:~$ sudo fdtput -t s /dtb.img /serial@c81004e0 status okay

Այնուհետև ես ստուգում եմ վիրահատության հաջողությունը:

khadas@Khadas:~$ fdtget /dtb.img /serial@c81004e0 status
okay

Այս հրամանը, ըստ երևույթին, խմբագրում է devtree-ն անմիջապես, ինչը շատ հարմար է:

Այս գործողության հաջող ավարտից հետո վերագործարկեք և տեղադրեք GPS դեյմոնը:

khadas@Khadas:~$ sudo reboot

GPS դեյմոնի տեղադրում: Ես տեղադրում եմ ամեն ինչ և անմիջապես կտրում այն ​​հետագա կոնֆիգուրացիայի համար:

sudo apt install gpsd gpsd-clients -y
sudo killall gpsd
 
/* GPS daemon stop/disable */
sudo systemctl stop gpsd.socket
sudo systemctl disable gpsd.socket

Կարգավորումների ֆայլի խմբագրում:

sudo vim /etc/default/gpsd

Տեղադրում եմ UART, որից կկախվի GPS-ը։

DEVICES="/dev/ttyS4"

Եվ հետո մենք ամեն ինչ միացնում ենք և սկսում:

/* GPS daemon enable/start */
sudo systemctl enable gpsd.socket
sudo systemctl start gpsd.socket

Դրանից հետո ես միացնում եմ GPS-ը։

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

GPS լարը ձեռքումս է, UART կարգաբերող լարերը՝ մատներիս տակ։

Ես վերաբեռնում և ստուգում եմ GPS-ի աշխատանքը gpsmon ծրագրի միջոցով:

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Դուք չեք կարող տեսնել արբանյակները այս սքրինշոթում, բայց դուք կարող եք տեսնել կապը GPS ընդունիչի հետ, և դա նշանակում է, որ ամեն ինչ լավ է:

Python-ում ես փորձեցի այս դեյմոնի հետ աշխատելու բազմաթիվ տարբերակներ, բայց որոշեցի այն մեկը, որը ճիշտ էր աշխատում python 3-ի հետ:

Տեղադրում եմ անհրաժեշտ գրադարանը։

sudo -H pip3 install gps3 

Եվ ես քանդակում եմ աշխատանքային ծածկագիրը։

from gps3.agps3threaded import AGPS3mechanism
...

def getPositionData(agps_thread):
	counter = 0;
	while True:
		longitude = agps_thread.data_stream.lon
		latitude = agps_thread.data_stream.lat
		if latitude != 'n/a' and longitude != 'n/a':
			return '{}' .format(longitude), '{}' .format(latitude)
		counter = counter + 1
		print ("Wait gps counter = %d" % counter)
		if counter == 10:
			ErrorMessage("Ошибка GPS приемника!!!")
			return "NA", "NA"
		time.sleep(1.0)
...
f __name__ == '__main__':
...
	#gps
	agps_thread = AGPS3mechanism()  # Instantiate AGPS3 Mechanisms
	agps_thread.stream_data()  # From localhost (), or other hosts, by example, (host='gps.ddns.net')
	agps_thread.run_thread()  # Throttle time to sleep after an empty lookup, default '()' 0.2 two tenths of a second

Եթե ​​ինձ անհրաժեշտ է կոորդինատներ ստանալ, դա արվում է հետևյալ զանգով.

longitude, latitude = getPositionData(agps_thread)

Իսկ 1-10 վայրկյանի ընթացքում ես կամ կստանամ կոորդինատը, կամ ոչ։ Այո, կոորդինատներ ստանալու տասը փորձ եմ ունեցել։ Ոչ օպտիմալ, ծուռ և թեքված, բայց աշխատում է: Ես որոշեցի դա անել, քանի որ GPS-ը կարող է վատ ընդունելություն ունենալ և ոչ միշտ ստանալ տվյալներ: Եթե ​​դուք սպասում եք տվյալների ստանալուն, ապա եթե աշխատում եք հեռավոր սենյակում, ծրագիրը կսառչի այս վայրում: Ուստի ես իրագործեցի այս ոչ էլեգանտ տարբերակը։

Սկզբունքորեն, եթե ավելի շատ ժամանակ լիներ, հնարավոր կլիներ GPS-ից տվյալներ ստանալ անմիջապես UART-ի միջոցով, վերլուծել դրանք առանձին թեմայում և աշխատել դրա հետ։ Բայց ընդհանրապես ժամանակ չկար, այստեղից էլ՝ դաժանորեն տգեղ օրենսգիրքը։ Եվ այո, ես չեմ ամաչում։

Լույս արտանետող դիոդ

LED-ի միացումը պարզ էր և միևնույն ժամանակ դժվար: Հիմնական դժվարությունն այն է, որ համակարգում PIN համարը չի համապատասխանում գրատախտակի վրա նշված PIN համարին և քանի որ փաստաթուղթը գրված է ձախ կողմում: ՕՀ-ում ապարատային կապի համարը և փին համարը համեմատելու համար հարկավոր է գործարկել հրամանը.

gpio readall

Համակարգում և տախտակի վրա կցուցադրվի փին համապատասխանության աղյուսակ: Որից հետո ես արդեն կարող եմ գործարկել քորոցը հենց ՕՀ-ում: Իմ դեպքում LED-ը միացված է GPIOH_5.

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Ես միացնում եմ GPIO փին ելքային ռեժիմին:

gpio -g mode 421 out

Ես գրում եմ զրո:

gpio -g write 421 0

Մեկը գրում եմ.

gpio -g write 421 1

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա
Ամեն ինչ վառվում է «1» գրելուց հետո

#gpio subsistem
def gpio_init():
	os.system("gpio -g mode 421 out")
	os.system("gpio -g write 421 1")

def gpio_set(val):
	os.system("gpio -g write 421 %d" % val)
	
def error_blink():
	gpio_set(0)
	time.sleep(0.1)
	gpio_set(1)
	time.sleep(0.1)
	gpio_set(0)
	time.sleep(0.1)
	gpio_set(1)
	time.sleep(0.1)
	gpio_set(0)
	time.sleep(1.0)
	gpio_set(1)

def good_blink():
	gpio_set(1)

Հիմա սխալների դեպքում զանգում եմ error_blink()-ն ու լուսադիոդը գեղեցիկ կթարթի։

Ծրագրային հանգույցներ

Speedtest API

Մեծ ուրախություն է, որ speedtest.net ծառայությունն ունի իր սեփական python-API-ն, կարող եք նայել Github.

Լավն այն է, որ կան սկզբնաղբյուրներ, որոնք նույնպես կարելի է դիտել: Ինչպես աշխատել այս API-ի հետ (պարզ օրինակներ) կարելի է գտնել այստեղ համապատասխան բաժինը.

Ես տեղադրում եմ python գրադարանը հետևյալ հրամանով.

sudo -H pip3 install speedtest-cli

Օրինակ, դուք կարող եք նույնիսկ արագության ստուգիչ տեղադրել Ubuntu-ում անմիջապես ծրագրաշարից: Սա նույն python հավելվածն է, որն այնուհետև կարող է գործարկվել անմիջապես վահանակից:

sudo apt install speedtest-cli -y

Եվ չափեք ձեր ինտերնետի արագությունը:

speedtest-cli
Retrieving speedtest.net configuration...
Testing from B***** (*.*.*.*)...
Retrieving speedtest.net server list...
Selecting best server based on ping...
Hosted by MTS (Moscow) [0.12 km]: 11.8 ms
Testing download speed................................................................................
Download: 7.10 Mbit/s
Testing upload speed......................................................................................................
Upload: 3.86 Mbit/s

Արդյունքում, ճիշտ այնպես, ինչպես ես արեցի: Ես ստիպված էի մտնել այս արագության թեստի սկզբնական կոդերը, որպեսզի դրանք ավելի լիարժեք կիրառեի իմ նախագծում: Ամենակարևոր խնդիրներից մեկը հեռահաղորդակցության օպերատորի անունը ստանալն է, որպեսզի այն փոխարինվի ափսեի մեջ:

import speedtest
from datetime import datetime
...
#Указываем конкретный сервер для теста
#6053) MaximaTelecom (Moscow, Russian Federation)
servers = ["6053"]
# If you want to use a single threaded test
threads = None
s = speedtest.Speedtest()
#получаем имя оператора сотовой связи
opos = '%(isp)s' % s.config['client']
s.get_servers(servers)
#получаем текстовую строку с параметрами сервера
testserver = '%(sponsor)s (%(name)s) [%(d)0.2f km]: %(latency)s ms' % s.results.server
#тест загрузки
s.download(threads=threads)
#тест выгрузки
s.upload(threads=threads)
#получаем результаты
s.results.share()

#После чего формируется строка для записи в csv-файл.
#получаем позицию GPS
longitude, latitude = getPositionData(agps_thread)
#время и дата
curdata = datetime.now().strftime('%d.%m.%Y')
curtime = datetime.now().strftime('%H:%M:%S')
delimiter = ';'
result_string = opos + delimiter + str(curpos) + delimiter + 
	curdata + delimiter + curtime + delimiter + longitude + ', ' + latitude + delimiter + 
	str(s.results.download/1000.0/1000.0) + delimiter + str(s.results.upload / 1000.0 / 1000.0) + 
	delimiter + str(s.results.ping) + delimiter + testserver + "n"
#тут идет запись в файл логов

Այստեղ նույնպես ամեն ինչ պարզվեց, որ այնքան էլ պարզ չէր, թեև շատ ավելի պարզ կթվա։ Սկզբում սերվերների պարամետրը հավասար էր [], ասում են, ընտրիր լավագույն սերվերը։ Արդյունքում ես ունեի պատահական սերվերներ և, ինչպես կարող եք կռահել, փոփոխական արագություն: Սա բավականին բարդ թեմա է, ֆիքսված սերվերի օգտագործումը, եթե այո, ստատիկ կամ դինամիկ, պահանջում է հետազոտություն: Բայց ահա արագության չափման գրաֆիկների օրինակ Beeline օպերատորի համար, երբ դինամիկ կերպով ընտրում է թեստային սերվեր և ստատիկորեն ամրագրված:

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա
Դինամիկ սերվեր ընտրելիս արագության չափման արդյունքը.

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա
Արագության փորձարկման արդյունք՝ մեկ խիստ ընտրված մեկ սերվերով։

Թեստավորման ժամանակ երկու տեղում էլ «մորթի» է, և այն պետք է հեռացնել մաթեմատիկական մեթոդներով։ Բայց ֆիքսված սերվերի դեպքում այն ​​մի փոքր ավելի քիչ է, և ամպլիտուդան ավելի կայուն է:
Ընդհանրապես, սա մեծ հետազոտության վայր է։ Եվ ես կչափեի իմ սերվերի արագությունը՝ օգտագործելով iperf կոմունալը: Բայց մենք մնում ենք տեխնիկական բնութագրերին:

Փոստի ուղարկում և սխալներ

Փոստ ուղարկելու համար ես փորձեցի մի քանի տասնյակ տարբեր տարբերակներ, բայց ի վերջո կանգ առա հետևյալի վրա. Ես գրանցեցի փոստարկղ Yandex-ում, հետո վերցրեցի Սա նամակ ուղարկելու օրինակ է. Ես ստուգեցի այն և ներդրեցի ծրագրում: Այս օրինակը ուսումնասիրում է տարբեր տարբերակներ, այդ թվում՝ ուղարկելը gmail-ից և այլն: Ես չէի ուզում անհանգստանալ իմ փոստի սերվերի տեղադրմամբ և ժամանակ չունեի դրա համար, բայց ինչպես պարզվեց ավելի ուշ, դա նույնպես ապարդյուն էր:

Տեղեկամատյաններն ուղարկվել են ըստ ժամանակացույցի, եթե կա կապ, յուրաքանչյուր 6 ժամը՝ ժամը 00-ին, 06-ին, 12-ին և 18-ին։ Ուղարկեց այն հետևյալ կերպ.

from send_email import *
...
message_log = "Логи тестирования платы №1"
EmailForSend = ["[email protected]", "[email protected]"]
files = ["/home/khadas/modems_speedtest/csv"]
...
def sendLogs():
	global EmailForSend
	curdata = datetime.now().strftime('%d.%m.%Y')
	сurtime = datetime.now().strftime('%H:%M:%S')
	try:
		for addr_to in EmailForSend:
			send_email(addr_to, message_log, "Логи за " + curdata + " " + сurtime, files)
	except:
		print("Network problem for send mail")
		return False
	return True

Ի սկզբանե ուղարկվել են նաև սխալներ: Սկզբից դրանք կուտակվում էին ցուցակում, այնուհետև ուղարկվում էին նաև ժամանակացույցի միջոցով, եթե կապ կար: Այնուամենայնիվ, այնուհետև խնդիրներ առաջացան այն բանի հետ, որ Yandex-ը սահմանափակում է օրական ուղարկվող հաղորդագրությունների քանակը (սա ցավ է, տխրություն և նվաստացում): Քանի որ նույնիսկ րոպեում կարող էին լինել հսկայական քանակությամբ սխալներ, մենք ստիպված եղանք հրաժարվել փոստով սխալներ ուղարկելուց: Ուստի նկատի ունեցեք Yandex ծառայությունների միջոցով նման խնդրի մասին տեղեկատվություն ավտոմատ կերպով ուղարկելիս:

Հետադարձ կապի սերվեր

Որպեսզի կարողանայի մուտք ունենալ դեպի հեռավոր սարքաշար և այն հարմարեցնել և վերակազմավորել, ինձ արտաքին սերվեր էր անհրաժեշտ: Ընդհանուր առմամբ, արդարության համար, ճիշտ կլինի ուղարկել բոլոր տվյալները սերվերին և կառուցել բոլոր գեղեցիկ գրաֆիկները վեբ ինտերֆեյսի մեջ։ Բայց ոչ միանգամից։

VPS-ի համար ես ընտրեցի ruvds.com. Դուք կարող եք վերցնել ամենապարզ սերվերը: Եվ ընդհանրապես, իմ նպատակների համար սա բավական կլիներ։ Բայց քանի որ ես չեմ վճարել սերվերի համար իմ գրպանից, ես որոշեցի վերցնել այն փոքր պահուստով, որպեսզի բավական լինի, եթե մենք տեղադրենք վեբ ինտերֆեյս, մեր սեփական SMTP սերվեր, VPN և այլն: Բացի այդ, կարող եք ստեղծել Telegram բոտ և խնդիրներ չունենալ դրա արգելափակման հետ: Հետեւաբար, ես ընտրեցի Ամստերդամը եւ հետեւյալ պարամետրերը.

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Որպես սարքաշարի հետ կապի մեթոդ, vim2-ն ընտրեց հակադարձ ssh կապը և, ինչպես ցույց տվեց պրակտիկան, դա լավագույնը չէ: Եթե ​​կապը կորչում է, սերվերը պահում է պորտը և որոշ ժամանակ հնարավոր չէ միանալ դրա միջոցով: Հետևաբար, դեռ ավելի լավ է օգտագործել հաղորդակցման այլ մեթոդներ, օրինակ՝ VPN: Ապագայում ես ուզում էի անցնել VPN, բայց ժամանակ չունեի.

Ես չեմ խորանա firewall-ի տեղադրման, իրավունքների սահմանափակման, root ssh կապերի անջատման և VPS-ի ստեղծման այլ ճշմարտությունների մասին: Ես կցանկանայի հավատալ, որ դուք արդեն ամեն ինչ գիտեք։ Հեռակա կապի համար ես սերվերի վրա նոր օգտվող եմ ստեղծում:

adduser vimssh

Ես ստեղծում եմ ssh կապի բանալիներ մեր սարքավորման վրա:

ssh-keygen

Եվ ես դրանք պատճենում եմ մեր սերվերին:

ssh-copy-id [email protected]

Մեր սարքավորման վրա ես ստեղծում եմ ավտոմատ հակադարձ ssh միացում յուրաքանչյուր բեռնման ժամանակ:

[Unit] Description=Auto Reverse SSH
Requires=systemd-networkd-wait-online.service
After=systemd-networkd-wait-online.service
[Service] User=khadas
ExecStart=/usr/bin/ssh -NT -o ExitOnForwardFailure=yes -o ServerAliveInterval=60 -CD 8080 -R 8083:localhost:22 [email protected]
RestartSec=5
Restart=always
[Install] WantedBy=multi-user.target

Ուշադրություն դարձրեք 8083 պորտին. այն որոշում է, թե որ պորտը ես կօգտագործեմ հակադարձ ssh-ի միջոցով միանալու համար: Ավելացրեք այն գործարկմանը և սկսեք:

sudo systemctl enable autossh.service
sudo systemctl start autossh.service

Դուք նույնիսկ կարող եք տեսնել կարգավիճակը.

sudo systemctl status autossh.service

Այժմ, մեր VPS սերվերի վրա, եթե գործարկենք.

ssh -p 8083 khadas@localhost

Այնուհետև ես հասնում եմ սարքավորման իմ փորձարկմանը: Իսկ ապարատայինից կարող եմ նաև logs և ցանկացած տվյալ ուղարկել իմ սերվերին ssh-ի միջոցով, ինչը շատ հարմար է։

Բոլորը միասին դնելով

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա
Միացնելով, եկեք սկսենք մշակումը և վրիպազերծումը

Ֆու, դե, վերջ, ես նկարագրեցի բոլոր հանգույցները: Հիմա ժամանակն է ամեն ինչ ի մի բերելու: Դուք կարող եք տեսնել կոդը այստեղ.

Կոդի հետ կապված կարևոր կետ. Այս նախագիծը կարող է չսկսվել այսպես, քանի որ այն հարմարեցված էր կոնկրետ առաջադրանքի, կոնկրետ ճարտարապետության համար: Թեև ես տալիս եմ սկզբնաղբյուրը, ես դեռ կբացատրեմ ամենաարժեքավոր բաները այստեղ, հենց տեքստում, հակառակ դեպքում դա բոլորովին անհասկանալի է:

Սկզբում ես սկզբնավորում եմ gps-ը, gpio-ն և գործարկում եմ առանձին ժամանակացույցի թեմա:

#запуск потока планировщика
pShedulerThread = threading.Thread(target=ShedulerThread, args=(1,))
pShedulerThread.start()

Ժամանակացույցը բավականին պարզ է. այն տեսնում է, թե արդյոք եկել է հաղորդագրություններ ուղարկելու ժամանակը և որն է ներկայիս սխալի կարգավիճակը: Եթե ​​կա սխալի դրոշ, ապա մենք թարթում ենք LED-ը:

#sheduler
def ShedulerThread(name):
	global ready_to_send
	while True:
		d = datetime.today()
		time_x = d.strftime('%H:%M')
		if time_x in time_send_csv:
			ready_to_send = True
		if error_status:
			error_blink()
		else:
			good_blink()
		time.sleep(1)

Այս նախագծի ամենադժվար մասը յուրաքանչյուր թեստի համար հակադարձ ssh կապի պահպանումն է: Յուրաքանչյուր թեստ ներառում է կանխադրված դարպասի և DNS սերվերի վերակազմավորում: Քանի որ ամեն դեպքում ոչ ոք չի կարդում, իմացեք, որ գնացքը փայտե ռելսերի վրա չի նստում։ Ով գտնում է Զատկի ձուն, ստանում է կոնֆետ:

Դա անելու համար ես ստեղծում եմ առանձին երթուղային աղյուսակ՝ set-mark 0x2 և տրաֆիկի վերահղման կանոն:

def InitRouteForSSH():
	cmd_run("sudo iptables -t mangle -A OUTPUT -p tcp -m tcp --dport 22 -j MARK --set-mark 0x2")
	cmd_run("sudo ip rule add fwmark 0x2/0x2 lookup 102")

Դուք կարող եք ավելին իմանալ այն մասին, թե ինչպես է այն աշխատում կարդալ այս հոդվածում.

Որից հետո ես անցնում եմ անվերջ հանգույց, որտեղ ամեն անգամ մենք ստանում ենք միացված մոդեմների ցուցակը (պարզելու համար, թե արդյոք ցանցի կոնֆիգուրացիան հանկարծակի փոխվել է):

network_list = getNetworklist()

Ցանցային ինտերֆեյսների ցուցակ ստանալը բավականին պարզ է:

def getNetworklist():
	full_networklist = os.listdir('/sys/class/net/')
	network_list = [x for x in full_networklist if "eth" in x and x != "eth0"]
	return network_list

Ցուցակը ստանալուց հետո ես բոլոր ինտերֆեյսերի վրա դրեցի IP հասցեներ, ինչպես ցույց տվեցի մոդեմի մասին գլխի նկարում։

SetIpAllNetwork(network_list)

def SetIpAllNetwork(network_list):
	for iface in network_list:
		lastip = "%d" % (3 + network_list.index(iface))
		cmd_run ("sudo ifconfig " + iface + " 192.168.8." + lastip +" up")

Այնուհետև ես պարզապես անցնում եմ յուրաքանչյուր ինտերֆեյսի միջով մի օղակով: Եվ ես կարգավորում եմ յուրաքանչյուր ինտերֆեյս:

	for iface in network_list:
		ConfigNetwork(iface)

def ConfigNetwork(iface):
#сбрасываем все настройки
		cmd_run("sudo ip route flush all")
#Назначаем шлюз по умолчанию
		cmd_run("sudo route add default gw 192.168.8.1 " + iface)
#задаем dns-сервер (это нужно для работы speedtest)
		cmd_run ("sudo bash -c 'echo nameserver 8.8.8.8 > /etc/resolv.conf'")

Ես ստուգում եմ ինտերֆեյսը ֆունկցիոնալության համար, եթե ցանց չկա, ապա ես առաջացնում եմ սխալներ: Եթե ​​կա ցանց, ապա ժամանակն է գործելու:

Այստեղ ես կարգավորում եմ ssh-ի երթուղավորումը այս ինտերֆեյսի վրա (եթե դա չի արվել), ուղարկում եմ սխալներ սերվերին, եթե ժամանակը եկել է, ուղարկում եմ տեղեկամատյաններ և վերջապես գործարկում արագության թեստ և պահում տեղեկամատյանները csv ֆայլում:

if not NetworkAvalible():
....
#Здесь мы формируем ошибки
....
else: #Есть сеть, ура, работаем!
#Если у нас проблемный интерфейс, на котором ssh, то меняем его
  if (sshint == lastbanint or sshint =="free"):
    print("********** Setup SSH ********************")
    if sshint !="free":
      сmd_run("sudo ip route del default via 192.168.8.1 dev " + sshint +" table 102")
    SetupReverseSSH(iface)
    sshint = iface
#раз сетка работает, то давай срочно все отправим!!!
    if ready_to_send:
      print ("**** Ready to send!!!")
        if sendLogs():
          ready_to_send = False
        if error_status:
          SendErrors()
#и далее тестируем скорость и сохраняем логи. 

Հարկ է նշել հակադարձ ssh-ի տեղադրման գործառույթը:

def SetupReverseSSH(iface):
	cmd_run("sudo systemctl stop autossh.service")
	cmd_run("sudo ip route add default via 192.168.8.1 dev " + iface +" table 102")
	cmd_run("sudo systemctl start autossh.service")

Եվ իհարկե, դուք պետք է ավելացնեք այս ամբողջ գեղեցկությունը ստարտափին: Դա անելու համար ես ստեղծում եմ ֆայլ.

sudo vim /etc/systemd/system/modems_speedtest.service

Եվ ես դրանում գրում եմ.

[Unit] Description=Modem Speed Test
Requires=systemd-networkd-wait-online.service
After=systemd-networkd-wait-online.service
[Service] User=khadas
ExecStart=/usr/bin/python3.6 /home/khadas/modems_speedtest/networks.py
RestartSec=5
Restart=always
[Install] WantedBy=multi-user.target

Ես միացնում եմ ավտոմատ բեռնումը և սկսում եմ:

sudo systemctl enable modems_speedtest.service
sudo systemctl start modems_speedtest.service

Այժմ ես կարող եմ տեսնել տեղեկամատյանները, թե ինչ է կատարվում՝ օգտագործելով հրամանը.

journalctl -u modems_speedtest.service --no-pager -f

Արդյունքները

Դե, հիմա ամենակարևորը, ի՞նչ եղավ արդյունքում։ Ահա մի քանի գրաֆիկներ, որոնք ես կարողացա նկարել մշակման և վրիպազերծման գործընթացում: Գրաֆիկները կառուցվել են gnuplot-ի միջոցով՝ հետևյալ սցենարով.

#! /usr/bin/gnuplot -persist
set terminal postscript eps enhanced color solid
set output "Rostelecom.ps"
 
#set terminal png size 1024, 768
#set output "Rostelecom.png"
 
set datafile separator ';'
set grid xtics ytics
set xdata time
set ylabel "Speed Mb/s"
set xlabel 'Time'
set timefmt '%d.%m.%Y;%H:%M:%S'
set title "Rostelecom Speed"

plot "Rostelecom.csv" using 3:6 with lines title "Download", '' using 3:7 with lines title "Upload"
 
set title "Rostelecom 2 Ping"
set ylabel "Ping ms"
plot "Rostelecom.csv" using 3:8 with lines title "Ping"

Առաջին փորձը Tele2 օպերատորի հետ էր, որը ես վարեցի մի քանի օր։

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Այստեղ ես օգտագործեցի դինամիկ չափիչ սերվեր: Արագության չափումները գործում են, բայց շատ են տատանվում, բայց որոշ միջին արժեք դեռ տեսանելի է, և դա կարելի է ստանալ՝ զտելով տվյալները, օրինակ՝ շարժվող միջինով:

Հետագայում ես կառուցեցի մի շարք գրաֆիկներ հեռահաղորդակցության այլ օպերատորների համար: Այս դեպքում արդեն կար մեկ թեստավորման սերվեր, և արդյունքները նույնպես շատ հետաքրքիր էին։

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Ինչպես տեսնում եք, թեման շատ ծավալուն է այս տվյալների հետազոտության և մշակման համար, և ակնհայտորեն չի տևում մի քանի շաբաթվա աշխատանք: Բայց…

Աշխատանքի արդյունք

Աշխատանքն անսպասելիորեն ավարտվեց իմ կամքից անկախ հանգամանքների պատճառով։ Այս նախագծի թույլ կողմերից մեկը, իմ սուբյեկտիվ կարծիքով, մոդեմն էր, որն իրականում չէր ցանկանում միաժամանակ աշխատել այլ մոդեմների հետ և ամեն անգամ բեռնվելիս նման հնարքներ էր անում։ Այս նպատակների համար կան հսկայական թվով այլ մոդեմների մոդելներ, սովորաբար դրանք արդեն Mini PCI-e ձևաչափով են և տեղադրված են սարքի ներսում և շատ ավելի հեշտ է կարգավորել: Բայց դա բոլորովին այլ պատմություն է: Նախագիծը հետաքրքիր էր, և ես շատ ուրախ էի, որ կարողացա մասնակցել դրան։

Արագության միաժամանակյա փորձարկում մի քանի LTE մոդեմների վրա

Source: www.habr.com

Добавить комментарий