Утилизация процессора из-за скрипта

Проблема такая:

Есть modbus 0-10V, через него происходят измерения параметров двух источников питания - напряжения (через резисторный делитель) и тока (через чипы ACS712). Получаю “сырые” напряжения на WB5. Загрузка процессора где-то 47% . Разумеется, чтобы получить то, что интересует - необходимо эти “сырые” переменные пересчитать простой арифметикой. Скрипт такой:

defineVirtualDevice("power_supply", {
  title: "Power supply", 
  
  cells: {
    'PS1 current' : {
        type : "current",
        value : 0
    },
    'PS1 voltage' : {
        type : "voltage",
        value : 0
    },
    'PS2 current' : {
        type : "current",
        value : 0
    },
    'PS2 voltage' : {
        type : "voltage",
        value : 0
    }
  }
});

defineRule("PS1_currency", {
whenChanged: "wp3084_7/VI_7",
  then: function (newValue, devName, cellName) {
       dev["power_supply"]["PS1 current"] = ((newValue - dev["wb-adc"]["5Vout"]/2) * 10).toFixed(2);
           }
});

defineRule("PS1_voltage", {
whenChanged: "wp3084_7/VI_2",
  then: function (newValue, devName, cellName) {
       dev["power_supply"]["PS1 voltage"] = (newValue * 1.699).toFixed(2);
           }
});

defineRule("PS2_currency", {
whenChanged: "wp3084_7/VI_8",
  then: function (newValue, devName, cellName) {
       dev["power_supply"]["PS2 current"] = ((newValue - dev["wb-adc"]["5Vout"]/2) * 5.4054).toFixed(2);
           }
});

defineRule("PS2_voltage", {
whenChanged: "wp3084_7/VI_1",
  then: function (newValue, devName, cellName) {
       dev["power_supply"]["PS2 voltage"] = (newValue * 1.691).toFixed(2);
           }
});

Скрипт честно отрабатывает что от него требуется и выдает нужные числа. Но при этом утилизация процессора WB5 уходит под 80%. Возникает вопрос - 4 простых арифметических действия в скрипте могут утилизировать процессор дополнительно на 33% (треть ресурса процессора!!!)? Что я делаю не так?

Это уже много. Покажите настройки, расскажите что делаете и вывод top покажите пожалуйста.

Нет, 4 простых арифметических действий не могут утилизировать процессор на 33%.
А вот запуск правил (неважно что именно они делают) например тысячу раз в секунду и последующее протаскивание данных через движок правил, очередь сообщений, БД и веб-интерфейс - вполне может.

Могу предположить, что у вас идёт очень большой поток данных с блока wp3084: опрос идёт на скорости шины, а т.к. блок отдаёт вам сырые аналоговые данные, то они каждый раз приходят разные и честно протаскиваются через всю систему. Можно снизить скорость опроса в настройках Serial Devices Configuration, настройка Poll Interval. Задать можно для всего порта, для одного девайса или для конкретного канала. Только обновите перед этим пожалуйста wb-mqtt-serial:

apt-get update && apt-get install wb-mqtt-serial

Знаю, что много. Но меньше 37% как-то не получалось вообще. Замечу, что цифры мной приведенные из мониторинга по SNMP (мне так удобнее), они несколько отличаются от top:

PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND
5834 root 20 0 876m 12m 5232 R 45.8 10.3 610:51.15 wb-rules
2924 mosquitt 20 0 6364 3104 1788 S 10.3 2.5 114:18.92 mosquitto
28306 root 20 0 36624 6360 5336 S 4.8 5.1 4:30.99 wb-mqtt-serial
3144 root 20 0 10640 2732 2100 S 4.5 2.2 51:06.53 wb-homa-adc
4705 root 20 0 19668 2580 1936 S 2.7 2.1 31:54.44 wb-homa-gpio
30526 root 20 0 3176 2060 1644 R 2.7 1.7 0:04.41 top
3236 root 20 0 10436 2608 2004 S 2.1 2.1 9:17.75 wb-homa-w1
301 root 20 0 0 0 0 S 1.8 0.0 6:29.91 w1_bus_master1
30475 root 20 0 0 0 0 S 1.2 0.0 0:01.43 kworker/0:2
3212 root 20 0 35144 5736 2404 S 0.9 4.6 14:23.38 python
1667 root 20 0 0 0 0 S 0.6 0.0 4:58.67 RTW_CMD_THREAD
30497 root 20 0 9384 4584 3992 S 0.6 3.7 0:02.24 sshd
3065 snmp 20 0 9632 3680 2268 S 0.3 3.0 8:47.95 snmpd
3275 root 20 0 834m 6168 3708 S 0.3 5.0 4:10.88 wb-mqtt-confed
3299 root 20 0 26900 2532 1924 S 0.3 2.1 3:36.31 wb-mqtt-lirc
3457 root -2 0 1740 1704 1392 S 0.3 1.4 3:53.65 watchdog
28307 root 20 0 1864 1408 1332 S 0.3 1.1 0:02.54 logger
1 root 20 0 2160 1240 1140 S 0.0 1.0 0:04.98 init
2 root 20 0 0 0 0 S 0.0 0.0 0:00.04 kthreadd
3 root 20 0 0 0 0 R 0.0 0.0 2:22.82 ksoftirqd/0
5 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 kworker/0:0H
7 root rt 0 0 0 0 S 0.0 0.0 0:01.80 watchdog/0
8 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 khelper
9 root 20 0 0 0 0 S 0.0 0.0 0:00.01 kdevtmpfs
10 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 perf
11 root 20 0 0 0 0 S 0.0 0.0 0:00.09 khungtaskd
12 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 writeback
13 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 crypto
14 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 kintegrityd
15 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 bioset
16 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 kblockd
18 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 rpciod
19 root 20 0 0 0 0 S 0.0 0.0 0:00.87 kswapd0
20 root 20 0 0 0 0 S 0.0 0.0 0:00.00 fsnotify_mark
21 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 nfsiod
35 root 20 0 0 0 0 S 0.0 0.0 0:15.42 mmcqd/0
36 root 20 0 0 0 0 S 0.0 0.0 0:00.00 mmcqd/0boot0
37 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 ipv6_addrconf
38 root 20 0 0 0 0 S 0.0 0.0 0:00.00 mmcqd/0boot1
39 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 deferwq
40 root 20 0 0 0 0 S 0.0 0.0 0:00.02 jbd2/mmcblk0p2-
41 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 ext4-rsv-conver
155 root 20 0 2880 1648 1236 S 0.0 1.3 0:01.34 udevd
228 root 20 0 0 0 0 S 0.0 0.0 0:03.39 spi32766
270 root 20 0 2872 1644 1220 S 0.0 1.3 0:00.73 udevd
271 root 20 0 2872 1528 1116 S 0.0 1.2 0:00.03 udevd
290 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 ci_otg
339 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 cfg80211
1334 root 20 0 0 0 0 S 0.0 0.0 0:08.64 jbd2/mmcblk0p6-
1335 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 ext4-rsv-conver
1447 root 0 -20 0 0 0 S 0.0 0.0 0:00.00 kworker/0:1H
2296 root 20 0 2764 1396 1240 S 0.0 1.1 0:00.03 wb-watch-config
2309 root 20 0 1840 1080 980 S 0.0 0.9 0:00.01 inotifywait
2310 root 20 0 2764 1068 908 S 0.0 0.9 0:00.00 wb-watch-config
2325 root 20 0 1704 1272 1192 S 0.0 1.0 0:00.01 startpar
2409 root -51 0 0 0 0 S 0.0 0.0 0:31.43 irq/136-0-0027
2446 root -51 0 0 0 0 S 0.0 0.0 0:09.81 irq/136-0-0026
2485 root -51 0 0 0 0 S 0.0 0.0 0:09.54 irq/136-0-0022
2524 root -51 0 0 0 0 S 0.0 0.0 0:09.50 irq/136-0-0024
2563 root -51 0 0 0 0 S 0.0 0.0 0:10.12 irq/136-0-0020
2663 root 20 0 2328 1140 1064 S 0.0 0.9 0:00.17 klogd
2665 root 20 0 2328 1256 1192 S 0.0 1.0 1:16.55 syslogd

Но даже тут видно, что основной пожиратель - wb-rules. Предлагаю пока не углубляться в сторону (хотя это тоже стоит рассмотреть, но позднее), а акцентировать внимание именно на том скрипте, что я привел - тут все четко - включаю это правило и сразу резко возрастает утилизация процессора.

Все верно Вы говорите. Игрался с параметром “Delay before accessing the device (ms)” для модуля - при его увеличении загрузка действительно снижается (сейчас по умолчанию - 100). Снижать общий Poll interval не могу, как и увеличивать сильно задержку на WP3084 - начинаются проблемы у дискретных модулей с отработкой нажатия физических кнопок. Аналогично было тут: Не срабатывают кнопки Почему настройки одного устройства сказываются на других - пока понять не могу, разбираюсь. Думаю, это будет тема для другого разговора. Пока решаю проблемы скрипта. Какой-нибудь возможности средствами скрипта обсчитывать данные с сильно меньшей частотой есть? Я не сильно большой знаток в этом деле… но меня бы устроило, если бы это происходило раз в несколько секунд, а не по факту изменения “сырой” переменной.

Все обновлено, в том числе и wb-mqtt-serial.

“Delay before accessing the device (ms)” - это не то, это не нужно трогать.

Ну я так понимаю, что кнопки у вас не на WP3084 заведены? Поставьте poll_interval у WP3084 в 500ms, у остального оставьте в дефолтный 0 (т.е. на макс. скорости) и всё.
Кнопки опрашиваются часто, аналоговые значения редко.

Если вы именно Delay before accessing the device (ms) ставили, то так и должно быть. Смысл этого параметра в установке гарантированного периода тишины перед опросом девайса, это иногда требуется для глючных устройств.

Poll Interval - это другое, его использует планировщик. Если по одному устройству он большой, то только это устройство будет редко опрашиваться.

Это не проблема скрипта

Правила в wb-rules привязываются к событиям, поэтому они выполняются при каждом обновлении соответствующей переменной.
Если вы всё-таки хотите бороться с симптомами, а не с проблемой, то можно вместо правил, привязанных к событиям, в wb-rules написать просто периодическое правило для конвертации.
Т.е. что-то вроде

defineRule("periodic_ps_conversion", {
  when: cron("@every 1s"),
  then: function () {
   dev["power_supply"]["PS1 current"] = ((dev["wp3084_7/VI_7"] - dev["wb-adc"]["5Vout"]/2) * 10).toFixed(2);
   dev["power_supply"]["PS1 voltage"] = (dev["wp3084_7/VI_8"] * 1.699).toFixed(2);
 }
});

А что надо? Этот параметр тоже сказывается на загрузке. Примерно пропорционально его величине.

Конечно на другие модули. Это как поставить? Я вижу только poll interval 10ms на всю шину. Может быть надо в JSON у нужного модуля добавить что-нибудь такое: “poll_interval”: 500?

Понятно. Кстати, изделия от WP отрабатывают без ошибок на серийном порту даже если этот параметр вообще в 0 поставить (при 100 по умолчанию), что я и сделал для дискретных модулей (были проблемы с теми же кнопками без этого, так кнопки стали нормально работать), хотя у других моих modbus устройств (диммер, счетчик и термостат) при этом сразу валятся ошибки.

Понял, спасибо. Как крайний случай буду иметь ввиду. Конечно, хотелось бы победить проблему :slight_smile:

Итак, остается понять как и где сделать настройку poll interval для конкретного устройства. В JSON?

Попробовал добавить через JSON:

Изменений в утилизации процессора нет. Циферки показаний как скакали, так и продолжают скакать куда чаще, чем 1 секунда.

Мне кажется у вас не последний wb-mqtt-serial. Если последний, то Poll Interval можно было бы добавить через properties у девайса

Да, Вы оказались правы. Я как-то обычно делаю apt-get update && apt-get upgrage, но при этом wb-mqtt-serial не обновляется… как оказалось. Сделал apt-get update && apt-get install wb-mqtt-serial, обновилось, при этом обновились и другие пакеты. Действительно, появился poll_interval и действительно после установки 1000 циферки стали скакать реже… Но вот случилось нехорошее - после обновления перестали работать все модули расширения и скрипты. При этом в WEB интерфейсе скрипты видятся, а модули нет. Serial устройства - нормально. Перегрузил питанием - и все стало еще хуже. Пропал и WEB интерфейс - 403 Forbidden. Я в трауре… что делать теперь? SSH работает…

Эх, следующий раз читать, с чем именно просит согласиться apt-get

Видимо он так разрешил какой-то конфликт - путём удаления половины софта.

Ставьте обратно:

apt-get install wb-mqtt-serial wb-homa-adc wb-homa-gpio wb-hwconf-manager wb-mqtt-homeui wb-rules

может быть что-то забыл из списка

Так и есть. Вот оно как было:

root@wirenboard:~# apt-get install wb-mqtt-serial
Reading package lists… Done
Building dependency tree
Reading state information… Done
The following packages were automatically installed and are no longer required:
jq libc-dev-bin libc6-dev libevent-2.0-5 libgmp10 liblog4cpp5 linux-libc-dev manpages manpages-dev mqtt-tools python-chardet
python-crypto python-gevent python-greenlet python-gspread python-httplib2 python-oauth2client python-oauthlib python-requests
python-six python-support python-uritemplate tcc ucf
Use ‘apt-get autoremove’ to remove them.
The following extra packages will be installed:
liblog4cpp5 libwbmqtt
The following packages will be REMOVED:
wb-homa-adc wb-homa-gpio wb-homa-w1 wb-hwconf-manager wb-mqtt-db wb-mqtt-homeui wb-mqtt-lirc wb-test-suite
The following NEW packages will be installed:
liblog4cpp5
The following packages will be upgraded:
libwbmqtt wb-mqtt-serial
2 upgraded, 1 newly installed, 8 to remove and 0 not upgraded.
Need to get 231 kB of archives.
After this operation, 11.4 MB disk space will be freed.
Do you want to continue [Y/n]? Y
Get:1 http://releases.contactless.ru/ wheezy/main wb-mqtt-serial armel 1.18 [96.5 kB]
Get:2 http://releases.contactless.ru/ wheezy/main libwbmqtt armel 1.3.4 [17.8 kB]
Get:3 http://httpredir.debian.org/debian/ wheezy/main liblog4cpp5 armel 1.0-4 [117 kB]
Fetched 231 kB in 2s (106 kB/s)
(Reading database … 36817 files and directories currently installed.)
Removing wb-test-suite …
dpkg: warning: while removing wb-test-suite, directory ‘/usr/lib/wb-test-suite/wb5_func_test’ not empty so not removed
dpkg: warning: while removing wb-test-suite, directory ‘/usr/lib/wb-test-suite/common’ not empty so not removed
Removing wb-hwconf-manager …
Stopping initialize Device Tree overlays: wb-hwconf-manager
Unfortunately, overlays unloading is broken … (warning).
If you have removed or replaced modules, please reboot … (warning).
.
Removing wb-homa-adc …
Stopping MQTT Driver for ADC: wb-homa-adc.
Removing wb-homa-gpio …
Stopping MQTT Driver for GPIO-controlled switches: wb-homa-gpio.
Removing wb-homa-w1 …
Removing wb-mqtt-homeui …
Removing wb-mqtt-db …
Removing wb-mqtt-lirc …
Stopping WB LIRC driver: wb-mqtt-lirc.
Selecting previously unselected package liblog4cpp5.
(Reading database … 35668 files and directories currently installed.)
Unpacking liblog4cpp5 (from …/liblog4cpp5_1.0-4_armel.deb) …
Preparing to replace wb-mqtt-serial 1.16.1 (using …/wb-mqtt-serial_1.18_armel.deb) …
Unpacking replacement wb-mqtt-serial …
Preparing to replace libwbmqtt 1.3.2 (using …/libwbmqtt_1.3.4_armel.deb) …
Unpacking replacement libwbmqtt …
Setting up liblog4cpp5 (1.0-4) …
Setting up libwbmqtt (1.3.4) …
Setting up wb-mqtt-serial (1.18) …
Installing new version of config file /etc/wb-mqtt-serial.conf.sample …
root@wirenboard:~#

Объясните, что надо было сделать, чтобы установить обновление и при этом не произошло удаления других пакетов?

Сейчас буду ставить обратно…

Не соглашаться на предложения апт-гета, добавить все пакеты из “will be REMOVED” в список для установки:

apt-get install wb-mqtt-serial wb-homa-adc wb-homa-gpio wb-homa-w1 wb-hwconf-manager wb-mqtt-db wb-mqtt-homeui wb-mqtt-lirc wb-test-suite
1 лайк

Вроде ожило. Спасибо! Изначальный вопрос тоже решился положительно, опрос устройства стал регулироваться через poll_interval и как следствие - снизилась загрузка процессора. Еще раз спасибо!

Есть еще вопросы не по изначальной теме, но как следствие данного обсуждения - как и где узнавать про актуальные обновления, вроде того, что сейчас установил? После обновления wb-mqtt-serial вернулись проблемы с Uniel (оно и понятно отчего - до этого работал serial от Дмитрия). Повторять процедуру правки serial и будет ли когда-нибудь решен этот вопрос хотя бы в варианте Дмитрия?