У меня есть последовательный порт. Другая программа записывает в последовательный порт каждые 0,2 секунды. Каждый раз данные, записываемые в последовательный порт, всегда имеют длину 83 байта. Серийный порт можно правильно прочитать с помощью minicom.
У меня есть программа, которая может читать последовательный порт. Каждый раз поток байтов записывается в последовательный порт:
65 66 67 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90
В большинстве случаев данные могут быть получены правильно. Однако иногда данные путаются. Как только данные испорчены, почти все входящие сообщения испорчены.
Иногда я получаю вывод из своего кода как:
65 0 66 67 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 90 65 66 67
Это странно. Поскольку, по-видимому, после первых 65 есть 0. Кроме того, последние три байта равны 65 66 67, что выглядит как начало нового сообщения.
Код для открытия и настройки последовательного порта:
int serial_fd = open(device, O_RDWR | O_NOCTTY | O_NDELAY|O_NONBLOCK);
if (serial_fd < 0) {
return -1;
}
struct termios options;
tcgetattr(serial_fd, &options);
options.c_cflag |= (CLOCAL | CREAD);
//8N1 mode
options.c_cflag &= ~CSIZE;
options.c_cflag |= CS8;
options.c_cflag &= ~CSTOPB;
options.c_cflag &=~PARENB;
options.c_cflag &= ~CRTSCTS;
options.c_lflag &= ~(ICANON|ECHO|ECHONL|ISIG|IEXTEN);
options.c_iflag &= ~(IGNBRK|BRKINT|PARMRK|ISTRIP|INLCR|IGNCR|ICRNL|IXON);
options.c_oflag &= ~OPOST;
cfsetospeed(&options, B115200);
cfsetispeed(&options, B115200);
tcsetattr(serial_fd, TCSANOW, &options);
tcflush(serial_fd, TCIFLUSH);
Код для чтения из последовательного порта и распечатки полученного сообщения:
uint8_t *buff,buff_data[100];
buff = buff_data;
int len,fs_sel;
fd_set fs_read;
int expectedLength=83;
int len_acc = 0;
while(1){
FD_ZERO(&fs_read);
FD_SET(serial_fd, &fs_read);
fs_sel = select(serial_fd+1,&fs_read,NULL,NULL,NULL);
if(fs_sel)
{
len = read(serial_fd, buff, expectedLength-len_acc);
if (len<=0) continue;
len_acc += len;
if (len_acc < expectedLength) {
buff += len;
continue;
}
len_acc = 0;
buff = buff_data;
for (int i=0; i<expectedLength; i++){
std::cout <<(int)buff[i]<<" ";
}
std::cout<< std::endl;
}
}
Спасибо за вашу помощь.