我希望有一个进程g_main_loop,它调用文件描述符中传入字符的回调。
所以我尝试在我的电路板上使用上面的代码手动创建/home/dev
文件。
除了启动此代码之外,不做其他事情,回调是持续调用。
我不明白为什么。我希望只有在/home/dev
文件中写入才能调用回调。它是f_open
文件选项问题吗?或者我没有做正确的事情,因为文件描述符认为数据是读取的?
#include <stdio.h>
#include <glib.h>
#include <glib/gstdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
gboolean cb_1 (GIOChannel *source, GIOCondition condition, gpointer data);
int main(void)
{
GMainLoop* mainloop;
int fd;
GIOChannel* channel;
mainloop = g_main_loop_new(NULL, TRUE);
fd=g_open("/home/dev", O_RDONLY, O_NONBLOCK);
channel=g_io_channel_unix_new(fd);
g_io_add_watch(channel, G_IO_IN, cb_1, NULL);
g_main_loop_run(mainloop);
g_main_loop_unref(mainloop);
}
gboolean cb_1 (GIOChannel *source, GIOCondition condition, gpointer data)
{
gchar** line=NULL;
GIOStatus status;
GError* error;
printf("cb\n");
status=g_io_channel_read_line(source, line, NULL, NULL, &error);
if(G_IO_STATUS_NORMAL == status)
{
printf("callback : data : %s\n", *line);
g_free(*line);
}
return TRUE;
}
答案 0 :(得分:1)
只要文件可供阅读,打开文件并创建频道就会触发回调。
在Linux中,您需要使用inotify观察器来实现您想要的效果。以下是帮助您理解它的代码段。在回调方法中,您需要读取struct inotify_event以了解调用回调的事件。阅读inotify手册页,了解可以使用的可能掩码的完整详细信息。您可能还需要IN_CREATE |等标志IN_DELETE。
#include <stdio.h>
#include <stdlib.h>
#include <glib.h>
#include <sys/inotify.h>
GMainLoop *mainloop;
static gboolean inotify_data(GIOChannel * channel, GIOCondition cond, gpointer user_data)
{
printf("event on GIOChannel\n");
char buffer[256];
gsize bytes_read;
GIOStatus status = g_io_channel_read_chars(channel, buffer, sizeof(buffer) - 1, &bytes_read, NULL);
/* buffer can have multiple inotify_event structs which contains
* details of what event, which file triggered this callback.
*/
return TRUE;
}
int main(void)
{
int fd, wd;
GIOChannel *channel;
mainloop = g_main_loop_new(NULL, FALSE);
fd = inotify_init();
if (fd < 0) {
exit(EXIT_FAILURE);
}
wd = inotify_add_watch(fd, "/home/test", IN_OPEN | IN_MODIFY);
channel = g_io_channel_unix_new(fd);
if (!channel) {
close(fd);
exit(EXIT_FAILURE);
}
g_io_channel_set_close_on_unref(channel, TRUE);
g_io_channel_set_encoding(channel, NULL, NULL);
g_io_channel_set_buffered(channel, FALSE);
g_io_add_watch(channel, G_IO_IN | G_IO_HUP | G_IO_NVAL | G_IO_ERR, inotify_data, NULL);
g_main_loop_run(mainloop);
return 0;
}