Linux CAN socketCAN—文件传输的可靠性如何

Linux CAN socketCAN—文件传输的可靠性如何,linux,qt,can-bus,esp32,Linux,Qt,Can Bus,Esp32,我想将文件(每个大约4MB的mp3)发送到通过CAN连接的设备。我正在用Linux机器和ESP32进行测试。问题在于并非所有数据都到达目的地 我使用socketCAN和UCCB USB-CAN转换器从Linux机器发送 到ESP32,或在两个ESP32之间 从PC Linux发送到ESP32时,有时只保存1/3的mp3文件,在发送过程中,我运行了candump slcan0命令,看起来所有数据都在总线上,但ESP32没有看到一些帧 当我在两个ESP32之间发送数据时,例如4MB的数据,接收到的E

我想将文件(每个大约4MB的mp3)发送到通过CAN连接的设备。我正在用Linux机器和ESP32进行测试。问题在于并非所有数据都到达目的地

我使用socketCAN和UCCB USB-CAN转换器从Linux机器发送 到ESP32,或在两个ESP32之间

从PC Linux发送到ESP32时,有时只保存1/3的mp3文件,在发送过程中,我运行了candump slcan0命令,看起来所有数据都在总线上,但ESP32没有看到一些帧

当我在两个ESP32之间发送数据时,例如4MB的数据,接收到的ESP32会得到大约398MB的数据,一些帧会丢失

我正在使用命令“slcand-o-c-f-s8/dev/ttyACM0 slcan0”来创建slcan0接口,尽管使用-s开关改变速度似乎不起作用

我是否遗漏了什么,或者CAN不适合这种高速、高负载操作?我想在canbus上安装30台设备,接收大约1GB的数据(mp3文件)

代码如下:

CanMgr::CanMgr(QObject *parent,LogModel *logModel):QObject(parent) {
    this->logModel=logModel;

    send_timer=new QTimer(this);
    send_timer->setSingleShot(true);
    send_timer->setInterval(1);
    connect(send_timer,&QTimer::timeout,this,&CanMgr::processQueue);
}
void CanMgr::connectDevice() {
    QString errorString;
    m_canDevice = QCanBus::instance()->createDevice(m_pluginName,m_socketName,&errorString);

    if (!m_canDevice) {
        qDebug()<<QString("Error creating device '%1', reason: '%2'").arg(m_pluginName).arg(errorString);
        return;
    }

    m_numberFramesWritten = 0;

    connect(m_canDevice, &QCanBusDevice::errorOccurred, this, &CanMgr::processErrors);
    connect(m_canDevice, &QCanBusDevice::framesReceived, this, &CanMgr::processReceivedFrames);
    connect(m_canDevice, &QCanBusDevice::framesWritten, this, &CanMgr::processFramesWritten);
    connect(m_canDevice, &QCanBusDevice::stateChanged,this, &CanMgr::stateChanged);


    m_canDevice->setConfigurationParameter(QCanBusDevice::BitRateKey,"250000");
    if (!m_canDevice->connectDevice()) {
        qDebug()<<tr("Connection error: %1").arg(m_canDevice->errorString());

        delete m_canDevice;
        m_canDevice = nullptr;
    } else {

        QVariant bitRate = m_canDevice->configurationParameter(QCanBusDevice::BitRateKey);
        if (bitRate.isValid()) {
            qDebug()<<tr("Plugin: %1, connected to %2 at %3 kBit/s").arg(m_pluginName).arg(m_socketName).arg(bitRate.toInt() / 1000);
        } else {
            qDebug()<<tr("Plugin: %1, connected to %2").arg(m_pluginName).arg(m_socketName);
        }
    }
}
void CanMgr::sendFileContent(QByteArray data) {
    quint32 frameId = 0;
    quint32 dev_id=2;
    quint32 cmd_id=0;
    frameId=(dev_id<<16) | cmd_id;

    m_canDevice->clear();


    QByteArray size=Helper::byteArrFromInt((quint32)data.size(),8);
    qDebug()<<"CanMgr::sendFileContent file size in bytes:"<<Helper::printHex(size);

    QCanBusFrame frame = QCanBusFrame(frameId,size);
    frame.setExtendedFrameFormat(true);
    qDebug()<<"frame data:"<<frame.toString()<<" stat:"<<m_canDevice->state();
    queue.append(frame);

    frameId = 0;
    dev_id=2;
    cmd_id=1;

    frameId=(dev_id<<16) | cmd_id;

    for(int i=0;i<data.size();i+=8) {

        QCanBusFrame frame = QCanBusFrame(frameId, data.mid(i,8));
        frame.setExtendedFrameFormat(true);
        queue.append(frame);
    }

    frameId = 0;
    dev_id=2;
    cmd_id=2;
    frameId=(dev_id<<16) | cmd_id;


    frame = QCanBusFrame(frameId, size);
    frame.setExtendedFrameFormat(true);
    queue.append(frame);

    process_frame=false;
    send_timer->start();
}
void CanMgr::processQueue() {
    if(queue.isEmpty()) {
        qDebug()<<"CanMgr::processQueu queue empty";
        return;
    }
    if(process_frame) {
        ;
    }
    else {
        curr_frame=queue.dequeue();
        process_frame=true;
    }
    qDebug()<<"CanMgr::processQueue frame data:"<<curr_frame.toString()<<" towrite:"<<m_canDevice->framesToWrite()<<" left:"<<queue.count();

    m_canDevice->writeFrame(curr_frame);
}
void CanMgr::processFramesWritten(qint64 count) {
    qDebug()<<"CanMgr::processFramesWritten count:"<<count;
    process_frame=false;
    this->processQueue();
}
QString CanMgr::processErrors(QCanBusDevice::CanBusError error) const
{
    QString err_str;
    switch (error) {
    case QCanBusDevice::ReadError:
    case QCanBusDevice::WriteError:
    case QCanBusDevice::ConnectionError:
    case QCanBusDevice::ConfigurationError:
    case QCanBusDevice::UnknownError:
        err_str= m_canDevice->errorString();
        qDebug()<<"Error:"<<err_str;
        send_timer->start();
        return err_str;
        break;
    default:
        break;
    }
}
CanMgr::CanMgr(QObject*父对象,LogModel*LogModel):QObject(父对象){
此->logModel=logModel;
发送计时器=新的QTimer(此);
发送定时器->设置单次显示(真);
发送定时器->设置间隔(1);
连接(发送计时器、&QTimer::timeout、this、&CanMgr::processQueue);
}
void CanMgr::connectDevice(){
QString错误字符串;
m_canDevice=QCanBus::instance()->createDevice(m_pluginName、m_socketName和&errorString);
如果(!m_canDevice){
qDebug()连接设备(){
qDebug()配置参数(QCanBusDevice::BitRateKey);
if(bitRate.isValid()){

qDebug()我会说显示您的I/O代码。添加到原始POST的代码您肯定丢失了一些东西,因为CAN没有数据包丢失。数据包仅在tx或rx缓冲区溢出时在节点内丢失。原因可能是发送器没有等待可用的缓冲区,或者是因为接收器没有在e下一个到达。@Lundin你说得对。例如,当我从ESP向PC发送数据时,我得到了所有的数据包(当然PC会更快)。当我从PC向ESP发送数据包时,ESP会收到1/4的数据包,因此我同意缓冲区溢出。但如何处理该问题,而不是:发送一个数据包(PC到ESP)-等待确认(ESP到PC)-发送另一个数据包(PC到ESP)