如何使用GIOChannel

时间:2017-07-19 10:09:03

标签: gtk3 glib gio

我从stackoverflow本身得到了以下样本。

#include <glib.h>
#include <gio/gio.h>

gchar *buffer;

gboolean
network_write(GIOChannel *source,
            GIOCondition cond,
            gpointer data)
{
    return TRUE;
}
gboolean
network_read(GIOChannel *source,
            GIOCondition cond,
            gpointer data)
{
    GString *s = g_string_new(NULL);
    GError *error;
    g_print("Inside network_read function\n");
    GIOStatus ret = g_io_channel_read_line_string(source, s, NULL, &error);
    if (ret == G_IO_STATUS_ERROR)
        g_error ("Error reading: %s\n", error->message);
    else
        g_print("Got: %s\n", s->str);

    return TRUE;
}

gboolean
new_connection(GSocketService *service,
              GSocketConnection *connection,
              GObject *source_object,
              gpointer user_data)
{
  GSocketAddress *sockaddr = g_socket_connection_get_remote_address(connection, NULL);
  GInetAddress *addr = g_inet_socket_address_get_address(G_INET_SOCKET_ADDRESS(sockaddr));
  guint16 port = g_inet_socket_address_get_port(G_INET_SOCKET_ADDRESS(sockaddr));

  g_print("New Connection from %s:%d\n", g_inet_address_to_string(addr), port);

  GSocket *socket = g_socket_connection_get_socket(connection);

  gint fd = g_socket_get_fd(socket);
g_print("Naseeb fd: %d\n", fd);
  GIOChannel *channel = g_io_channel_unix_new(fd);
  if(!g_io_add_watch(channel, G_IO_IN, (GIOFunc) network_read, NULL))
  {
      g_print("Got Error while adding network_read\n");
  }
//  g_io_add_watch(channel, G_IO_OUT, (GIOFunc) network_write, NULL);
  return TRUE;
}

int main(int argc, char **argv) {
    g_type_init();
    GSocketService *service = g_socket_service_new();
    GInetAddress *address = g_inet_address_new_from_string("0.0.0.0");
    GSocketAddress *socket_address = g_inet_socket_address_new(address, 3001);
    g_socket_listener_add_address(G_SOCKET_LISTENER(service), socket_address, G_SOCKET_TYPE_STREAM,
            G_SOCKET_PROTOCOL_TCP, NULL, NULL, NULL);

    g_object_unref(socket_address);
    g_object_unref(address);
    g_socket_service_start(service);

    g_signal_connect(service, "incoming", G_CALLBACK(new_connection), NULL);
    g_socket_service_start(service);

    GMainLoop *loop = g_main_loop_new(NULL, FALSE);
    g_main_loop_run(loop);
    return 0;
}

使用此代码,我可以将客户端连接到服务器。我使用 new_connection

函数中打印的消息确认相同内容

但是当我从客户端发送数据时,回调 network_read 永远不会在服务器上调用。虽然客户端,send()API返回值显示发送的总字节数。

1)服务器端是否缺少api。 2)调用 network_write 的正确方法是什么?

1 个答案:

答案 0 :(得分:0)

您不应该使用GIOChannelnew_connection()已经有连接,您可以使用stream = g_io_stream_get_input_stream (G_IO_STREAM (connection));来获取GInputStream来读取。