В настоящее время я создаю программное обеспечение в Linux, в котором данные должны поступать на компьютер со скоростью 56 КБ в неизмененном исходном формате от COM1.
Я могу достичь этого вручную, выполнив следующие команды на терминале Unix:
screen /dev/ttyS0 57600
stty -F /dev/ttyS0 -ixon
И каждый раз я проверяю данные с помощью этой команды:
od -tx1 -w11 -v /dev/ttyS0
Если бы я пропустил вторую команду выше, тогда коды символов 11 и 13 никогда не были бы напечатаны на экране. Я думаю, что это связано с программным управлением потоком. В моих настройках связи я не использую управление потоком и не хочу, чтобы linux переназначал любые символы.
Итак, я попытался создать код, который бы эффективно давал те же результаты, но я думаю, что мои серийные настройки неверны, потому что когда я выполнял код, символы не совпадали.
Я знаю, какие значения следует ожидать, потому что я создал удаленное оборудование, к которому подключен ПК через последовательный порт, и удаленное оборудование прямо сейчас передает одну и ту же последовательность строк снова и снова.
Теперь, если я запустил этот код, а затем остановил выполнение и решил запустить три команды, указанные выше, в терминале Unix, вывод был бы на 100% правильным.
Это код:
#include <termios.h>
#include <stdio.h>
#include <stropts.h>
#include <poll.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/signal.h>
#include <sys/types.h>
#define BAUDRATE B57600 /* Want 56K speed */
#define _POSIX_SOURCE 1 /* POSIX compliant source */
#define MODEMDEVICE "/dev/ttyS0" /* My serial port */
int main(){
int res; //result value from call
struct termios oldtio,newtio;
struct pollfd fds[2];
fds[0].fd = open(MODEMDEVICE, O_RDWR | O_NOCTTY | O_NONBLOCK);
if (fds[0].fd <0) {perror(MODEMDEVICE); return -1; }
fds[0].events=POLLIN;
tcgetattr(fds[0].fd,&oldtio); /* save current port settings */
/* Assign new settings. Could I somehow crunch this down? */
newtio.c_cflag = BAUDRATE | CRTSCTS | CS8 | CLOCAL | CREAD;
newtio.c_iflag = IGNPAR | ICRNL | ~IXON | ~IXOFF;
newtio.c_oflag = 0;
newtio.c_lflag = ICANON;
newtio.c_cc[VMIN]=1;
newtio.c_cc[VTIME]=0;
tcflush(fds[0].fd, TCIFLUSH);
tcsetattr(fds[0].fd,TCSANOW,&newtio);
// Wait for data
unsigned char buf[1024]; //Get a huge buffer incase this PC is super slow
int ct=22; //count 22 bytes before new line
unsigned int ms=0,entn=0; //Set entry number + delayed ms to 0
printf("%04u: ",entn); //print entry # 0 label
while (1){
res=poll(fds,1,1);
if (res > 0){
if (fds[0].revents & POLLIN){
// Here we have something
res = read(fds[0].fd,buf,sizeof(buf));
if (res > 1){
//show how long we waited for next data if over 1ms
if (ms > 0){printf("(%u)",ms);ms=0;}
int n;
for (n=0;n<res;n++){
printf("%02X ",buf[n]); //print characters as hex
ct--;
if (ct==0){
//We printed 22 characters so print a new line and next label
ct=22;
printf("\n");
entn++;
printf("%04u: ",entn);
}
}
}
}
}else{
//No data so add 1ms to the total
ms++;
}
//Loop is endless
}
return 0;
}
Как мне исправить мой код, чтобы я мог использовать его вместо того, чтобы каждый раз запускать три вышеуказанные команды, чтобы увидеть правильный вывод?