2012-12-22 93 views
1

簡單的問題。當我寫信給/dev/ttyS1時,它不會立即刷新它。這可能是與我的串行端口初始化有關...但我無法弄清楚!我的代碼是這樣的:linux c寫入後沖刷串行緩衝區

#define BAUDRATE B115200 
#define MODEMDEVICE "/dev/ttyS1" 
#define _POSIX_SOURCE 1 /* POSIX compliant source */ 
#define FALSE 0 
#define TRUE 1 

volatile int STOP = FALSE; 

void signal_handler_IO(int status); /* definition of signal handler */ 
int wait_flag = TRUE; /* TRUE while no signal received */ 


int main() 
{ 
    int fd, c, res; 
    struct termios oldtio, newtio; 
    struct sigaction saio; /* definition of signal action */ 
    char buf[255]; 

    /* open the device to be non-blocking (read will return immediatly) */ 
    fd = open(MODEMDEVICE, O_RDWR | O_NOCTTY | O_NONBLOCK); 
    if (fd < 0) { 
     perror(MODEMDEVICE); 
     exit(-1); 
    } 

    /* install the signal handler before making the device asynchronous */ 
    saio.sa_handler = signal_handler_IO; 
    //saio.sa_mask = 0; 
    saio.sa_flags = 0; 
    saio.sa_restorer = NULL; 
    sigaction(SIGIO, &saio, NULL); 

    /* allow the process to receive SIGIO */ 
    fcntl(fd, F_SETOWN, getpid()); 
    /* Make the file descriptor asynchronous (the manual page says only 
    O_APPEND and O_NONBLOCK, will work with F_SETFL...) */ 
    fcntl(fd, F_SETFL, FASYNC); 

    tcgetattr(fd, &oldtio); /* save current port settings */ 
    /* set new port settings for canonical input processing */ 
    newtio.c_cflag = BAUDRATE | CRTSCTS | CS8 | CLOCAL | CREAD; 
    newtio.c_iflag = IGNPAR | ICRNL; 
    newtio.c_oflag = 0; 
    newtio.c_lflag = ICANON; 
    newtio.c_cc[VMIN] = 1; 
    newtio.c_cc[VTIME] = 0; 
    tcflush(fd, TCIFLUSH); 
    tcsetattr(fd, TCSANOW, &newtio); 

    int i = 0; 

    /* loop while waiting for input. normally we would do something 
    useful here */ 
    while (1) { 
     printf(".\n"); 
     usleep(100000); 
     //tcflush(fd, TCOFLUSH); 
     //tcflush(fd, TCIOFLUSH); 
     i++; 
     if (i == 20) { 
      // ------------------ write to serial ---------------------- 
      int n = write(fd, "ATZ\n", 4); 
      if (n < 0) 
       fputs("write() of 4 bytes failed!\n", stderr); 

     } 

     /* after receiving SIGIO, wait_flag = FALSE, input is available 
     and can be read */ 
     if (wait_flag == FALSE) { 
      res = read(fd, buf, 255); 
      buf[res] = 0; 
      printf(":%s:%d\n", buf, res); 
      wait_flag = TRUE; /* wait for new input */ 
     } 
    } 
    /* restore old port settings */ 
    tcsetattr(fd, TCSANOW, &oldtio); 
} 



void signal_handler_IO(int status) { 
    printf("received SIGIO signal.\n"); 
    wait_flag = FALSE; 
} 

任何想法?

+0

你能描述到底發生了什麼嗎? –

+0

像minicom或busybox的集成microcom這樣的程序是否按預期工作,沒有意外的延遲?僅僅是因爲 - 尤其是在嵌入式系統中 - 中斷問題是串行通信中莫名其妙的延遲來源。 – fvu

+0

輸入: 當輸入通過串行接收時,調用signal_handler_IO,它又將wait_flag設置爲FALSE,以便主循環從串行讀取輸入。這工作正常。 輸出: 當我這樣做: int n = write(fd,「ATZ \ n」,4); 它不立即寫入。基本上緩衝區是不會刷新,直到它溢出或我呼籲關閉(fd) –

回答

0

我不認爲這是一個解決方案,但補充說:

tcflush(fd, TCIOFLUSH); // clear buffer 

清除緩衝區似乎做的伎倆。但是,應該有一些更優雅和適當的解決方案。

+5

該文件將建議TCIOFLUSH應該清除*清除數據(放在地板上),而不是*發送*它。 –

1

您已通過設置CRTSCTS啓用CTS硬件流量控制。這意味着如果如果CTS輸入到UART沒有激活,UART應該避免發送。

您可能需要查看termios手冊頁。