Черговий раз використовував цей блог як записник для того, щоб налаштувати ще один Linux'овий роутер. На цей раз мені стала в нагоді нотатка понад дворічної давності про нарізку internet-каналу з допомогою скрипта htb.init. Проте з голови зовсім вилетіло, що котролювати швидкість можна лише на вихідному інтерфейсі, що логічно: не можете ж ви контролювати швидкість приходу вхідних пакетів — як їх друга сторона відправила так і прийдуть.
В результаті я написав правила обмеження швидкості на інтерфейсі, який «дивиться» в internet, i в мене получилося, що користувач може скачувати інформацію з максимальною швидкістю, а віддавати — з тою, яку я «нарізав». Здоровий глузд же підказує, що треба хоча б навпаки, а в ідеалі — контролювати швидкість в обидві сторони.
Здавалося б — нема нічого простішого — продублювати конфігурацію для інтерфейсу, до якого підключений користувач і «дєло в шляпє», але мої граблі, як завжди виявляється, такими простими не бувають: користувач з’єднується по протоколу pppoe і як називається інтерфейс з’єднання котрого користувача наперед вгадати неможливо, більше того — поки користувач не з’єднався потрібного інтерфейсу просто-напросто в системі немає.
Довелося трохи погуглити.
Як на зло, першими на очі потрапили рішення «викидати htb.init, читати документацію по ip та tc і писати скрипти самому». Були навіть приклади скриптів. Але світ не без добрих людей і хвилин за 15 я таки знайшов відносно просте рішення з використанням того ж htb.init.
Рішення, що називається, «в лоб»: зробити шаблонну конфігурацію, розмножити її для всіх можливих варіантів назви інтерфейсу (від ppp0 до ppp254) і перезапускати htb.init при кожному з’єднанні/відключенні pppoe-клієнта.
Само собою 255 однотипних операцій зручніше робити скриптом, тільки чувак, котрий то написав, в своєму прикладі скрипта намертво забив імена шаблонних файлів (благо в нього їх тільки три) і розмножував їх копіюванням. Мені це не сподобалося, бо
а) по мірі додавання/прибирання користувачів міняється набір шаблонних файлів, тому я просто вирішив читати список і підміняти шаблонну частину назви на потрібну;
б) при зміні параметрів в існуючому файлі потрібно наново запускати процес копіювання, а якщо робити не копії, а лінки на шаблонні файли (як я і зробив), то при редагуванні шаблонів зміни у всіх 255-ти екземплярах відбудуться автоматично.
В результаті скрипт набув такого вигляду:
# cat make_clones #!/bin/bash #прибрати існуючі версії rm -f /etc/sysconfig/htb/ppp* #цикл для 255 можливих інтерфейсів for pppno in `seq 0 254`; do #прочитати назви шаблонних файлів (починаються зppp) for ppptpl in `find /etc/sysconfig/htb/ppp.d/ -name ppp\*`; do #сформувати назву файла конфігурації. Відкидаємоppp, #замість нього додаємо повний шлях і назву інтерфейсу; #відкидання символів після крапки — необов’язкове — #htb.init їх дозволяє (як примітку), але так красивіше #виглядає: в шаблонах все підписано, а в «живій» #конфігурації тільки необхідний мінімум pppXfile=/etc/sysconfig/htb/ppp${pppno}`basename ${ppptpl}|colrm 1 3|cut -d "." -f 1` ln -f ${ppptpl} ${pppXfile} done done
Запускати це чудо слід лише при додаванні чи вилученні користувача. Параметри існуючого можна міняти в відповідному файлі шаблону або будь-якого інтерфейсу і вони автоматично відбудуться у всіх решта відповідних файлах, бо лінки рулять!
Залишилося закинути скрипт перезапуску htb.init в папки /etc/ppp/ip-up.d та /etc/ppp/ip-down.d, який складається з однієї стрічки:
/sbin/htb.init restart
Знаю, що зазвичай він знаходиться зовсім не там, але в мене використовується systemd, та й скрипт потрібно запускати зовсім не на завантаженні системи, тому мені зручніше тримати його в /sbin/
Свої проколи я встиг зрозуміти і виправити до підключення реальних користувачів, тому ніхто нічого не помітив, але на майбутнє нотатку треба собі залишити — хто зна: може через два з половиню роки знов щось таке налаштовувати буду :-)
Працює на AutoGenCMS 0.2.6