-1

I am reading data continuously from RS 485 port by C program from a device by the following code. For some reason, obtained data is not the latest data in the device. The changes of data is not reflected when I read data, it gives me old value. After couple of minutes, I get the changed value (since I am continuously reading). If I read the same device by Pytty I get the updated value immediately. So there must be some problem in my code though I couldn't figure it out. Any help would be great!

static int load_serial_port(char *port) //port is 485, port="/dev/ttyS2"/
{
int fd = 0;
    fd = open (port, O_RDWR);
        if (fd < 0) {
            log_error("SerialPort opening failed.");
            return -1;
        }
        struct serial_rs485 rs485conf;
        /* Enable RS485 mode: */
        rs485conf.flags |= SER_RS485_ENABLED;

        /* Set logical level for RTS pin equal to 1 when sending: */
        rs485conf.flags |= SER_RS485_RTS_ON_SEND;
        /* or, set logical level for RTS pin equal to 0 when sending: */
        rs485conf.flags &= ~(SER_RS485_RTS_ON_SEND);

        /* Set logical level for RTS pin equal to 1 after sending: */
        rs485conf.flags |= SER_RS485_RTS_AFTER_SEND;
        /* or, set logical level for RTS pin equal to 0 after sending: */
        rs485conf.flags &= ~(SER_RS485_RTS_AFTER_SEND);

        /* Set rts delay before send, if needed: */
        rs485conf.delay_rts_before_send = 0;

        /* Set rts delay after send, if needed: */
        rs485conf.delay_rts_after_send = 0;

        /* Set this flag if you want to receive data even whilst sending data */
        //rs485conf.flags |= SER_RS485_RX_DURING_TX;

        if (ioctl (fd, TIOCSRS485, &rs485conf) < 0) {
            log_error("SerialPort config failed.");
            return -1;
        }
        struct termios option;
        tcgetattr(fd, &option);

        cfsetospeed(&option, B9600); /* baud rate */
        option.c_cflag &= ~PARENB; /* no parity */
        option.c_cflag &= ~CSTOPB; /* 1 stop bit */
        option.c_cflag &= ~CSIZE;
        option.c_cflag |= CS8 | CLOCAL; /* 8 bits */
        option.c_lflag = ICANON; /* canonical mode */
        option.c_oflag &= ~OPOST; /* raw output */

        tcsetattr(fd, TCSANOW, &option); /* apply the settings */
        tcflush(fd, TCOFLUSH);
        log_debug("SerialPort loaded fd %d", fd);
return fd;
}

Following is the read function

static void port_read(port_t *s)
{

uint8_t rxBuffer[20];
char portString[20] = "";
double value = 0.0;
if(s->serialPortFd > 0) {
int amount = read(s->serialPortFd, rxBuffer, 100);
    int i = 0;
    int charindex = 0;
    if(amount > 1 ) {
        for (i = 0; i< amount; i++) {
            if ( isdigit(  rxBuffer[i]) || (   (char)rxBuffer[i] == '-' || (char)rxBuffer[i] == '.') ) {
                portString[charindex] = (char)rxBuffer[i];
                charindex++;
            }
        }
        portString[charindex] = '\0';
        sscanf(portString, "%lf", &value); //value is same ???
    }
}
memset(rxBuffer, 0, sizeof rxBuffer);
}
RotatingWheel
  • 1,023
  • 14
  • 27
  • Dunno mate, for some reason your port object is not being updated. Check if it has like "flush" or "read" functions. Maybe it would be a good idea to call em in port_read function. – Sv Sv Nov 17 '17 at 16:22
  • rs485conf.flags |= SER_RS485_RTS_ON_SEND; rs485conf.flags &= ~(SER_RS485_RTS_ON_SEND); What are you trying to do here? You turn the bit on then you turn it off. Same with SER_RS485_RTS_AFTER_SEND – JJF Nov 17 '17 at 16:25
  • Your `read(s->serialPortFd, rxBuffer, 100)` is wrong: you are reading up to 100 bytes in a buffer of just 20, so you risk a buffer overflow. Consider writing `read(s->serialPortFd, rxBuffer, sizeof(rxBuffer))` instead. – rodrigo Nov 17 '17 at 17:02
  • @Sv Sv, thereis read function but I did not find flush function. How puttty is working? In putty I have exact same settings. – RotatingWheel Nov 17 '17 at 17:09
  • Your code is incomplete; in particular, it seems to be missing a `main()` function and at least one `#include`. Please [edit] your code so it's a [mcve] of your problem, then we can try to reproduce and solve it. You should also read [ask]. – Toby Speight Nov 20 '17 at 15:29

1 Answers1

0

Sometimes I feel experts post, comment in this forum without reading questions carefully. I found the correct solution after reading and doing more experiment and that I was expecting to save time. My reading goes fine with the following changes in my code:

            int amount = read(s->serialPortFd, rxBuffer, 20);
            tcflush(s->serialPortFd, TCIOFLUSH);

I was missing flashing the file.

RotatingWheel
  • 1,023
  • 14
  • 27