在MacOS上写入串行端口时出现问题

时间:2018-10-03 11:57:59

标签: c++ macos serial-port boost-asio macos-mojave

背景

我正在尝试向MacOS Mojave上的串行端口写入/打印。串行端口通过ESC / POS仿真连接到热敏打印机。我已使用boost::asio::serial_port中的boost 1.67.0来完成此任务。请参见以下代码:

#define SUCCESS 0
#define FAIL -1

#include <string>
#include <cstdio>
#include <iostream>
#include <boost/asio.hpp>
#include <boost/asio/serial_port.hpp>

int main(int argc, char *argv[]){

    boost::system::error_code ec;
    boost::asio::io_service io;
    boost::asio::serial_port port( io );

    std::string portname="/dev/tty.usbserial-12";

    try{
        port.open(portname.c_str(), ec);

        if (ec) {
            std::cout << "error : port.open() failed... portname=" << portname << ", e=" << ec.message().c_str() << std::endl; 
            return FAIL;
        }
        port.set_option( boost::asio::serial_port_base::baud_rate( 19200 ) );

        unsigned char init[2] = { 27, 64 };
        unsigned char hello[6] = { 'h', 'e', 'l', 'l', 'o', '\0'};
        unsigned char cut[2] = { 29, 86 };

        boost::asio::write(port, boost::asio::buffer(init, sizeof(init)));
        boost::asio::write(port, boost::asio::buffer(hello, sizeof(hello)));
        boost::asio::write(port, boost::asio::buffer(cut, sizeof(cut)));

        port.close();
        return SUCCESS;
    }catch(...){
        return FAIL;
    }
}

编辑1

我尝试在以下代码段中使用FileDescriptor:

int fd; //Descriptor for the port
fd = open("/dev/tty.usbserial-12", O_RDWR | O_NOCTTY | O_NDELAY);
if (fd == -1) {
    std::cout << "Unable to open port. \n";
    return FAIL;
}

struct termios options;

tcgetattr(fd, &options);
cfsetispeed(&options, B19200);
cfsetospeed(&options, B19200);

options.c_cflag &= ~PARENB;
options.c_cflag &= ~CSTOPB;
options.c_cflag &= ~CSIZE;
options.c_oflag &= ~OPOST;
options.c_cflag |= CS8;
options.c_cflag |= (CLOCAL | CREAD);
tcsetattr(fd, TCSANOW, &options);

std::cout << "Port configured.\n";

unsigned char init[2] = { 27, 64 };
unsigned char hello[6] = { 'h', 'e', 'l', 'l', 'o', '\0'};
unsigned char cut[2] = { 29, 86};

int rv = FAIL;

rv = write(fd, init, 2);
if(rv<SUCCESS){
    std::cout << "could not write" << std::endl;
    return FAIL;
}

rv = write(fd, "hello\n", 6);
if(rv<SUCCESS){
    std::cout << "could not write" << std::endl;
    return FAIL;
}

rv = write(fd, cut, 2);
if(rv<SUCCESS){
    std::cout << "could not write" << std::endl;
    return FAIL;
}

std::cout << "closing FD" << std::endl;
close(fd);
return SUCCESS;

上一个片段的控制台输出:

Port configured.
closing FD

不幸的是,在设备端没有错误并且没有输出

编辑1 END

通过将ls /dev/tty.usbserial*ls /dev/cu.usbserial*的输出连接到Mac之前和之后,我可以确认MacOS拾取了连接的串行端口。

此外,如果我运行screen /dev/tty.usbserial-12 19200,然后运行我的应用,则会收到一条错误消息,指出该resource busy

在进行在线搜索时,我遇到了一个SimpleSerial实现,并在文件顶部写了以下注释:

  

重要提示:   在Mac OS X Boost上,asio的串行端口存在错误,并且通常实现   这个类的不起作用。因此,暂时编写了一个变通方法类,   直到asio(希望如此)才能修复Mac对串行端口的兼容性。   请注意,与asio之前OS X文档中所述不同的是   是固定的串行端口 writes 不是异步的,但至少   异步 read 起作用。   此外,打开的串行端口会忽略以下选项:奇偶校验,   字符大小,流,停止位,默认为8N1格式。   我知道这很糟糕,但至少总比没有好。

我尝试在线搜索以确认存在一个已知错误,但找不到相关错误。

问题

上面的代码执行没有任何错误,但是由于我不知道的原因,打印机上没有输出。我可以使用screen /dev/tty.usbserial-12 19200“打印”。

相同的代码在运行raspbian的Raspberry PI上可以正常工作,并在打印机上产生所需的输出。

问题

我的代码有什么问题吗?我一路上错过了一些步骤吗?我该如何解决这个问题?

0 个答案:

没有答案