Перейти к содержанию
    

В общем с AVRами дружу недавно, столкнулся с острой необходимостью использования протокола Modbus RTU (т.к. оборудование уже используют на многих объектах и нужно общение приборов с новыми прошивками работающими по тому же принципу). В общем, надеюсь, найдутся добрые люди, которые смогут мне простому смертному помочь в освоении этого протокола на базе ATMega16. Собственно готовых кодов не нужно, мне б полностью принцип понять применительно к моей задаче. Я кое чего нашел от прежнего программиста, вот все что есть:

 

-------------------------------

Протокол передачи данных ModBus RTU.

Функция для передачи данных: 04 - «read input registers».

Запрашивать 14 регистров начиная с нулевого. Каждый регистр – двухбайтное слово. Обращаю внимание, что в протоколе ModBus все слова передаются старшим байтом вперед. Были случаи что попадалась документация с разными таблицами CRC и разными полиномами. Ниже приведу свои таблицы.

Порядок передаваемых данных:

 

1. Значение A

2. Значение B

3. Значение C

4. Значение D

5. Значение E

6. Значение F

7. Значение G

8. Значение H

9. Значение I

10.Значение J

11.Значение K

12.Значение L

13.Значение M

14.Значение N

 

Запись параметров - 16 (10 Hex) Preset Multiple Registers

Порядок передаваемых данных:

 

1. Значение I

2. Значение J

3. Значение K

4. Значение L

5. Значение M

6. Значение N

 

 

const unsigned char CRCHi[] = {

0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0,

0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,

0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,

0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,

0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1,

0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41,

0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1,

0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,

0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0,

0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40,

0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1,

0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,

0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0,

0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40,

0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,

0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,

0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0,

0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,

0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,

0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,

0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,

0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40,

0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1,

0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,

0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0,

0x80, 0x41, 0x00, 0xC1, 0x81, 0x40};

 

const unsigned char CRCLo[] = {

0x00, 0xC0, 0xC1, 0x01, 0xC3, 0x03, 0x02, 0xC2, 0xC6, 0x06,

0x07, 0xC7, 0x05, 0xC5, 0xC4, 0x04, 0xCC, 0x0C, 0x0D, 0xCD,

0x0F, 0xCF, 0xCE, 0x0E, 0x0A, 0xCA, 0xCB, 0x0B, 0xC9, 0x09,

0x08, 0xC8, 0xD8, 0x18, 0x19, 0xD9, 0x1B, 0xDB, 0xDA, 0x1A,

0x1E, 0xDE, 0xDF, 0x1F, 0xDD, 0x1D, 0x1C, 0xDC, 0x14, 0xD4,

0xD5, 0x15, 0xD7, 0x17, 0x16, 0xD6, 0xD2, 0x12, 0x13, 0xD3,

0x11, 0xD1, 0xD0, 0x10, 0xF0, 0x30, 0x31, 0xF1, 0x33, 0xF3,

0xF2, 0x32, 0x36, 0xF6, 0xF7, 0x37, 0xF5, 0x35, 0x34, 0xF4,

0x3C, 0xFC, 0xFD, 0x3D, 0xFF, 0x3F, 0x3E, 0xFE, 0xFA, 0x3A,

0x3B, 0xFB, 0x39, 0xF9, 0xF8, 0x38, 0x28, 0xE8, 0xE9, 0x29,

0xEB, 0x2B, 0x2A, 0xEA, 0xEE, 0x2E, 0x2F, 0xEF, 0x2D, 0xED,

0xEC, 0x2C, 0xE4, 0x24, 0x25, 0xE5, 0x27, 0xE7, 0xE6, 0x26,

0x22, 0xE2, 0xE3, 0x23, 0xE1, 0x21, 0x20, 0xE0, 0xA0, 0x60,

0x61, 0xA1, 0x63, 0xA3, 0xA2, 0x62, 0x66, 0xA6, 0xA7, 0x67,

0xA5, 0x65, 0x64, 0xA4, 0x6C, 0xAC, 0xAD, 0x6D, 0xAF, 0x6F,

0x6E, 0xAE, 0xAA, 0x6A, 0x6B, 0xAB, 0x69, 0xA9, 0xA8, 0x68,

0x78, 0xB8, 0xB9, 0x79, 0xBB, 0x7B, 0x7A, 0xBA, 0xBE, 0x7E,

0x7F, 0xBF, 0x7D, 0xBD, 0xBC, 0x7C, 0xB4, 0x74, 0x75, 0xB5,

0x77, 0xB7, 0xB6, 0x76, 0x72, 0xB2, 0xB3, 0x73, 0xB1, 0x71,

0x70, 0xB0, 0x50, 0x90, 0x91, 0x51, 0x93, 0x53, 0x52, 0x92,

0x96, 0x56, 0x57, 0x97, 0x55, 0x95, 0x94, 0x54, 0x9C, 0x5C,

0x5D, 0x9D, 0x5F, 0x9F, 0x9E, 0x5E, 0x5A, 0x9A, 0x9B, 0x5B,

0x99, 0x59, 0x58, 0x98, 0x88, 0x48, 0x49, 0x89, 0x4B, 0x8B,

0x8A, 0x4A, 0x4E, 0x8E, 0x8F, 0x4F, 0x8D, 0x4D, 0x4C, 0x8C,

0x44, 0x84, 0x85, 0x45, 0x87, 0x47, 0x46, 0x86, 0x82, 0x42,

0x43, 0x83, 0x41, 0x81, 0x80, 0x40};

 

Надеюсь на помощь!

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

А вопрос-то, собственно, в чём?

freemodbus.berlios.de - готовый модуль.

Встраивается буквально в 3 шага.

Если хотите разобраться с имеющейся у вас реализацией, задавайте конкретные вопросы.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Вопросов много.. За ссылку конечно спасибо, но видимо пока я там ничего понять не смогу. Про модбас знаю только что слово такое есть, узнать бы принцип протокола именно RTU (для моей задачи, глобально протокол осваивать нет необходимости пока). Также как высчитывать CRC16? (как я понял его нужно высчитывать используя две таблицы, которые приведены выше), т.е. полный алгоритм подсчета что с чем складывать куда что сдвигать и при каких условиях. Какие временные интервалы выдерживать при посылках/ожиданиях ответа. Пока только умею атмегой посылать/принимать байты с заданной скоростью без какого либо протокола..) Вобщем, у меня есть формат посылки, которую нужно отправить в прибор, в ответ на которую прибор должен прислать все необходимые данные.. Видимо аццкая жара которая неделю влияет на мозги (белок то сворачивается) и мне б "на пальцах для тупых" основные принципы протокола (по каким правилам что передавать и когда чего принимать) и принцип подсчета црц16 исходя из приведенных таблиц

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Если тупо на пальцах именно про RTU, то основная фишка там - это таймаут 3.5 символа по приёму пакета.

То есть, если между двумя любыми байтами разрыв больше, то это считается концом пакета.

В freemodbus это реализовано с помощью таймера.

По приёму каждого символа заводится таймер на 3.5 символа вперёд, а символ кладётся в буфер.

Если сработал таймер, значит имеем тайм-аут и соответственно конец пакета.

Вызывается обработчик, который анализирует целостность пакета (CRC, заголовок, код команды, длина пакета) и выставляет соответствующие флаги, которые затем обрабатываются функцией eMBpoll(), которая, в свою очередь, вызывает CallBack-функции для обработки команд.

Вычисление CRC производится в функции usMBCRC16 (./RTU/mbcrc.c)

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

В общем с AVRами дружу недавно...

Admin:

Тема перенесена, как не имеющая отношения к AVR. Напомю, так-же, что на форуме есть раздел "Для начинающих" и поиск.

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Почитайте это и вот это.

 

Контрольная сумма считается так:

static __flash unsigned char aucCRCHi[] = {
    0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
    0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,
    0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01,
    0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41,
    0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81,
    0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0,
    0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01,
    0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,
    0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
    0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,
    0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01,
    0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
    0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
    0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,
    0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01,
    0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
    0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
    0x40
};

static __flash unsigned char aucCRCLo[] = {
    0x00, 0xC0, 0xC1, 0x01, 0xC3, 0x03, 0x02, 0xC2, 0xC6, 0x06, 0x07, 0xC7, 0x05, 0xC5, 0xC4,
    0x04, 0xCC, 0x0C, 0x0D, 0xCD, 0x0F, 0xCF, 0xCE, 0x0E, 0x0A, 0xCA, 0xCB, 0x0B, 0xC9, 0x09,
    0x08, 0xC8, 0xD8, 0x18, 0x19, 0xD9, 0x1B, 0xDB, 0xDA, 0x1A, 0x1E, 0xDE, 0xDF, 0x1F, 0xDD,
    0x1D, 0x1C, 0xDC, 0x14, 0xD4, 0xD5, 0x15, 0xD7, 0x17, 0x16, 0xD6, 0xD2, 0x12, 0x13, 0xD3,
    0x11, 0xD1, 0xD0, 0x10, 0xF0, 0x30, 0x31, 0xF1, 0x33, 0xF3, 0xF2, 0x32, 0x36, 0xF6, 0xF7,
    0x37, 0xF5, 0x35, 0x34, 0xF4, 0x3C, 0xFC, 0xFD, 0x3D, 0xFF, 0x3F, 0x3E, 0xFE, 0xFA, 0x3A,
    0x3B, 0xFB, 0x39, 0xF9, 0xF8, 0x38, 0x28, 0xE8, 0xE9, 0x29, 0xEB, 0x2B, 0x2A, 0xEA, 0xEE,
    0x2E, 0x2F, 0xEF, 0x2D, 0xED, 0xEC, 0x2C, 0xE4, 0x24, 0x25, 0xE5, 0x27, 0xE7, 0xE6, 0x26,
    0x22, 0xE2, 0xE3, 0x23, 0xE1, 0x21, 0x20, 0xE0, 0xA0, 0x60, 0x61, 0xA1, 0x63, 0xA3, 0xA2,
    0x62, 0x66, 0xA6, 0xA7, 0x67, 0xA5, 0x65, 0x64, 0xA4, 0x6C, 0xAC, 0xAD, 0x6D, 0xAF, 0x6F,
    0x6E, 0xAE, 0xAA, 0x6A, 0x6B, 0xAB, 0x69, 0xA9, 0xA8, 0x68, 0x78, 0xB8, 0xB9, 0x79, 0xBB,
    0x7B, 0x7A, 0xBA, 0xBE, 0x7E, 0x7F, 0xBF, 0x7D, 0xBD, 0xBC, 0x7C, 0xB4, 0x74, 0x75, 0xB5,
    0x77, 0xB7, 0xB6, 0x76, 0x72, 0xB2, 0xB3, 0x73, 0xB1, 0x71, 0x70, 0xB0, 0x50, 0x90, 0x91,
    0x51, 0x93, 0x53, 0x52, 0x92, 0x96, 0x56, 0x57, 0x97, 0x55, 0x95, 0x94, 0x54, 0x9C, 0x5C,
    0x5D, 0x9D, 0x5F, 0x9F, 0x9E, 0x5E, 0x5A, 0x9A, 0x9B, 0x5B, 0x99, 0x59, 0x58, 0x98, 0x88,
    0x48, 0x49, 0x89, 0x4B, 0x8B, 0x8A, 0x4A, 0x4E, 0x8E, 0x8F, 0x4F, 0x8D, 0x4D, 0x4C, 0x8C,
    0x44, 0x84, 0x85, 0x45, 0x87, 0x47, 0x46, 0x86, 0x82, 0x42, 0x43, 0x83, 0x41, 0x81, 0x80,
    0x40
};

unsigned int
usMBCRC16(unsigned char * pucFrame, unsigned int usLen )
{
    unsigned char   ucCRCHi = 0xFF;
    unsigned char   ucCRCLo = 0xFF;
    int             iIndex;

    while( usLen-- )
    {
        iIndex = ucCRCLo ^ *( pucFrame++ );
        ucCRCLo = ucCRCHi ^ (aucCRCHi[iIndex] );
        ucCRCHi = ( aucCRCLo[iIndex] );
    }
    return ucCRCHi << 8 | ucCRCLo;
}

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Почитайте это и вот это.

 

Контрольная сумма считается так:

 

Благодарю за пример, сегодня уже находил что-то подобное, я пишу на ассемблере пока только, с Си имею дело только когда чего-нить в visual-среде под винду пишу (ну это боловство пока только). В начале я как понимаю мы объявляем переменные а дальше крах мозга...)))) я заранее пршу прощения, так стыдно.....))) ну и собсно исходя из того, что я пишу на машинном уровне мне б понять как соотносится принятый байт со значениями в этих таблицах и как в итоге получается этот несчастный црц.. я не зря "на пальцах для тупых" попросил, но я не безнадежен....)) в последний раз я так мучался когда не знал с чего начать контроллеры осваивать))) ну вот освоил 51, AVR, хочу еще ARM, но тут без Си никак (последнее - енто лирическое отступление, мона пропустить). Вобщем, в идеале, я принимаю все байты посылки, считаю црц, если он правильный то проверяю 1й байт, если он совпадает с адресом прибора, то по функции выдаю ответ с данными, если во время приема возникла тишина в 3,5 байта (исходя из скорости) то полученные данные считаю полностью принятой посылкой (ну и дальше сначала как описал), правильно глаголю? осталос только с этими таблицами разобраться на машинном уровне..

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

unsigned int
usMBCRC16(unsigned char * pucFrame, unsigned int usLen )  
// pucFrame - указатель на начало буфера (адрес)
// usLen - длина пакета 
{
    unsigned char   ucCRCHi = 0xFF;  // старший байт црц
    unsigned char   ucCRCLo = 0xFF;  // младший
    int             iIndex;

    while( usLen-- )  // цикл, usLen уменьшается на 1 при каждой итерации
    {
        iIndex = ucCRCLo ^ *( pucFrame++ );  // ксорим ucCRCLo  и байт, на который указывает pucFrame. 
        // полученное значение будет индексом iIndex в таблицах. pucFrame инкрементируется.
        ucCRCLo = ucCRCHi ^ (aucCRCHi[iIndex] );  // ксорим ucCRCHi и значение из таблицы aucCRCHi с индексом iIndex.
        ucCRCHi = ( aucCRCLo[iIndex] );  // ucCRCHi равно значению из таблицы aucCRCLo с индексом iIndex
    }
    return ucCRCHi << 8 | ucCRCLo;  // Возвращаем старший и младший байт CRC в виде 16-разрядного слова
}

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Возвращаем старший и младший байт CRC в виде 16-разрядного слова

 

Вот спасибо хорошо положите на камод.. Епт, все оказывается не так сложно. Спасибо добрый человек за разжовывание..)) на бумажке посчитал по этому методу (через таблички) и все получается, ну пока для посылки всего из одного байта посчитал)) Только после подсчета получается какбы итоговое значение младшего байта CRC ставится старшим байтом, а старшее итоговое ставится младшим, круто блин

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Вот спасибо хорошо положите на камод.. Епт, все оказывается не так сложно. Спасибо добрый человек за разжовывание..))

Да незачем.

Учите Си, пригодится в хозяйстве!

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

попробовал я с двухбайтной посылкой на бумажке посчитать.. может кому пригодится, с такими же проблемами как у меня с мосКом))) допустим я передаю два байта 01 04. В программке работы с com-портом CRC16 получилось равным 01 E3 т.е. в бинарном коде 00000001 11100011.

 

Изначальные условия у меня такие: ucCRCHi = 11111111, ucCRCLo = 11111111, iIndex = 0, pucFrame = 0, usLen = 2, таблицы вышеуказанные

 

выполняем действия пока usLen не обнулится:

 

---обрабатываем 1й байт (0x01)

 

iIndex = 11111111 xor 00000001 = 11111110 (т.е. дес. 254)

ucCRCLo = ucCRCHi xor aucCRCHi{iIndex=254} = 11111111 xor 0x81 (10000001) = 01111110

ucCRCHi = aucCRCLo{iIndex=254} = 10000000 (т.е. 0x80)

 

---обрабатываем 2й байт (0x04)

 

iIndex = 01111110 xor 00000100 = 01111010 (т.е. дес. 122)

ucCRCLo = ucCRCHi xor aucCRCHi{iIndex=122} = 10000000 xor 0x81 (10000001) = 00000001

ucCRCHi = aucCRCLo{iIndex=122} = 11100011 (т.е. 0xE3)

 

итого получается ucCRCLo + ucCRCHi = 01 E3, те самые что выдала программка в начале

 

всем большое СПАСИБО

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Почему никто из отвечающих не дал ссылки на текст самой спецификации? Как я понял, вопрошающий ее не читал. Ссылка на сайт modbus.org.

MODBUS Protocol Specification

MODBUS Over Serial Line FOR LEGACY APPLICATIONS ONLY

Modbus Serial Line Protocol and Implementation Guide V1.02

MODBUS TCP/IP

Object Messaging Specification for the Modbus TCP Protocol

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

на железе сегодня полностью отладил прием 8ми байт (1й - адрес, 2й - функция 3й4й - начальный адрес регистров, 5й6й - кол-во регистров, 7й8й - CRC16), CRC16 считает, при скорости 57600 выжидаю 70мс (3.5/57.6 = 60.8мс, но я решил для верности немножко с запасом) после приема очередного байта, если время прошло считаю как новый фрэйм, также сделал что если приходит больше 8ми байт в одном фрэйме, то каждый 9тый воспринимается как начало нового 8ми байтого фрэйма, короче радости полные штаны))

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

также сделал что если приходит больше 8ми байт в одном фрэйме, то каждый 9тый воспринимается как начало нового 8ми байтого фрэйма, короче радости полные штаны))

Это неправильно, в RTU должен быть разрыв 3,5 символа.

Если его нет, то это будет ошибка формата фрейма.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Это неправильно, в RTU должен быть разрыв 3,5 символа.

Если его нет, то это будет ошибка формата фрейма.

 

сделал, теперь молчит если больше 8ми байт. У меня вопрос созрел по самому модбасу. Вобщем как я и говорил у меня ни исходников предыдущей версии прошивки нету ни связи с тем программистом который ее создавал. Так вот, значит посылаю я прибору со старой прошивкой строку:

 

01 04 00 00 00 01 31 CA

 

а он мне в ответ

 

01 04 08 00 00 00 00 00 00 FF FF 25 BD

 

Возникает у меня как минимум 2 вопроса

 

1. Что за 08 и откуда оно берется? Эт явно что-то с модбасом связано

2. Почему так много данных выдает (пускай они даже 00 00), судя по всему он выдает четыре 2хбайтных параметра 00 00 00 00 00 00 FF FF, хотя я в исходящей посылке даю прибору инструкцию на передачу всего одного слова данных начиная с 00 00 адреса. Я предполагал, что ответ будет примерно таким:

 

01 04 xx xx CRC16

 

Поможите люди опытныя..)

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...