int fe_input_add (int sok, int flags, void *func, void *data) { int tag, type = 0; GIOChannel *channel; #ifdef G_OS_WIN32 if (flags & FIA_FD) channel = g_io_channel_win32_new_fd (sok); else channel = g_io_channel_win32_new_socket (sok); #else channel = g_io_channel_unix_new (sok); #endif if (flags & FIA_READ) type |= G_IO_IN | G_IO_HUP | G_IO_ERR; if (flags & FIA_WRITE) type |= G_IO_OUT | G_IO_ERR; if (flags & FIA_EX) type |= G_IO_PRI; tag = g_io_add_watch (channel, type, (GIOFunc) func, data); g_io_channel_unref (channel); return tag; }
GIOChannel * g_io_channel_unix_new (gint fd) { gboolean is_fd, is_socket; struct stat st; int optval, optlen; is_fd = (fstat (fd, &st) == 0); optlen = sizeof (optval); is_socket = (getsockopt (fd, SOL_SOCKET, SO_TYPE, (char *) &optval, &optlen) != SOCKET_ERROR); if (is_fd && is_socket) g_warning (G_STRLOC ": %d is both a file descriptor and a socket, file descriptor interpretation assumed.", fd); if (is_fd) return g_io_channel_win32_new_fd_internal (fd, &st); if (is_socket) return g_io_channel_win32_new_socket(fd); g_warning (G_STRLOC ": %d is neither a file descriptor or a socket", fd); return NULL; }
void HttpClient::on_connected(gpointer data, bool succeeded) { HttpClient *oHttpClient = (HttpClient *)data; if (!succeeded) { gchar *mes = g_strdup_printf("Can not connect to %s: %s\n", oHttpClient->host_.c_str(), Socket::get_error_msg().c_str()); on_error_.emit(oHttpClient, mes); g_free(mes); return; } #ifdef _WIN32 oHttpClient->channel_ = g_io_channel_win32_new_socket(oHttpClient->sd_); #else oHttpClient->channel_ = g_io_channel_unix_new(oHttpClient->sd_); #endif g_io_channel_set_encoding(oHttpClient->channel_, NULL, NULL); /* make sure that the channel is non-blocking */ int flags = g_io_channel_get_flags(oHttpClient->channel_); flags |= G_IO_FLAG_NONBLOCK; GError *err = NULL; g_io_channel_set_flags(oHttpClient->channel_, GIOFlags(flags), &err); if (err) { gchar *str = g_strdup_printf("Unable to set the channel as non-blocking: %s", err->message); on_error_.emit(oHttpClient, str); g_free(str); g_error_free(err); return; } if (oHttpClient->SendGetRequest()) return; oHttpClient->out_source_id_ = g_io_add_watch(oHttpClient->channel_, GIOCondition(G_IO_OUT), on_io_out_event, oHttpClient); oHttpClient->in_source_id_ = g_io_add_watch(oHttpClient->channel_, GIOCondition(G_IO_IN | G_IO_ERR), on_io_in_event, oHttpClient); }
/* Returns the FD or -1 on resource limit. */ int new_channel_from_socket (int sock) { int idx; for (idx = 0; idx < MAX_SLAFD; idx++) if (! giochannel_table[idx].used) break; if (idx == MAX_SLAFD) { errno = EIO; return -1; } giochannel_table[idx].used = 1; giochannel_table[idx].chan = g_io_channel_win32_new_socket (sock); giochannel_table[idx].fd = -1; giochannel_table[idx].socket = sock; giochannel_table[idx].primary = 1; g_io_channel_set_encoding (giochannel_table[idx].chan, NULL, NULL); g_io_channel_set_buffered (giochannel_table[idx].chan, FALSE); return idx; }
int fe_input_add (int sok, int read, int write, int ex, void *func, void *data) { int tag, type = 0; GIOChannel *channel; #ifdef WIN32 if (read == 3) channel = g_io_channel_win32_new_fd (sok); else channel = g_io_channel_win32_new_socket (sok); #else channel = g_io_channel_unix_new (sok); #endif if (read) type |= G_IO_IN | G_IO_HUP | G_IO_ERR; if (write) type |= G_IO_OUT | G_IO_ERR; if (ex) type |= G_IO_PRI; tag = g_io_add_watch (channel, type, (GIOFunc) func, data); g_io_channel_unref (channel); return tag; }
int main ( int argc, char **argv ) { int ifd = fileno( stdin ); int ofd = fileno( stdout ); GMainLoop *gmloop = g_main_loop_new( NULL, FALSE ); GError *error = NULL; GIOChannel *in ; GIOFlags flags ; GIOStatus status ; #ifdef G_PLATFORM_WIN32 // no idea if this works or not. in = g_io_channel_win32_new_socket( (HANDLE)win32_get_osfhandle(ifd) ); out = g_io_channel_win32_new_socket( (HANDLE)win32_get_osfhandle(ofd) ); #else in = g_io_channel_unix_new( ifd ); out = g_io_channel_unix_new( ofd ); #endif // *********************************************************************** g_queue_init( &out_queue ); // *********************************************************************** flags = g_io_channel_get_flags( in ); status = g_io_channel_set_flags( in, flags | G_IO_FLAG_NONBLOCK, &error ); if( status != G_IO_STATUS_NORMAL ) { fprintf( stderr , "Setting O_NONBLOCK on stdin: [%d] %s\n" , error->code, error->message ); g_clear_error( &error ); exit( error->code ); } // *********************************************************************** g_io_add_watch ( in, IO_IN , (GIOFunc)sexp_handler, NULL ); g_io_add_watch ( in, IO_ERR, (GIOFunc)quit_handler, gmloop ); //g_timeout_add ( 1000, _heartbeat, NULL ); sexp_init ( &parser ); g_main_loop_run ( gmloop ); sexp_exit ( &parser ); purple_plugins_unload_all(); purple_core_quit(); exit( 0 ); }
GIOChannel *g_io_channel_new(int handle) { GIOChannel *chan; #ifdef WIN32 chan = g_io_channel_win32_new_socket(handle); #else chan = g_io_channel_unix_new(handle); #endif g_io_channel_set_encoding(chan, NULL, NULL); g_io_channel_set_buffered(chan, FALSE); return chan; }
static gboolean sock_connect_async_cb(GIOChannel *source, GIOCondition condition, gpointer data) { SockConnectData *conn_data = (SockConnectData *)data; gint fd; gint val; guint len; SockInfo *sockinfo; if (conn_data->io_tag == 0 && conn_data->channel == NULL) return FALSE; fd = g_io_channel_unix_get_fd(source); conn_data->io_tag = 0; conn_data->channel = NULL; g_io_channel_unref(source); len = sizeof(val); if (getsockopt(fd, SOL_SOCKET, SO_ERROR, &val, &len) < 0) { perror("getsockopt"); close(fd); sock_connect_address_list_async(conn_data); return FALSE; } if (val != 0) { close(fd); log_error(LOG_PROTOCOL, _("%s:%d: connection failed (%s).\n"), conn_data->hostname, conn_data->port, strerror(val)); sock_connect_address_list_async(conn_data); return FALSE; } sockinfo = g_new0(SockInfo, 1); sockinfo->sock = fd; #ifndef G_OS_WIN32 sockinfo->sock_ch = g_io_channel_unix_new(fd); #else sockinfo->sock_ch = g_io_channel_win32_new_socket(fd); #endif sockinfo->hostname = g_strdup(conn_data->hostname); sockinfo->port = conn_data->port; sockinfo->state = CONN_ESTABLISHED; sockinfo->canonical_name = g_strdup(conn_data->canonical_name); conn_data->func(sockinfo, conn_data->data); sock_connect_async_cancel(conn_data->id); return FALSE; }
GIOChannel * g_io_channel_unix_new (gint fd) { struct stat st; if (fstat (fd, &st) == 0) return g_io_channel_win32_new_fd (fd); if (getsockopt (fd, SOL_SOCKET, SO_TYPE, NULL, NULL) != SO_ERROR) return g_io_channel_win32_new_socket(fd); g_warning (G_STRLOC ": %d is neither a file descriptor or a socket", fd); return NULL; }
static gint sock_connect_address_list_async(SockConnectData *conn_data) { SockAddrData *addr_data; gint sock = -1; for (; conn_data->cur_addr != NULL; conn_data->cur_addr = conn_data->cur_addr->next) { addr_data = (SockAddrData *)conn_data->cur_addr->data; if ((sock = socket(addr_data->family, addr_data->socktype, addr_data->protocol)) < 0) { perror("socket"); continue; } set_nonblocking_mode(sock, TRUE); if (connect(sock, addr_data->addr, addr_data->addr_len) < 0) { if (EINPROGRESS == errno) { break; } else { perror("connect"); close(sock); } } else { break; } } if (conn_data->cur_addr == NULL) { conn_data->func(NULL, conn_data->data); sock_connect_async_cancel(conn_data->id); return -1; } conn_data->cur_addr = conn_data->cur_addr->next; #ifndef G_OS_WIN32 conn_data->channel = g_io_channel_unix_new(sock); #else conn_data->channel = g_io_channel_win32_new_socket(sock); #endif conn_data->io_tag = g_io_add_watch(conn_data->channel, G_IO_IN|G_IO_OUT, sock_connect_async_cb, conn_data); return 0; }
void DictClient::on_resolved(gpointer data, struct hostent *ret) { DictClient *oDictClient = (DictClient *)data; oDictClient->sd_ = Socket::socket(); if (oDictClient->sd_ == -1) { on_error_.emit("Can not create socket: " + Socket::get_error_msg()); return; } #ifdef _WIN32 oDictClient->channel_ = g_io_channel_win32_new_socket(oDictClient->sd_); #else oDictClient->channel_ = g_io_channel_unix_new(oDictClient->sd_); #endif /* RFC2229 mandates the usage of UTF-8, so we force this encoding */ g_io_channel_set_encoding(oDictClient->channel_, "UTF-8", NULL); g_io_channel_set_line_term(oDictClient->channel_, "\r\n", 2); /* make sure that the channel is non-blocking */ int flags = g_io_channel_get_flags(oDictClient->channel_); flags |= G_IO_FLAG_NONBLOCK; GError *err = NULL; g_io_channel_set_flags(oDictClient->channel_, GIOFlags(flags), &err); if (err) { g_io_channel_unref(oDictClient->channel_); oDictClient->channel_ = NULL; on_error_.emit("Unable to set the channel as non-blocking: " + std::string(err->message)); g_error_free(err); return; } if (!Socket::connect(oDictClient->sd_, ret, oDictClient->port_)) { gchar *mes = g_strdup_printf("Can not connect to %s: %s\n", oDictClient->host_.c_str(), Socket::get_error_msg().c_str()); on_error_.emit(mes); g_free(mes); return; } oDictClient->source_id_ = g_io_add_watch(oDictClient->channel_, GIOCondition(G_IO_IN | G_IO_ERR), on_io_event, oDictClient); }
static SockInfo *sockinfo_from_fd(const gchar *hostname, gushort port, gint sock) { SockInfo *sockinfo; sockinfo = g_new0(SockInfo, 1); sockinfo->sock = sock; #ifndef G_OS_WIN32 sockinfo->sock_ch = g_io_channel_unix_new(sock); #else sockinfo->sock_ch = g_io_channel_win32_new_socket(sock); #endif sockinfo->hostname = g_strdup(hostname); sockinfo->port = port; sockinfo->state = CONN_ESTABLISHED; return sockinfo; }
void StarDictClient::on_connected(gpointer data, bool succeeded) { StarDictClient *oStarDictClient = (StarDictClient *)data; if (!succeeded) { static bool showed_once = false; if (!showed_once) { showed_once = true; gchar *mes = g_strdup_printf(_("Can not connect to %s: %s\n"), oStarDictClient->host_.c_str(), Socket::get_error_msg().c_str()); on_error_.emit(mes); g_free(mes); } return; } #ifdef _WIN32 oStarDictClient->channel_ = g_io_channel_win32_new_socket(oStarDictClient->sd_); #else oStarDictClient->channel_ = g_io_channel_unix_new(oStarDictClient->sd_); #endif g_io_channel_set_encoding(oStarDictClient->channel_, NULL, NULL); /* make sure that the channel is non-blocking */ int flags = g_io_channel_get_flags(oStarDictClient->channel_); flags |= G_IO_FLAG_NONBLOCK; GError *err = NULL; g_io_channel_set_flags(oStarDictClient->channel_, GIOFlags(flags), &err); if (err) { g_io_channel_unref(oStarDictClient->channel_); oStarDictClient->channel_ = NULL; gchar *str = g_strdup_printf(_("Unable to set the channel as non-blocking: %s"), err->message); on_error_.emit(str); g_free(str); g_error_free(err); return; } oStarDictClient->is_connected_ = true; oStarDictClient->waiting_banner_ = true; oStarDictClient->reading_type_ = READ_LINE; oStarDictClient->in_source_id_ = g_io_add_watch(oStarDictClient->channel_, GIOCondition(G_IO_IN | G_IO_ERR), on_io_in_event, oStarDictClient); }
static void client_init(struct client *client, int fd) { static unsigned int next_client_num; assert(fd >= 0); client->cmd_list_size = 0; client->cmd_list_OK = -1; #ifndef G_OS_WIN32 client->channel = g_io_channel_unix_new(fd); #else client->channel = g_io_channel_win32_new_socket(fd); #endif /* GLib is responsible for closing the file descriptor */ g_io_channel_set_close_on_unref(client->channel, true); /* NULL encoding means the stream is binary safe; the MPD protocol is UTF-8 only, but we are doing this call anyway to prevent GLib from messing around with the stream */ g_io_channel_set_encoding(client->channel, NULL, NULL); /* we prefer to do buffering */ g_io_channel_set_buffered(client->channel, false); client->source_id = g_io_add_watch(client->channel, G_IO_IN|G_IO_ERR|G_IO_HUP, client_in_event, client); client->input = fifo_buffer_new(4096); client->lastTime = time(NULL); client->cmd_list = NULL; client->deferred_send = g_queue_new(); client->deferred_bytes = 0; client->num = next_client_num++; client->send_buf_used = 0; client->permission = getDefaultPermissions(); (void)write(fd, GREETING, sizeof(GREETING) - 1); }
/* Binary compatibility */ GIOChannel * g_io_channel_win32_new_stream_socket (int socket) { return g_io_channel_win32_new_socket (socket); }
static void * glib_ctx_add(void *ctx, const verto_ev *ev, verto_ev_flag *flags) { glib_ev *gev = NULL; GIOCondition cond = 0; verto_ev_type type = verto_get_type(ev); gev = g_new0(glib_ev, 1); if (!gev) return NULL; switch (type) { case VERTO_EV_TYPE_IO: #ifdef WIN32 gev->chan = g_io_channel_win32_new_socket(verto_get_fd(ev)); #else gev->chan = g_io_channel_unix_new(verto_get_fd(ev)); #endif if (!gev->chan) goto error; g_io_channel_set_close_on_unref(gev->chan, FALSE); if (*flags & VERTO_EV_FLAG_IO_READ) cond |= G_IO_IN | G_IO_PRI | G_IO_ERR | G_IO_HUP | G_IO_NVAL; if (*flags & VERTO_EV_FLAG_IO_WRITE) cond |= G_IO_OUT | G_IO_ERR | G_IO_HUP | G_IO_NVAL; gev->src = g_io_create_watch(gev->chan, cond); break; case VERTO_EV_TYPE_TIMEOUT: gev->src = g_timeout_source_new(verto_get_interval(ev)); break; case VERTO_EV_TYPE_IDLE: gev->src = g_idle_source_new(); break; case VERTO_EV_TYPE_CHILD: gev->src = g_child_watch_source_new(verto_get_proc(ev)); *flags &= ~VERTO_EV_FLAG_PERSIST; /* Child events don't persist */ break; case VERTO_EV_TYPE_SIGNAL: #if GLIB_MAJOR_VERSION >= 2 #if GLIB_MINOR_VERSION >= 29 #ifdef G_OS_UNIX /* Not supported on Windows */ gev->src = g_unix_signal_source_new(verto_get_signal(ev)); break; #endif #endif /* GLIB_MINOR_VERSION >= 29 */ #endif /* GLIB_MAJOR_VERSION >= 2 */ default: return NULL; /* Not supported */ } if (!gev->src) goto error; if (type == VERTO_EV_TYPE_IO) g_source_set_callback(gev->src, (GSourceFunc) glib_callback_io, (void *) ev, NULL); else if (type == VERTO_EV_TYPE_CHILD) g_source_set_callback(gev->src, (GSourceFunc) glib_callback_child, (void *) ev, NULL); else g_source_set_callback(gev->src, glib_callback, (void *) ev, NULL); if (*flags & VERTO_EV_FLAG_PRIORITY_HIGH) g_source_set_priority(gev->src, G_PRIORITY_HIGH); else if (*flags & VERTO_EV_FLAG_PRIORITY_MEDIUM) g_source_set_priority(gev->src, G_PRIORITY_DEFAULT_IDLE); else if (*flags & VERTO_EV_FLAG_PRIORITY_LOW) g_source_set_priority(gev->src, G_PRIORITY_LOW); g_source_set_can_recurse(gev->src, FALSE); if (g_source_attach(gev->src, ((glib_ev_ctx*) ctx)->context) == 0) goto error; return gev; error: if (gev) { if (gev->chan) g_io_channel_unref(gev->chan); if (gev->src) { g_source_destroy(gev->src); g_source_unref(gev->src); } g_free(gev); } return NULL; }