analogRead "ломает" ModBus
- Войдите на сайт для отправки комментариев
Втр, 18/02/2020 - 00:17
#include <ModbusRtu.h>
// assign the Arduino pin that must be connected to RE-DE RS485 transceiver
#define TXEN 17
uint16_t au16data[] = {0,0};
Modbus slave(1, Serial1, TXEN);
void setup() {
Serial1.begin( 115200 ); // baud-rate at 115200
slave.start();
}
void loop() {
slave.poll(au16data, 2);
au16data[REG_TEMPER] = analogRead(A0); // если эта строчка есть, то обмен по ModBus ломается
}
Всем привет.
Похоже, забуксовал на граблях:
Есть скетч, который использует ModBus. Его задача получить значение с определенного канала АЦП и положить в регистр ModBus. Сам Modbus работает безупречно, но лишь до первого использования функции analogRead. Значения читаются, но после этого слей не отвечает мастеру. Осцилла, к сожалению, под руками нет. Может быть есть какой-то очевидный косяк?
Arduino Micro, если это важно...
Что за пин такой - 17?
REG_TEMPER откуда вылезло?
Что за пин такой - 17?
REG_TEMPER откуда вылезло?
Да я код пообрезал...
REG_TEMPER == 0, 17ый пин - кхм... 17ый порт...
Оно работает... Но до того, как я вызываю analogRead.
17й порт это еще хуже.
17й порт это еще хуже.
поменял, не помогло...
#include <ModbusRtu.h> // assign the Arduino pin that must be connected to RE-DE RS485 transceiver #define TXEN 5 #define PWM_1 3 #define PWM_2 4 #define FAN_POWER 8 #define FAN_SPEED_1 12 //9 #define FAN_SPEED_2 11 //10 #define FAN_SPEED_3 10 //11 #define FAN_SPEED_4 9 //12 #define DC_1 7 #define DC_2 6 #define GPIO_10 17 #define GPIO_2 2 enum Regs { REG_FAN_SPEED, REG_PWM_1_PERIOD, REG_PWM_1_DUTY, REG_PWM_2_PERIOD, REG_PWM_2_DUTY, REG_DRY_CON_1, REG_DRY_CON_2, REG_TEMPER, REG_GPIO_1, REG_GPIO_2, REG_SIZE }; // FAN_SPEED, PERIOD_MS, DUTY, uint16_t au16data[REG_SIZE]; Modbus slave(1, Serial1, TXEN); void setup() { memset (au16data, 0, sizeof(au16data)); pinMode(PWM_1, OUTPUT); digitalWrite(PWM_1, LOW); pinMode(PWM_2, OUTPUT); digitalWrite(PWM_2, LOW); // pinMode(GPIO_1, INPUT); // digitalWrite(GPIO_1, HIGH); pinMode(GPIO_2, INPUT); digitalWrite(GPIO_2, HIGH); pinMode(FAN_POWER, OUTPUT); pinMode(FAN_SPEED_1, OUTPUT); pinMode(FAN_SPEED_2, OUTPUT); pinMode(FAN_SPEED_3, OUTPUT); pinMode(FAN_SPEED_4, OUTPUT); pinMode(DC_1, OUTPUT); pinMode(DC_2, OUTPUT); Serial1.begin( 115200 ); // baud-rate at 115200 Serial.begin( 115200 ); // baud-rate at 115200 // Serial.println(analogRead(A0)); slave.start(); } void processFanSpeed(uint16_t regime) { switch (regime) { case 1: digitalWrite(FAN_SPEED_1, HIGH); digitalWrite(FAN_SPEED_2, LOW); digitalWrite(FAN_SPEED_3, LOW); digitalWrite(FAN_SPEED_4, LOW); delay(10); digitalWrite(FAN_POWER, HIGH); break; case 2: digitalWrite(FAN_SPEED_1, LOW); digitalWrite(FAN_SPEED_2, HIGH); digitalWrite(FAN_SPEED_3, LOW); digitalWrite(FAN_SPEED_4, LOW); delay(10); digitalWrite(FAN_POWER, HIGH); break; case 3: digitalWrite(FAN_SPEED_1, LOW); digitalWrite(FAN_SPEED_2, LOW); digitalWrite(FAN_SPEED_3, HIGH); digitalWrite(FAN_SPEED_4, LOW); delay(10); digitalWrite(FAN_POWER, HIGH); break; case 4: digitalWrite(FAN_SPEED_1, LOW); digitalWrite(FAN_SPEED_2, LOW); digitalWrite(FAN_SPEED_3, LOW); digitalWrite(FAN_SPEED_4, HIGH); delay(10); digitalWrite(FAN_POWER, HIGH); break; default: digitalWrite(FAN_POWER, LOW); digitalWrite(FAN_SPEED_1, LOW); digitalWrite(FAN_SPEED_2, LOW); digitalWrite(FAN_SPEED_3, LOW); digitalWrite(FAN_SPEED_4, LOW); break; } } void processPwm_1(uint16_t *period, uint16_t *duty) { static int value = LOW; static long previousMillis = 0; if (*period > 300) { *period = 0; *duty = 0; } if (*duty > 100) { *period = 0; *duty = 0; } long _duty = *period * *duty * 10; long _period = *period * 1000; if (millis() - previousMillis < _duty) digitalWrite(PWM_1, HIGH); else digitalWrite(PWM_1, LOW); if (millis() - previousMillis > _period) previousMillis = millis(); } void processPwm_2(uint16_t *period, uint16_t *duty) { static int value = LOW; static long previousMillis = 0; if (*period > 300) { *period = 0; *duty = 0; } if (*duty > 100) { *period = 0; *duty = 0; } long _duty = *period * *duty * 10; long _period = *period * 1000; if (millis() - previousMillis < _duty) digitalWrite(PWM_2, HIGH); else digitalWrite(PWM_2, LOW); if (millis() - previousMillis > _period) previousMillis = millis(); } int16_t getTemp() { int16_t value = analogRead(0); // Serial.println(value); return value; } void loop() { slave.poll(au16data, REG_SIZE); processFanSpeed(au16data[REG_FAN_SPEED]); processPwm_1(&(au16data[REG_PWM_1_PERIOD]), &(au16data[REG_PWM_1_DUTY])); processPwm_2(&(au16data[REG_PWM_2_PERIOD]), &(au16data[REG_PWM_2_DUTY])); // au16data[REG_GPIO_1] = digitalRead(GPIO_1); au16data[REG_GPIO_2] = digitalRead(GPIO_2); // au16data[REG_TEMPER] = getTemp(); digitalWrite(DC_1, au16data[REG_DRY_CON_1]); digitalWrite(DC_2, au16data[REG_DRY_CON_2]); }Целиком...
А с каких пор нулевой пин стал аналоговым?
А с каких пор нулевой пин стал аналоговым?
A0, конечно.
но это ничего не меняет.
Так "модбас ломается" только от analogRead в строке 176 или от любого, например в строке 164?
Если gettemp просто вызывать в лупе, но не сохранять в массиве.
А с каких пор нулевой пин стал аналоговым?
Да всю жизнь был! Как то слабовато, дядя. Зато одни понты.
А с каких пор нулевой пин стал аналоговым?
Да всю жизнь был!
Никада нулевой пин аналоговым не был. Был и есть четырнаццатый, он же A0.
Мы вещаем за то, что это
164int16_t value = analogRead(0);неправильноА с каких пор нулевой пин стал аналоговым?
Да всю жизнь был!
Никада нулевой пин аналоговым не был. Был и есть четырнаццатый, он же A0.
Мы вещаем за то, что это
164int16_t value = analogRead(0);неправильноint analogRead(uint8_t pin) { ... if (pin >= 14) pin -= 14; // allow for channel or pin numbersДед, 0 - это не пин, а канал АЦП для analogRead. А0 == 0.
ну лана, ошибся я, ну дак я и не настаиваю, зачем я буду спорить с умными людями? :)
Оправдываясь, ориентировался на ватэто, там нигде за 0 ничего не сказано, только за "A0 to A5 on most boards"
https://www.arduino.cc/reference/en/language/functions/analog-io/analogread/
Вызов analogRead ломает модбас вне зависимости от аргументов и сохраняем ли мы возвращаемое значение или нет.
Если вызывать в setup - тоже самое.
Мой косяк. Причём аппаратный! Был коротыш между 3.3В и AREF.