2 / 2 / 1
Регистрация: 10.11.2016
Сообщений: 94
1

Циклическое чтение информации через RS232 с использованием goto

13.05.2017, 20:21. Показов 2850. Ответов 18
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
Всем доброго времени суток!
Перейду сразу к делу, есть два фотоприемника (ФП), которые считывают данные при засветки их лазером. Оба ФП подключены к блоку управления, тот в свою очередь подключается к ПК по Com порту. Задача импульсно в течении определенного времени считывать данные с ФП и передавать через Com порт и записывать в массив данных.

Сам процесс считывания уже реализован, но по всей видимости неверно. Есть так же уже реализованное ПО для той же самой задачи но на Cи, нужно переписать функцию для С++ либо написать свою.
Я попробовал написать свою и столкнулся с проблемой использования так называемых "меток" и оператора goto. Зачем, собственно, использовать те самые метки. Отвечаю - обмен данными через ком порт идет следующим образом: с ПК отсылается байт из 9 битов, в ответ приходит такой же байт но с измененными (если это нужно) данными. А оператор goto нужен для того чтобы постоянно отправлять байты, до тех пор пока блок не откликнется прислав в ответном байте измененный бит (8 бит), это даст нам понять что он готов передать данные, потом отправляем ему пустой байт по определенному адресу (0xdb) и в ответ прилетает такой же байт, но с нужными данными, затем работа устройства повторяется указанное пользователем время и количество замера данных.

Основная проблема в том, что я, как новичек, не совсем понимаю как работать с goto, а обычный цикл здесь не воспринимается устройством (мы зависим от его быстродействия), ну и в уже работающей программе на Си как раз используются эти "метки".

Прошу помощи в выявлении ошибок в коде, на основании логов (во вложенных файлах - логи обмена данными по RS232 во время проведения эксперимента) Write и Read логов записанных в порт и считанных с него соответственно.
А так же прилагаю код правильной и рабочей реализации этой задачи на Си и неправильно работающий код на С++.

Рабочий код на Си:
C
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
char YesStop=0;
char SSS[80];
 
unsigned Ready;
int W;
 
Ready=1;
 
byte Cur_Count;
 
BOOL Read_ADC_Expos(int *Data_ADC_1,int *Data_ADC_2 )
{
 
int W;
byte Ready;
 
loop:
if (YesStop) return TRUE;
 
Write_Data[0]=0x81; // читаем тек счетчик и сравниваем c Cur_Count
Write_Data[1]=0;
Write_Data[2]=0xd6;
Write_Data[3]=0;
Write_Data[4]=0;
Write_Data[5]=0;
Write_Data[6]=1;
 
if (!Send_Pack(Write_Data,Read_Data)) return FALSE;
 
Ready = Read_Data[6];
 
if (Ready!=Cur_Count)  //  можно считывать данные  
{
Cur_Count=Ready;
 
Write_Data[0]=0xe1; // читаем
Write_Data[1]=0;
Write_Data[2]=0xdb;
Write_Data[3]=0;
Write_Data[4]=0;
Write_Data[5]=0;
Write_Data[6]=0;
 
if (!Send_Pack(Write_Data,Read_Data)) return FALSE;
 
W=Read_Data[5];
W&=0x0f;
W<<=8; 
 
W+=Read_Data[6];
*Data_ADC_2 = (int)(((double)W - BSig)/(ASig-BSig)*4000);
 
W=Read_Data[3];
W&=0x0f;
W<<=8; 
 
W+=Read_Data[4];
 
*Data_ADC_1 = (int)(((double)W - BRef)/(ARef-BRef)*4000); 
 
sprintf(SSS," ADC_1 = %d ADC_2 = %d ",*Data_ADC_1,*Data_ADC_2);
 
WriteLog(SSS);
 
return TRUE;
}
 
else // Ready = Cur_Count
{
if (YesStop) return TRUE; 
 
goto loop;
}
 
}
 
 
BOOL White_End_Pause(byte *Cur_Count)
{
 
int W;
byte Ready;
 
loop:
 
if (YesStop) return TRUE;
 
Write_Data[0]=0x81; // читаем тек счетчик и сравниваем c Cur_Count
Write_Data[1]=0;
Write_Data[2]=0xd6;
Write_Data[3]=0;
Write_Data[4]=0;
Write_Data[5]=0;
Write_Data[6]=1;
 
if (!Send_Pack(Write_Data,Read_Data)) return FALSE;
 
Ready = Read_Data[6];
 
if (Ready==*Cur_Count) 
{
 
//----------------------------------------------- надо ли что то делать 
 
goto loop;    //  можно считывать данные  
 
 
}
 
else // Ready! = Cur_Count
{
 
*Cur_Count=Ready;
    
    return TRUE; 
 
}
 
}
Не рабочий код на плюсах с указанием до какого момента работает, а с какой строки уже нет:
C++ (Qt)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
QByteArray TabWindow::setDelay(unsigned char adress, unsigned short delay) //функция формирования байтов задержки
{
    unsigned char sixb, sevenb;
    sixb=(delay>>8)&0xff;
    sevenb=(delay&0xff);
    QByteArray resDelay;
    resDelay.resize(9);
    resDelay[0] = 0x55;
    resDelay[1] = 0x21;
    resDelay[2] = 0;
    resDelay[3] = adress;
    resDelay[4] = 0;
    resDelay[5] = 0;
    resDelay[6] = sixb;
    resDelay[7] = sevenb;
    resDelay[8] = resDelay[1];
    for (int i=2; i<8; i++)
        resDelay[8]=resDelay[8]+resDelay[i];
    return resDelay;
}
 
 
void TabWindow::on_expButton_clicked() //функция эксперимента
{
    //открытие и установка параметром Com порта
    com1->open(QIODevice::ReadWrite);
    com1->setFlowControl(QSerialPort::NoFlowControl);
    com1->setBaudRate(QSerialPort::Baud115200);
    com1->setStopBits(QSerialPort::OneStop);
    com1->setDataBits(QSerialPort::Data8);
    com1->setDataTerminalReady(false);
    com1->clear();
 
    //считывание параметров задержки из главного окна программы
    zad1in=ui->zad1LE->text().toInt();
    zad2in=ui->zad2LE->text().toInt();
    zad3in=ui->zad3LE->text().toInt();
    expTime=2*ui->expTimeLE->text().toInt();
 
    //выделение и изменение размера переменных массивов 
    wdelay1.resize(9);
    wdelay2.resize(9);
    wdelay3.resize(9);
 
    testRes1.resize(9);
    testRes2.resize(9);
    testRes3.resize(9);
 
    //приминение функции формирования байтов задержки
    wdelay1=setDelay(0xDF, (unsigned short)zad1in);
    wdelay2=setDelay(0xE1, 3);
    wdelay3=setDelay(0xE3, (unsigned short)zad2in);
 
    //запись байтов задержки
    com1->write(wdelay1);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    testRes1 = com1->readAll();
 
    com1->write(wdelay2);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    testRes2 = com1->readAll();
 
    com1->write(wdelay3);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    testRes3 = com1->readAll();
    
    //создание байтов алгоритма эксперимента
    flagRes1.resize(9);
    flagRes2.resize(9);
 
    unsigned char sixbexp, sevenbexp;
    sixbexp=(expTime>>8)&0xff;
    sevenbexp=(expTime&0xff);
    flag1.resize(9);
    flag1[0]=0x55;
    flag1[1]=1;
    flag1[2]=1;
    flag1[3]=0x0d;
    flag1[4]=0;
    flag1[5]=0;
    flag1[6]=sixbexp;
    flag1[7]=sevenbexp;
    flag1[8]=flag1[1];
    for (int i=2; i<8; i++)
        flag1[8]=flag1[8]+flag1[i];
 
    unsigned char sixbp, sevenbp;
    sixbp=(zad3in>>8)&0xff;
    sevenbp=(zad3in&0xff);
    flag2.resize(9);
    flag2[0]=0x55;
    flag2[1]=1;
    flag2[2]=1;
    flag2[3]=0x21;
    flag2[4]=0;
    flag2[5]=0;
    flag2[6]=sixbp;
    flag2[7]=sevenbp;
    flag2[8]=flag2[1];
    for (int i=2; i<8; i++)
        flag2[8]=flag2[8]+flag2[i];
 
    //запись флагов с параметрами эксперимента
    com1->write(flag1);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    flagRes1 = com1->readAll();
 
    com1->write(flag2);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    flagRes2 = com1->readAll();
 
    int N=expTime;
 
    expSignal.resize(1);
 
    //формирование байтов на считывание данных во время эксперимента
    //Experiment writepack 1
    expWrite1.resize(9);
    expWrite1[0] = 0x55;
    expWrite1[1] = 1;
    expWrite1[2] = 0;
    expWrite1[3] = 0xc2;
    expWrite1[4] = 0;
    expWrite1[5] = 0;
    expWrite1[6] = 0;
    expWrite1[7] = 1;
    expWrite1[8] = expWrite1[1];
    for (int i=2; i<8; i++)
        expWrite1[8]=expWrite1[8]+expWrite1[i];
 
    //Experiment writepack 2
    expWrite2.resize(9);
    expWrite2[0] = 0x55;
    expWrite2[1] = 0x81;
    expWrite2[2] = 0;
    expWrite2[3] = 0xc2;
    expWrite2[4] = 0;
    expWrite2[5] = 0;
    expWrite2[6] = 0;
    expWrite2[7] = 0;
    expWrite2[8] = expWrite2[1];
    for (int i=2; i<8; i++)
        expWrite2[8]=expWrite2[8]+expWrite2[i];
 
    //Experiment readpack 1
    expRead1.resize(9);
    expRead1[0] = 0x55;
    expRead1[1] = 0x81;
    expRead1[2] = 0;
    expRead1[3] = 0xD6;
    expRead1[4] = 0;
    expRead1[5] = 0;
    expRead1[6] = 0;
    expRead1[7] = 1;
    expRead1[8] = expRead1[1];
    for (int i=2; i<8; i++)
        expRead1[8]=expRead1[8]+expRead1[i];
 
    //Experiment readpack 2
    expRead2.resize(9);
    expRead2[0] = 0x55;
    expRead2[1] = 0xE1;
    expRead2[2] = 0;
    expRead2[3] = 0xDB;
    expRead2[4] = 0;
    expRead2[5] = 0;
    expRead2[6] = 0;
    expRead2[7] = 0;
    expRead2[8] = expRead2[1];
    for (int i=2; i<8; i++)
        expRead2[8]=expRead2[8]+expRead2[i];
 
 
    ARef = 4000;
    BRef = 0;
    ASig = 4000;
    BSig = 0;
    QFile adcFile("ADC data.csv");
 
 
    expResult.resize(9);
    expResultP.resize(9);
    
    //запись байтов по адресу 0xC2 для начала стадии считывания данных
    com1->write(expWrite1);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    expResult = com1->readAll();
 
    //с данной строки логи отправляемые и получаемые в ответ программой на С++ не совпадают с логами на Си 
    //ошибка где то ниже
    int count=0;
    expSignal[0]=count;
    while ((int)expSignal[0]<14)
    {
    com1->write(expWrite2);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    expResult = com1->readAll();
    //expSignal[0]=count+1;
 
    //отправление байта для проверки можно ли проводить считывание по адресу 0хd6
    flag1:
    com1->write(expRead1);
    com1->waitForBytesWritten(100);
    com1->waitForReadyRead(100);
    expResultP = com1->readAll();
    expSignal[0] = expResultP[7];
    if ((int)expSignal[0]!=(int)expSignal[0]+1) goto flag1;
    else goto flag2;
 
    //если прошлый байт изменился в 8 бите на 1, считываем данные
    flag2:
    com1->write(expRead2);
    com1->waitForBytesWritten(100);
    com1->waitForReadyRead(100);
    expResult = com1->readAll();
 
    //операции преобразования полученных данных
    //Reading massive of data
 
        expRes1 = 0;
        expRes1 = expResult[4];
        expRes1 = expRes1 & 0xf;
        expRes1 = expRes1 << 8;
        expRes1 = expRes1 + expResult[5];
        expRes1 = (((double)expRes1 - BRef) / (ARef - BRef) * 4000);
 
        expRes2 = 0;
        expRes2 = expResult[6];
        expRes2 = expRes2 & 0xf;
        expRes2 = expRes2 << 8;
        expRes2 = expRes2 + expResult[7];
        expRes2 = (((double)expRes2 - BSig) / (ASig - BSig) * 4000);
 
        ADC1.resize(count+1);
        ADC2.resize(count+1);
        ADC1[count]=expRes1;
        ADC2[count]=expRes2;
        count++;
}
 
    //запись данных в файл
    //Recording data to file
         QTextStream out(&adcFile);
         if(adcFile.open(QIODevice::WriteOnly|QIODevice::Truncate))
         {
             out<<"ADC1"<<';';
             out<<"ADC2"<<';'<<"\r\n";
 
             for (int i=0; i<N; i++)
             {
                 out.setRealNumberNotation(QTextStream::ScientificNotation);
                 out<<ADC1[i]<<';';
                 out<<ADC2[i]<<';'<<"\r\n";
             }
             adcFile.close();
         }
    //End of reading and recording data
         com1->clear();
         com1->close();
}
Логи write C++ и С.docx

Логи read C++ и С.docx
0
Лучшие ответы (1)
13.05.2017, 20:21
IT_Exp
Эксперт
34794 / 4073 / 2104
Регистрация: 17.06.2006
Сообщений: 32,602
Блог
13.05.2017, 20:21
Ответы с готовыми решениями:

Чтение информации с весов через COM порт
Здравствуйте. Недавно начал изучать C++ и стоит такая задача. У меня есть программка, которая должна считывать вес через COM порт и...

Передача информации с ПК по RS232 на UART ATmega2313
Помогите разобраться с алгоритмом. Есть символьная строка информации, &quot;Привет123&quot;. Какой тип переменных (на с++) использовать для...

Циклическое чтение из файла
Доброго времени суток! Столкнулся с проблемой. К своему стыду не могу реализоавть простейший код в DEVC++ Суть: есть файл формата...

18
2 / 2 / 1
Регистрация: 10.11.2016
Сообщений: 94
13.05.2017, 20:51  [ТС] 2
Добавлю к комментариям которые показывают с какой строки ошибка:

//Ошибка в том что с данной строки цикл должен повторятся и привязываться к тому что условие выполнения цикла
//это то что в ответном байте от блока по адресу 0хd6 8 бит с каждым шагом цикла увеличивается на 1цу в 16 системе
0
Эксперт .NET
 Аватар для Rius
11280 / 7219 / 1601
Регистрация: 25.05.2015
Сообщений: 21,837
Записей в блоге: 14
13.05.2017, 21:00 3
Ваш COM не имеет отношения к тому COM, который в этом разделе форума.
Может есть человеческое описание протокола обмена?
0
2 / 2 / 1
Регистрация: 10.11.2016
Сообщений: 94
13.05.2017, 21:15  [ТС] 4
Да, есть конечно:packet_laz_stend.doc
0
Эксперт .NET
 Аватар для Rius
11280 / 7219 / 1601
Регистрация: 25.05.2015
Сообщений: 21,837
Записей в блоге: 14
13.05.2017, 21:35 5
Описание вполне адекватное, не считая что слово "slave" в данном контексте переводится не как "раб", а как "ведомый".
goto не нужен, хватило бы и цикла do-while или while.
Чтение и запись регистров необходимо вынести в отдельные методы. Потом уже ими оперировать.
1
шКодер самоучка
 Аватар для Max Dark
2289 / 1962 / 949
Регистрация: 09.10.2013
Сообщений: 4,403
Записей в блоге: 3
13.05.2017, 21:38 6
Лучший ответ Сообщение было отмечено Krounis как решение

Решение

переписал сишный код goto на do-while
C
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
BOOL Read_ADC_Expos(int *Data_ADC_1, int *Data_ADC_2)
{
 
    int W;
    byte Ready;
 
    // цикл ожидания готовности
    do {
        if (YesStop)
            return TRUE;
 
        Write_Data[0] = 0x81; // читаем тек счетчик и сравниваем c Cur_Count
        Write_Data[1] = 0;
        Write_Data[2] = 0xd6;
        Write_Data[3] = 0;
        Write_Data[4] = 0;
        Write_Data[5] = 0;
        Write_Data[6] = 1;
 
        if (!Send_Pack(Write_Data, Read_Data))
            return FALSE;
 
        Ready = Read_Data[6];
    }
    while (Ready == Cur_Count);
 
    //  можно считывать данные
    {
        Cur_Count = Ready;
 
        Write_Data[0] = 0xe1; // читаем
        Write_Data[1] = 0;
        Write_Data[2] = 0xdb;
        Write_Data[3] = 0;
        Write_Data[4] = 0;
        Write_Data[5] = 0;
        Write_Data[6] = 0;
 
        if (!Send_Pack(Write_Data, Read_Data))
            return FALSE;
 
        W = Read_Data[5];
        W &= 0x0f;
        W <<= 8;
 
        W += Read_Data[6];
        *Data_ADC_2 = (int)(((double)W - BSig) / (ASig - BSig) * 4000);
 
        W = Read_Data[3];
        W &= 0x0f;
        W <<= 8;
 
        W += Read_Data[4];
 
        *Data_ADC_1 = (int)(((double)W - BRef) / (ARef - BRef) * 4000);
 
        sprintf(SSS, " ADC_1 = %d ADC_2 = %d ", *Data_ADC_1, *Data_ADC_2);
 
        WriteLog(SSS);
 
    }
    return TRUE;
}
 
BOOL White_End_Pause(byte *Cur_Count)
{
 
    int W;
    byte Ready;
 
    do {
 
        if (YesStop)
            break;
 
        Write_Data[0] = 0x81; // читаем тек счетчик и сравниваем c Cur_Count
        Write_Data[1] = 0;
        Write_Data[2] = 0xd6;
        Write_Data[3] = 0;
        Write_Data[4] = 0;
        Write_Data[5] = 0;
        Write_Data[6] = 1;
 
        if (!Send_Pack(Write_Data, Read_Data))
            return FALSE;
 
        Ready = Read_Data[6];
    }
    while (Ready == *Cur_Count);
 
    *Cur_Count = Ready;
 
    return TRUE;
}
1
2 / 2 / 1
Регистрация: 10.11.2016
Сообщений: 94
13.05.2017, 21:45  [ТС] 7
Rius, спасибо попробую

Добавлено через 39 секунд
Max Dark, а можно его в c++шном коде использовать?
0
Эксперт .NET
 Аватар для Rius
11280 / 7219 / 1601
Регистрация: 25.05.2015
Сообщений: 21,837
Записей в блоге: 14
13.05.2017, 21:50 8
Хоть где можно, но сами исходные коды (оба) подлежат уничтожению...

Сделайте для примера нечто вроде такого:
C++
1
2
3
4
5
6
7
8
9
10
11
12
public:
bool read(uint8_t deviceAddress, uint16_t valueAddress, uint8_t *value);
bool read(uint8_t deviceAddress, uint16_t valueAddress, uint16_t *value);
bool read(uint8_t deviceAddress, uint16_t valueAddress, float *value);
 
bool write(uint8_t deviceAddress, uint16_t valueAddress, uint8_t value);
bool write(uint8_t deviceAddress, uint16_t valueAddress, uint16_t value);
bool write(uint8_t deviceAddress, uint16_t valueAddress, float value);
 
private:
bool read(uint8_t deviceAddress, uint16_t valueAddress, uint8_t length, uint8_t *array);
bool write(uint8_t deviceAddress, uint16_t valueAddress, uint8_t length, const uint8_t *array);
1
шКодер самоучка
 Аватар для Max Dark
2289 / 1962 / 949
Регистрация: 09.10.2013
Сообщений: 4,403
Записей в блоге: 3
13.05.2017, 21:52 9
Цитата Сообщение от Krounis Посмотреть сообщение
а можно его в c++шном коде использовать?
Теоретически можно, но нужно будет перетаскивать всю обвязку - использованные глобальные переменные, функции и так далее.
Вот, например, как объявлена функция Send_Pack? А массивы Write_Data, Read_Data?
1
2 / 2 / 1
Регистрация: 10.11.2016
Сообщений: 94
13.05.2017, 21:53  [ТС] 10
Rius, эти методы я так понял использовать для записи и считывания регистров, в замен СИшного Send_Pack(Write_Data, Read_Data)? А по сути, что от этого меняется? те же операции, только метом, или я что то недопонял?
0
Эксперт .NET
 Аватар для Rius
11280 / 7219 / 1601
Регистрация: 25.05.2015
Сообщений: 21,837
Записей в блоге: 14
13.05.2017, 21:57 11
Krounis, от это меняется читаемость, отлаживаемость и сопровождаемость. В лучшую сторону.
И это далеко не предел.
Ещё можно пару уровней создать поверх, и весь обмен сведётся к
Код
настроить
считывать, пока не настроилось.
считать результат.
2
2 / 2 / 1
Регистрация: 10.11.2016
Сообщений: 94
13.05.2017, 22:12  [ТС] 12
Max Dark, прошу прощения, реализации этих методов были в другом файле, могли бы вы глянуть?
вот файл целиком:
C
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
///////////////////////////////////////////////////////////////////////////
// CCommPort
 
 
#include "stdafx.h"
/*#include <string.h>
#include <memory.h>
#include <stdio.h>
#include <fcntl.h>
#include <io.h>
#include <conio.h>
#include <dos.h>
*/
 
 
 
#include <fstream.h>
 
//#include "decl_data.h"
 
//#include "deftask.h"
#include "CommPortP.h"
 
#include "decl_data.h"
 
unsigned Answer;
 
CommPortP COMPORT;
 
static DWORD MASK;
 
static byte InfBuf[256];
 
static byte Check;  
static byte len;    
static byte wbuf[256];
static byte rbuf[256];
 
static ofstream OFLOG;
 
 
short ResetEndraw(void);
 
 
static  char SSS[200];
void M_P(char *S);
 
void WriteLog(char *Mes);
 
 
#define Read_Op  0x80
#define Write_Op 0x00
 
#define Len_1  0x00
#define Len_2  0x20
#define Len_4  0x60
 
 
#define Head_Pack  0x55
 
 
 
 
BOOL Send_Pack_Go(byte *Data, byte *Read)
{ 
int I;
int Count;
byte *Pbuf;
byte  ; 
byte *PData;
 
// EscapeCommFunction(m_hComm,CLRRTS);
 
// return TRUE;   //для тестировангия без прибора 
 
 
byte Read_Check;
 
COMPORT.ClearFifo();
 
 
//Check = -(SA+Com);
Pbuf=wbuf;
 
Count=0; Check=0;
 
*Pbuf++=Head_Pack; // заголовок пакета 
 
Count++;
 
 
for (I=0;I<7;I++)
{
Check+=Data[I];
 
if (Data[I]==Head_Pack) { *Pbuf++=Head_Pack; Count++; }
*Pbuf++=Data[I];  Count++;
}
 
if (Check==Head_Pack) { *Pbuf++=Head_Pack; Count++; }
 
*Pbuf++=Check; Count++; 
 
Answer=0;
 
if(!COMPORT.WriteBuf(wbuf,Count)) return FALSE; 
 
 
 
 
if(!COMPORT.ReadBuf(rbuf,1)) return FALSE; 
 
 
if (rbuf[0]!=Head_Pack) {M_P("Error  in the  Protocol"); return FALSE; }
 
Count=0; Check=0;
Pbuf=Read;
 
for(I=0;I<7;I++) 
{
if(!COMPORT.ReadBuf(rbuf,1)) return FALSE; 
Check+=rbuf[0]; 
*Pbuf++=rbuf[0];
if (rbuf[0]==Head_Pack) 
{
if(!COMPORT.ReadBuf(rbuf,1)) return FALSE; 
 
}
}// for 
 
// чтение контр суммы 
 
if(!COMPORT.ReadBuf(rbuf,1)) return FALSE; 
Read_Check=rbuf[0]; 
if (rbuf[0]==Head_Pack) 
{
if(!COMPORT.ReadBuf(rbuf,1)) return FALSE; 
 
}
 
 
if (Check-Read_Check)
{
    sprintf(SSS,"Error Check Sum  %x %x ",Check,Read_Check); 
            M_P(SSS); return FALSE; 
}
 
 
 
return TRUE;
}
 
 
 
 
extern char InitCom;
 
 
void InitCOMPORT(void)
{
 
COMPORT.setBaudRate(Par.Speed);
COMPORT.setCommNumber(Par.COM);
    
 
COMPORT.setCountOfStopBits(1);
COMPORT.setParity(0);   
 
if(!COMPORT.initialize()) 
{    
sprintf(SSS,"Ошибка инициализации СОМ%d",Par.COM);
M_P(SSS);
 
InitCom=0;
}
}
 
 
 
static CTime theTime;
 
 
extern char DirectName[];
static int CCC=0;
 
 
void WriteLog(char *Mes)
{
 
char SSS[256];
 
SetCurrentDirectory(DirectName);
 
 
/*
if (CCC<4) 
{
CCC++;  
M_P(DirectName);
 
M_P(Mes);
}   
*/
  
    OFLOG.clear(0);
    
    OFLOG.open("!Journal.err",ios::ate);
 
        
        theTime = CTime::GetCurrentTime();
 
 
 
     OFLOG << "\n" <<Mes;
 
sprintf(SSS,"\t %2d:%2d:%2d",theTime.GetHour(),
                             theTime.GetMinute(),
                             theTime.GetSecond());
 
     
     OFLOG << SSS;
     
 OFLOG.close();
 
 
}
 
BOOL Reply;
 
BOOL Send_Pack(byte *Data, byte *Read)
{
 
Reply= Send_Pack_Go(Data,Read);
 
 
if (!Reply)
{
sprintf(SSS,"Error Comand   - %2x %2x %2x %2x %2x %2x %2x ",
        Data[0],Data[1],
        Data[2],Data[3],
        Data[4],Data[5],
        Data[6]);
WriteLog(SSS);
 
}
 
 
return Reply;
 
}
Добавлено через 2 минуты
Rius, Вы правы) собственно это и видно из Си-шного кода) поэтому, наверное, мне его трудно было читать(( Эх, еще учиться и учиться) Благодарю за советы)

Добавлено через 1 минуту
Max Dark, можно ли использовать в с++ этот метод Send_Pack(...) целиком как есть?
0
шКодер самоучка
 Аватар для Max Dark
2289 / 1962 / 949
Регистрация: 09.10.2013
Сообщений: 4,403
Записей в блоге: 3
13.05.2017, 22:19 13
Цитата Сообщение от Krounis Посмотреть сообщение
можно ли использовать в с++ этот метод Send_Pack(...) целиком как есть?
Нет - придется переписывать.
1
2 / 2 / 1
Регистрация: 10.11.2016
Сообщений: 94
13.05.2017, 22:23  [ТС] 14
Max Dark, наверное проще будет свой метод написать, потому что в плюсах я хоть могу это сделать), а Си для меня непривычен и не понятен, если только с Вашей помощью . Спасибо большое, за помощь!
0
шКодер самоучка
 Аватар для Max Dark
2289 / 1962 / 949
Регистрация: 09.10.2013
Сообщений: 4,403
Записей в блоге: 3
15.05.2017, 00:00 15
Krounis, мне тут было нечем заняться и я набросал реализацию по вашему описанию протокола
Код довольно сырой + вам нужно будет реализовать собственно чтение/запись в com-порт, так как у меня прописано только формирование и расшифровка пакета
1
2 / 2 / 1
Регистрация: 10.11.2016
Сообщений: 94
15.05.2017, 11:59  [ТС] 16
Спасибо большое, гляну

Добавлено через 55 минут
Max Dark, эта реализация на С++? А где именно, в каком методе нужно реализовать чтение/запись в com-порт?
0
шКодер самоучка
 Аватар для Max Dark
2289 / 1962 / 949
Регистрация: 09.10.2013
Сообщений: 4,403
Записей в блоге: 3
15.05.2017, 12:10 17
Цитата Сообщение от Krounis Посмотреть сообщение
эта реализация на С++?
да.
Цитата Сообщение от Krounis Посмотреть сообщение
А где именно, в каком методе нужно реализовать чтение/запись в com-порт?
Вам нужно реализовать интерфейс PortInterface и переопределить в нем методы read и write.
Они принимают указатель на буфер и размер буфера.
Пример реализации интерфейса смотрите в DummyPort.hpp/DummyPort.cpp
Пример использования - в demo.cpp

P.S.: еще раз предупреждаю, что код сырой, и скорее всего его нужно дорабатывать.
0
2 / 2 / 1
Регистрация: 10.11.2016
Сообщений: 94
16.05.2017, 11:12  [ТС] 18
Max Dark, мне сегодня удалось все-таки добить свой код, т.е. теперь логи от использования моей программы совпадают с логами рабочей программы на 100%.
Получилось так:
Кликните здесь для просмотра всего текста
C++ (Qt)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
void TabWindow::on_expButton_clicked()
{
    com1->open(QIODevice::ReadWrite);
    com1->setFlowControl(QSerialPort::NoFlowControl);
    com1->setBaudRate(QSerialPort::Baud115200);
    com1->setStopBits(QSerialPort::OneStop);
    com1->setDataBits(QSerialPort::Data8);
    com1->setDataTerminalReady(false);
    com1->clear();
 
    wdelay1.resize(9);
    wdelay2.resize(9);
    wdelay3.resize(9);
 
    testRes1.resize(9);
    testRes2.resize(9);
    testRes3.resize(9);
 
    wdelay1=setDelay(0xDF, (unsigned short)zad1in);
    wdelay2=setDelay(0xE1, 3);
    wdelay3=setDelay(0xE3, (unsigned short)zad2in);
 
    com1->write(wdelay1);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    testRes1 = com1->readAll();
 
    com1->write(wdelay2);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    testRes2 = com1->readAll();
 
    com1->write(wdelay3);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    testRes3 = com1->readAll();
 
    flagRes1.resize(9);
    flagRes2.resize(9);
 
    unsigned char sixbexp, sevenbexp;
    sixbexp=(expTime>>8)&0xff;
    sevenbexp=(expTime&0xff);
    flag1.resize(9);
    flag1[0]=0x55;
    flag1[1]=1;
    flag1[2]=1;
    flag1[3]=0x0d;
    flag1[4]=0;
    flag1[5]=0;
    flag1[6]=sixbexp;
    flag1[7]=sevenbexp;
    flag1[8]=flag1[1];
    for (int i=2; i<8; i++)
        flag1[8]=flag1[8]+flag1[i];
 
    unsigned char sixbp, sevenbp;
    sixbp=(zad3in>>8)&0xff;
    sevenbp=(zad3in&0xff);
    flag2.resize(9);
    flag2[0]=0x55;
    flag2[1]=1;
    flag2[2]=1;
    flag2[3]=0x21;
    flag2[4]=0;
    flag2[5]=0;
    flag2[6]=sixbp;
    flag2[7]=sevenbp;
    flag2[8]=flag2[1];
    for (int i=2; i<8; i++)
        flag2[8]=flag2[8]+flag2[i];
 
    com1->write(flag1);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    flagRes1 = com1->readAll();
 
    com1->write(flag2);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    flagRes2 = com1->readAll();
 
    expSignal.resize(1);
 
    //Experiment writepack 1
    expWrite1.resize(9);
    expWrite1[0] = 0x55;
    expWrite1[1] = 1;
    expWrite1[2] = 0;
    expWrite1[3] = 0xc2;
    expWrite1[4] = 0;
    expWrite1[5] = 0;
    expWrite1[6] = 0;
    expWrite1[7] = 1;
    expWrite1[8] = expWrite1[1];
    for (int i=2; i<8; i++)
        expWrite1[8]=expWrite1[8]+expWrite1[i];
 
    //Experiment writepack 2
    expWrite2.resize(9);
    expWrite2[0] = 0x55;
    expWrite2[1] = 0x81;
    expWrite2[2] = 0;
    expWrite2[3] = 0xc2;
    expWrite2[4] = 0;
    expWrite2[5] = 0;
    expWrite2[6] = 0;
    expWrite2[7] = 0;
    expWrite2[8] = expWrite2[1];
    for (int i=2; i<8; i++)
        expWrite2[8]=expWrite2[8]+expWrite2[i];
 
    //Experiment readpack 1
    expRead1.resize(9);
    expRead1[0] = 0x55;
    expRead1[1] = 0x81;
    expRead1[2] = 0;
    expRead1[3] = 0xD6;
    expRead1[4] = 0;
    expRead1[5] = 0;
    expRead1[6] = 0;
    expRead1[7] = 1;
    expRead1[8] = expRead1[1];
    for (int i=2; i<8; i++)
        expRead1[8]=expRead1[8]+expRead1[i];
 
    //Experiment readpack 2
    expRead2.resize(9);
    expRead2[0] = 0x55;
    expRead2[1] = 0xE1;
    expRead2[2] = 0;
    expRead2[3] = 0xDB;
    expRead2[4] = 0;
    expRead2[5] = 0;
    expRead2[6] = 0;
    expRead2[7] = 0;
    expRead2[8] = expRead2[1];
    for (int i=2; i<8; i++)
        expRead2[8]=expRead2[8]+expRead2[i];
 
    ARef = 4000;
    BRef = 0;
    ASig = 4000;
    BSig = 0;
    QFile adcFile("ADC data.csv");
 
    expResult.resize(9);
    expResultP.resize(9);
    expResultC.resize(9);
 
    com1->write(expWrite1);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    expResult = com1->readAll();
 
    com1->write(expWrite2);
    com1->waitForBytesWritten(50);
    com1->waitForReadyRead(50);
    expResult = com1->readAll();
 
    int count=0;
    expSignal[0]=count;
    expResultC[7]=1;
    while ((int)expResultC[7]!=0)
    {
    do
    {
    com1->write(expRead1);
    com1->waitForBytesWritten(100);
    com1->waitForReadyRead(100);
    expResultP = com1->readAll();
    expSignal[0] = expResultP[7];
    } while ((int)expSignal[0]!=count+1&&(int)expSignal[0]!=0);
 
    com1->write(expRead2);
    com1->waitForBytesWritten(100);
    com1->waitForReadyRead(100);
    expResult = com1->readAll();
 
    com1->write(expWrite2);
    com1->waitForBytesWritten(100);
    com1->waitForReadyRead(100);
    expResultC = com1->readAll();
 
    //Reading massive of data
    expRes1 = 0;
    expRes1 = expResult[4];
    expRes1 = expRes1 & 0xf;
    expRes1 = expRes1 << 8;
    expRes1 = expRes1 + expResult[5];
    expRes1 = (((double)expRes1 - BRef) / (ARef - BRef) * 4000);
 
    expRes2 = 0;
    expRes2 = expResult[6];
    expRes2 = expRes2 & 0xf;
    expRes2 = expRes2 << 8;
    expRes2 = expRes2 + expResult[7];
    expRes2 = (((double)expRes2 - BSig) / (ASig - BSig) * 4000);
 
    ADC1.resize(count+1);
    ADC2.resize(count+1);
    ADC1[count]=expRes11;
    ADC2[count]=expRes22;
    count++;
    }
 
    //Recording data to file
     QTextStream out(&adcFile);
     if(adcFile.open(QIODevice::WriteOnly|QIODevice::Truncate))
     {
         out<<"ADC1"<<';';
         out<<"ADC2"<<';'<<"\r\n";
         //int N=expTime;
         for (int i=0; i<count; i++)
         {
             out.setRealNumberNotation(QTextStream::ScientificNotation);
             out<<ADC1[i]<<';';
             out<<ADC2[i]<<';'<<"\r\n";
         }
         adcFile.close();
     }
    //End of reading and recording data
     com1->clear();
     com1->close();
}
 
QByteArray TabWindow::setDelay(unsigned char adress, unsigned short delay)
{
    unsigned char sixb, sevenb;
    sixb=(delay>>8)&0xff;
    sevenb=(delay&0xff);
    QByteArray resDelay;
    resDelay.resize(9);
    resDelay[0] = 0x55;
    resDelay[1] = 0x21;
    resDelay[2] = 0;
    resDelay[3] = adress;
    resDelay[4] = 0;
    resDelay[5] = 0;
    resDelay[6] = sixb;
    resDelay[7] = sevenb;
    resDelay[8] = resDelay[1];
    for (int i=2; i<8; i++)
        resDelay[8]=resDelay[8]+resDelay[i];
    return resDelay;
}

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

А как выгружать или куда-то записывать данные, которые постоянно меняются в процессе эксперимента?
0
Байт
17.08.2017, 21:26     Циклическое чтение информации через RS232 с использованием goto
  #19

Не по теме:

Krounis, Прошу меня извинить, но в этой теме я ничего толкового сказать не могу

0
17.08.2017, 21:26
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
17.08.2017, 21:26
Помогаю со студенческими работами здесь

Чтение данных с COM/RS232 порта
Стоят весы подключённые к компу через RS232. Кладём на весы продукт, весы &quot;устаканиваются&quot; и кидают вес в виде &quot;000.254&quot;...

Чтение из последовательного порта по протоколу RS232
Добрый день , собственно имеется такой вопрос, работаю с устройством , необходимо реализовать чтение данных из порта , сейчас чтение...

Циклическое чтение данных из нескольких файлов .txt
Здравствуйте, уважаемые форумчане. Подскажите пожалуйста по следующей проблеме, так в интернете похожего ничего не нашел. Задача: имеется...

Циклическое копирование файлов с использованием команды XCOPY
Здравствуйте. Я хочу скопировать определённые файлы из одной директории в другую. Имею такой bat-файл: REM @echo off SET...

Циклическое чтение системного времени и очистка экрана в заданный момент
Приветствую, поможете разобраться? Программа должна очищать экран в заданный момент, но это не происходит. Что не так?


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
19
Ответ Создать тему

Редактор формул (кликните на картинку в правом углу, чтобы закрыть)
Опции темы

Новые блоги и статьи
Контейнер std::map в C++
bytestream 09.02.2025
Контейнер std::map в C++ - один из наиболее мощных инструментов стандартной библиотеки, предназначенный для хранения пар ключ-значение. Каждый элемент в map состоит из уникального ключа и связанного. . .
Как в Python сделать вывод с print без перевода строки и пробела
hw_wired 09.02.2025
Функция print в Python обеспечивает гибкие возможности для вывода информации в консоль. При стандартном использовании эта функция автоматически добавляет символ перевода строки в конце выводимого. . .
Как в Python проверить, что у объекта есть атрибут
hw_wired 09.02.2025
В Python существует несколько встроенных способов проверки наличия атрибутов у объектов. Наиболее распространенным является использование функции hasattr(), которая позволяет безопасно определить. . .
Как удалить экспортированну­ю переменную окружения в Linux
hw_wired 09.02.2025
В Linux работа с переменными окружения - важная часть системного администрирования и разработки. Экспортированные переменные окружения отличаются от обычных локальных переменных тем, что они доступны. . .
Ошибка Error: error:0308010C:­digital envelope routines::unsup­ported
hw_wired 09.02.2025
Ошибка "error:0308010C:digital envelope routines::unsupported" чаще всего появляется при работе с Node. js приложениями и связана с изменениями в системе безопасности криптографических алгоритмов. . . .
В чем отличие между .prop() и .attr()
hw_wired 09.02.2025
В jQuery методы . prop() и . attr() часто вызывают путаницу, поскольку на первый взгляд предназначены для похожих целей. Однако между ними существуют принципиальные различия в работе с DOM-элементами и. . .
В чем отличие SCSS и SASS
hw_wired 09.02.2025
SCSS и SASS появились как решение проблем, связанных с ограничениями обычного CSS при разработке крупных веб-проектов. Традиционный CSS, несмотря на свою простоту, не предоставлял разработчикам. . .
Как найти дубликаты в таблице базы данных
hw_wired 09.02.2025
Дублирование записей в таблицах баз данных может возникать по разным причинам: ошибки при вводе данных, некорректная работа систем импорта, слияние данных из разных источников или неправильная. . .
Как удалить дубликаты из массива в JavaScript
hw_wired 09.02.2025
Самый простой и современный способ удаления дубликатов в JavaScript - использование структуры данных Set в сочетании с Array. from. Set автоматически хранит только уникальные значения, а Array. from. . .
Go Protobuf: новый Opaque API
hw_wired 09.02.2025
Protocol Buffers (protobuf) давно зарекомендовал себя как эффективный формат сериализации данных, широко используемый в микросервисных архитектурах и распределенных системах. Однако существующая. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2025, CyberForum.ru