C++ 监控串口的多路复用技术DEMO
时间: 2023-07-31 17:05:52 浏览: 59
以下是一个使用多路复用技术监控串口的 C++ DEMO:
```c++
#include <iostream>
#include <string>
#include <vector>
#include <chrono>
#include <thread>
#include <fcntl.h>
#include <termios.h>
#include <unistd.h>
#include <sys/select.h>
using namespace std::chrono_literals;
// 打开串口
int open_serial_port(const std::string& port_name) {
int fd = open(port_name.c_str(), O_RDWR | O_NOCTTY | O_NONBLOCK);
if (fd < 0) {
std::cerr << "Failed to open serial port " << port_name << std::endl;
return -1;
}
// 设置串口属性
struct termios tty;
memset(&tty, 0, sizeof(tty));
if (tcgetattr(fd, &tty) != 0) {
std::cerr << "Failed to get serial port attributes" << std::endl;
close(fd);
return -1;
}
cfsetospeed(&tty, B115200);
cfsetispeed(&tty, B115200);
tty.c_cflag &= ~CSIZE;
tty.c_cflag |= CS8;
tty.c_cflag &= ~PARENB;
tty.c_cflag &= ~CSTOPB;
tty.c_cflag &= ~CRTSCTS;
tty.c_lflag = 0;
tty.c_oflag = 0;
tty.c_cc[VMIN] = 1;
tty.c_cc[VTIME] = 10;
if (tcsetattr(fd, TCSANOW, &tty) != 0) {
std::cerr << "Failed to set serial port attributes" << std::endl;
close(fd);
return -1;
}
return fd;
}
// 监控串口
void monitor_serial_port(const std::vector<int>& fds) {
fd_set read_fds;
FD_ZERO(&read_fds);
for (auto fd : fds) {
FD_SET(fd, &read_fds);
}
while (true) {
fd_set tmp_fds = read_fds;
int ret = select(FD_SETSIZE, &tmp_fds, nullptr, nullptr, nullptr);
if (ret < 0) {
std::cerr << "Failed to select file descriptors" << std::endl;
continue;
}
for (auto fd : fds) {
if (FD_ISSET(fd, &tmp_fds)) {
char buf[1024];
int len = read(fd, buf, sizeof(buf));
if (len <= 0) {
std::cerr << "Failed to read data from serial port" << std::endl;
continue;
}
std::string data(buf, buf + len);
std::cout << "Received data [" << data << "]" << std::endl;
}
}
}
}
int main() {
// 打开两个串口
int fd1 = open_serial_port("/dev/ttyS0");
int fd2 = open_serial_port("/dev/ttyS1");
// 监控串口
if (fd1 >= 0 && fd2 >= 0) {
std::vector<int> fds{fd1, fd2};
std::thread thread(monitor_serial_port, fds);
thread.detach();
}
// 发送数据
while (true) {
std::string data;
std::cout << "Please input data to send: ";
std::getline(std::cin, data);
if (data == "exit") {
break;
}
write(fd1, data.c_str(), data.size());
std::this_thread::sleep_for(100ms);
write(fd2, data.c_str(), data.size());
}
// 关闭串口
close(fd1);
close(fd2);
return 0;
}
```
在这个 DEMO 中,我们打开了两个串口 `/dev/ttyS0` 和 `/dev/ttyS1`,并使用多路复用技术同时监控这两个串口。当有数据到达时,我们将其打印出来。同时,我们也可以在命令行中输入数据并发送到串口上。注意,由于我们使用了非阻塞方式读取串口数据,因此在 DEMO 中使用了一个 100ms 的延时来确保数据已经写入串口。