Если у меня есть два экземпляра Glib::IOChannel, они блокируются до тех пор, пока оба не будут записаны.Каков правильный способ сделать это?

StackOverflow https://stackoverflow.com/questions/1043588

  •  20-08-2019
  •  | 
  •  

Вопрос

Я изменил найденный пример здесь использовать два канала ввода-вывода.Похоже, ни один из обратных вызовов не был вызван до того, как я записал данные на оба канала.После этого они вызываются по отдельности при записи в fifos.Я что-то забыл?

  • Запустите тестовую программу в одном окне командной строки.
  • Напишите echo "abc" > testfifo1 во втором окне командной строки.-> ничего не происходит.
  • Напишите echo "def" > testfifo2 в третьем окне командной строки.-> теперь я получаю "abc" и "def"
  • Напишите в один из fifo.Это блюдо подается немедленно.

Редактировать:Решением, как намекнул Гормли ниже, было отсутствие неблока.

read_fd1 = open("testfifo1", O_RDONLY | O_NONBLOCK);
...
read_fd2 = open("testfifo2", O_RDONLY | O_NONBLOCK);

Это изменение в приведенном ниже коде заставило его отреагировать немедленно.

Код:

#include <gtkmm/main.h>
#include <fcntl.h>
#include <iostream>

int read_fd1, read_fd2;
Glib::RefPtr<Glib::IOChannel> iochannel1, iochannel2;

// Usage: "echo "Hello" > testfifo<1|2>", quit with "Q"

bool MyCallback1(Glib::IOCondition io_condition)
{
    Glib::ustring buf;
    iochannel1->read_line(buf);
    std::cout << "io 1: " << buf;

    if (buf == "Q\n")
        Gtk::Main::quit();

    return true;
}

bool MyCallback2(Glib::IOCondition io_condition)
{
    Glib::ustring buf;
    iochannel2->read_line(buf);
    std::cout << "io 2: " << buf;

    if (buf == "Q\n")
        Gtk::Main::quit();

    return true;
}

int main(int argc, char *argv[])
{
    // the usual Gtk::Main object
    Gtk::Main app(argc, argv);

    if (access("testfifo1", F_OK) == -1)
    {
        if (mkfifo("testfifo1", 0666) != 0)
            return -1;
    }

    if (access("testfifo2", F_OK) == -1)
    {
        if (mkfifo("testfifo2", 0666) != 0)
            return -1;
    }

    read_fd1 = open("testfifo1", O_RDONLY);

    if (read_fd1 == -1)
        return -1;

    read_fd2 = open("testfifo2", O_RDONLY);

    if (read_fd2 == -1)
        return -1;

    Glib::signal_io().connect(sigc::ptr_fun(MyCallback1), read_fd1, Glib::IO_IN);
    Glib::signal_io().connect(sigc::ptr_fun(MyCallback2), read_fd2, Glib::IO_IN);

    iochannel1 = Glib::IOChannel::create_from_fd(read_fd1);
    iochannel2 = Glib::IOChannel::create_from_fd(read_fd2);

    app.run();

    if (unlink("testfifo1"))
        std::cerr << "error removing fifo 1" << std::endl;

    if (unlink("testfifo2"))
        std::cerr << "error removing fifo 2" << std::endl;

    return 0;
}
Это было полезно?

Решение

Эти два оператора блокируют попадание программы в основной цикл до тех пор, пока оба fifos не будут открыты для записи.блокируйте fifos до тех пор, пока не будут подключены обе стороны

iochannel1 = Glib::IOChannel::create_from_fd(read_fd1);iochannel2 = Glib::IOChannel::create_from_fd(read_fd2);

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top