AnsweredAssumed Answered

Issue when reading tty with nfs rootfs

Question asked by victorien on Oct 6, 2015
Latest reply on Oct 13, 2015 by victorien

Hi,

For an embedded device (kernel 3.14 and rootfs with OpenEmbedded), I develop a software which read the data on tty driver. This soft operates correctly when I test it on the board. If I use an nfs server for the rootfs the soft is stuck on the loop which read the tty file. I can't go out with 'ctrl+c', I can't write on the console and I have this kind of message " nfs: server 192.168.1.40 not responding, still trying"

Is there someone who knows this issue ?

Thanks

 

My software :

 

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <signal.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/poll.h>
#include <sys/ioctl.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <fcntl.h>
#include <termios.h>
#include <sys/fcntl.h>
#include <errno.h>
#include <unistd.h>
#include <time.h>

#define FALSE    0
#define TRUE    1

int print_help (int argc, char *argv[])
{
    printf("Test program for uart reception\n");
    printf("Usage :\n");
    printf("\t%s [-h -D -c]\n", argv[0]);
    printf("\t-D : use this tty device\n");
    printf("\t-c : control data to extract the trame\n");
    printf("\t-h : print help\n");
    return 0;
}

int wait_flag = TRUE ;

void signal_handler_IO (int status)
{
     //printf("received data from UART.\n");
     wait_flag = FALSE;
}

/*
 * The values for speed are B115200, B230400, B9600, B19200, B38400, B57600,
 * B1200, B2400, B4800, etc. The values for parity are 0 (meaning no parity),*
 * PARENB|PARODD (enable parity and use odd), PARENB (enable parity and use even),
 * PARENB|PARODD|CMSPAR (mark parity), and PARENB|CMSPAR (space parity).
 */
int set_interface_attribs (int fd, int speed, int parity)
{
    struct sigaction saio;
        struct termios tty;
        memset (&tty, 0, sizeof tty);


     /***/
    saio.sa_handler = signal_handler_IO;
    saio.sa_flags = 0;
    saio.sa_restorer = NULL;
    sigaction(SIGIO, &saio, NULL);

    fcntl (fd, F_SETFL, FNDELAY|FASYNC);
    fcntl (fd, F_SETOWN, getpid());
    /***/

        if (tcgetattr (fd, &tty) != 0)
        {
                printf("error from tcgetattr\n");
                return -1;
        }

        cfsetospeed (&tty, speed);
        cfsetispeed (&tty, speed);

        tty.c_cflag = (tty.c_cflag & ~CSIZE) | CS8;     // 8-bit chars
        // disable IGNBRK for mismatched speed tests; otherwise receive break
        // as \000 chars
        tty.c_iflag &= ~IGNBRK;         // disable break processing
        tty.c_lflag = 0;                // no signaling chars, no echo,
                                        // no canonical processing
        tty.c_oflag = 0;                // no remapping, no delays
        tty.c_cc[VMIN]  = 0;            // read doesn't block
        tty.c_cc[VTIME] = 5;            // 0.5 seconds read timeout

        tty.c_iflag &= ~(IXON | IXOFF | IXANY); // shut off xon/xoff ctrl

        tty.c_cflag |= (CLOCAL | CREAD);// ignore modem controls,
                                        // enable reading
        tty.c_cflag &= ~(PARENB | PARODD);      // shut off parity
        tty.c_cflag |= parity;
        tty.c_cflag &= ~CSTOPB;
        tty.c_cflag &= ~CRTSCTS;

        if (tcsetattr (fd, TCSANOW, &tty) != 0)
        {
                printf("error from tcsetattr\n");
                return -1;
        }
        return 0;
}

/*
 * "Blocking" sets whether a read() on the port waits for the specified number
 * of characters to arrive. Setting no blocking means that a read() returns
 * however many characters are available without waiting for more, up to the
 * buffer limit.
 */
void set_blocking (int fd, int should_block)
{
        struct termios tty;
        memset (&tty, 0, sizeof tty);
        if (tcgetattr (fd, &tty) != 0)
        {
                printf ("error from tggetattr\n");
                return;
        }

        tty.c_cc[VMIN]  = should_block ? 1 : 0;
        tty.c_cc[VTIME] = 5;            // 0.5 seconds read timeout

        if (tcsetattr (fd, TCSANOW, &tty) != 0)
                printf ("error setting term attributes\n");
}


int main(int argc, char *argv[]) {
    int i, j, k;
    int fd;
    char c;
    signed char index_trame = -1;
    char trame[6];
    char initChaine[30] = "Frame received on uart :";
    char *ttyDevice = "/dev/ttyAPP0";
    char chaineCar[100];
    char receptCar[6];
    char buf[255];
    char processData[512];
    char restofData[6];
    int sizeofData = 0;
    char ctrl_trame = 0;
    int loop = 0;
    int ret = 0;
    int count = 0;
    FILE* saveFile = NULL;

    /* Parse arguments */
    if (argc < 0 || argc > 4) {
        printf("Invalid number of argument\n");
        print_help(argc, argv);
        return 0;
    }
    j = 0;
    for (i=1; i<argc; i++) {
        if (argv[i][0] == '-') {
            for (k=1; argv[i][k]; k++) {
                switch (argv[i][k]) {
                    case 'D':
                        ttyDevice = argv[i+1];
                        printf("Use %s device\n",ttyDevice);
                        //i++;
                        break;
                    case 'c':
                        ctrl_trame = 1;
                        break;
                    case 'h':
                        print_help(argc, argv);
                        break;
                    default:
                        printf("Wrong option: -%c\n", argv[i][k]);
                        print_help(argc, argv);
                        return 0;
                }
            }
        } else {
        }
        j ++;
    }/**/

    /*run program*/
    printf(" Read serial port V0.6\n");

    saveFile = fopen("receptUart.txt", "w+");
    index_trame = 0;

    /* Ouverture de la liaison serie */
    if ( (fd=open(ttyDevice, O_RDONLY | O_NOCTTY | O_SYNC)) == -1 ) {
        printf("error open %s\n", ttyDevice);
        return -1;
    }

    set_interface_attribs (fd, B2400, 0);
    set_blocking (fd, 1);

    do {

            if (wait_flag == FALSE) {
                ret = read(fd, buf, 255);
                if (ctrl_trame) {
                    for (i=0;i<ret;i++)
                        processData[sizeofData+i] = buf[i];
                    sizeofData += ret;
                    for (i=0;i<sizeofData;i++) {
                        if ((sizeofData - i) < 6) {
                            break;
                        }
                        else if (processData[i] == 0xfa) {
                            count++;
                            printf ("Received frame n %d :", count);
                            for (j=0;j<6;j++) {
                                trame[j]=processData[i];
                                printf(" h%02x", processData[i]);
                                i++;
                            }
                            i--;
                            printf("\n");
                        }
                    }
                    for(j=i;j<sizeofData;j++)
                        processData[j-i] = processData[j];
                    sizeofData -= i;
                }
                else {
                    printf ("%i data received :", ret);
                    for (i=0;i<ret;i++) {
                        printf(" h%02x", buf[i]);
                    }
                    printf("\n");
                }
                wait_flag = TRUE;
            }
    }
    while (1);

    close(fd);
    printf("GoodBye\n");

    return EXIT_SUCCESS;
}

Outcomes