Skip to content

Serial Communication

COM (RS232) port and RS485/CAN1

There are two COM (RS232) ports and one RS485/CAN port avaible in STEP2. Two COM ports (COM1, COM2) are arrange in separated DSUB-9 connectors while the RS485/CAN port shares the 9-Pin connector with CAN port.


In order to verify the available serial ports on the platform one can use kernel log:

1
$ dmesg | grep tty


Check for available serial ports

Although there are four serial ports available, only three of them can be used on STEP-PC2. The ttyS3, ttyS4 are COM1 and COM2 ports on the STEP2 panel, while ttyS0 is the RS485/CAN port.


Serial ports on STEP2

The COM (RS232) ports and RS485 port are controlled by the NRMK library or standard serial API. In these APIs function, tp_open_serial_port is the most useful one to open and setup the serial ports (both RS232 port and RS458 port). Parameters for this function are the port name and the communication baudrate, and return is the file description (fd) for opened serial port.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
//! @brief Available serial ports on board
#define SERIALPORT1     "/dev/ttyS0"
#define SERIALPORT4     "/dev/ttyS3"
#define SERIALPORT5     "/dev/ttyS4"
#define SERIALPORT6     "/dev/ttyS5"

//! @brief Available serial ports on STEP-PC2
#define RS485PORT       "/dev/ttyS0"    //RS485 port
#define COM1            "/dev/ttyS3"    //COM1 port
#define COM2            "/dev/ttyS4"    //COM2 port

#define RS485_BAUD_LIMIT    1500000 //maximum RS485 baudrate
#define RS232_BAUD_LIMIT    230400      //maximum baudrate

// STEP-PC2 Serial
int NRMKkbhit(void);
int tp_open_serial_port(const char* portname, unsigned int baud);
int tp_configure_serial_port(int fd, int baud);

Note

On STEP2, due to physical characteristic, maximum baudrate for RS232 port and RS485 are not same. For RS232 ports (COM1, COM2) maximum rate is 230400 bps (230.4 Kbps) while that for RS485 port is 1500000 bps (1.5 Mbps).

Serial communication example

Let’s take a look at the tpserial example which is included in the install package. When a key is entered on a terminal, then key will be sent via the serial port, and when data come into the serial port, it is displayed on the terminal as well.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include "NRMKhw_tp.h"
int fd=-1;
void * read_thread(void* arg);
void * write_thread(void* arg);
//reading thread
void * read_thread(void* arg)
{
    int nbytes;
    char chr;
    while(1)
    {
        nbytes=read(fd,&chr,1);
        if (nbytes>0){
            printf("%c", chr);
        }
        usleep(1e4);
    }
}
//writing thread
void * write_thread(void* arg)
{
    int kchr;
    while(1)
    {
        if (NRMKkbhit())
        {
            kchr = getchar();
            write(fd,&kchr,1);
        }
        usleep(1e4);
    }
}
/****************************************************************************
 * Signal handler
 ***************************************************************************/
void catch_signal(int sig)
{
    if (fd>0) close(fd);
    exit(1);
}

int main(int argc, char* argv[])
{
    signal(SIGTERM, catch_signal);
    signal(SIGINT, catch_signal);

    int portNum=1;          //COM1 as default
    char portName[100];
    unsigned int baud = 115200;

    if (argc>1)
        portNum = atoi(argv[1]);
    switch (portNum)
    {
        case 0: strcpy(portName, RS485PORT); break;
        case 1: strcpy(portName, COM1); break;
        case 2: strcpy(portName, COM2); break;
        default: strcpy(portName, COM1); break;
    }

    if (argc>2)baud = atoi(argv[2]);

    if ((portNum==0) && (baud>RS485_BAUD_LIMIT))
        baud=RS485_BAUD_LIMIT;
    else if ((portNum>0) && (baud>RS232_BAUD_LIMIT))
        baud=RS232_BAUD_LIMIT;
    if (baud<1200)
        baud=1200;

    printf("Serial example: port=#%s, baud=%i\n", portName, baud);

    fd=tp_open_serial_port(portName, baud);
    if(fd<0)
         return 1;

    usleep(1e5);
    pthread_t tid1,tid2;
    pthread_create(&tid1, NULL, read_thread, NULL);
    pthread_create(&tid2, NULL, write_thread, NULL);
    pthread_join(tid1,NULL);
    pthread_join(tid2,NULL);

    return 0;
}
  • The function tp_open_serial_port is used to open the serial port (line 75).

  • Reading from and writing to serial port are performed by the standard read/write Linux functions. Two threads are created for read/write operations.

  • In write_thread (line 23 – 35) the keyboard is scanned for input key.

  • If any key is pressed (NRMKkbhit) it will be captured and sent to the serial port by write function. The first parameter for write function is file description of serial port, the second parameter is pointer to data buffer to be sent and the last one is the number of sent bytes.

  • The read_thread (line 9 – 21) is a polling loop which wait for data come serial port.

  • The read system function is used for getting data purpose, nbytes=read(fd,&chr,1). The first parameter for read function is file description of serial port, the second parameter is pointer to buffer to save comming data and the last one is the number of bytes to read. The return value of read function is actual number of received bytes.


  1. There is no RS485 port on STEP2 Blue cover. Please refer to RS485 port for details.