diff --git a/configure.in b/configure.in index 514fd753e..5c33ab951 100644 --- a/configure.in +++ b/configure.in @@ -954,6 +954,26 @@ AC_CHECK_FUNCS(_NSGetEnviron) AC_FUNC_VSNPRINTF_C99 AC_FUNC_PRINTF_UNIX98 +# Internet address families +if test $glib_native_win32 = yes; then + glib_inet_includes=[" +#include + "] +else + glib_inet_includes=[" +#include + "] +fi + +glib_failed=false +GLIB_CHECK_VALUE(AF_INET, $glib_inet_includes, glib_failed=true) +GLIB_CHECK_VALUE(AF_INET6, $glib_inet_includes, glib_failed=true) +# winsock defines this even though it doesn't support it +GLIB_CHECK_VALUE(AF_UNIX, $glib_inet_includes, glib_failed=true) +if $glib_failed ; then + AC_MSG_ERROR([Could not determine values for AF_INET* constants]) +fi + dnl dnl if statfs() takes 2 arguments (Posix) or 4 (Solaris) dnl @@ -2986,6 +3006,10 @@ _______EOF */ typedef $g_pid_type GPid; +#define GLIB_SYSDEF_AF_UNIX $g_af_unix +#define GLIB_SYSDEF_AF_INET $g_af_inet +#define GLIB_SYSDEF_AF_INET6 $g_af_inet6 + G_END_DECLS #endif /* GLIBCONFIG_H */ @@ -3272,6 +3296,10 @@ g_pollhup=$glib_cv_value_POLLHUP g_pollerr=$glib_cv_value_POLLERR g_pollnval=$glib_cv_value_POLLNVAL +g_af_unix=$glib_cv_value_AF_UNIX +g_af_inet=$glib_cv_value_AF_INET +g_af_inet6=$glib_cv_value_AF_INET6 + g_stack_grows=$glib_cv_stack_grows g_have_eilseq=$have_eilseq diff --git a/docs/reference/gio/gio-docs.xml b/docs/reference/gio/gio-docs.xml index 46af7fe4d..8872ed7af 100644 --- a/docs/reference/gio/gio-docs.xml +++ b/docs/reference/gio/gio-docs.xml @@ -90,6 +90,13 @@ + + Networking + + + + + Utilities diff --git a/docs/reference/gio/gio-sections.txt b/docs/reference/gio/gio-sections.txt index 36e9aee34..a2d19b7c5 100644 --- a/docs/reference/gio/gio-sections.txt +++ b/docs/reference/gio/gio-sections.txt @@ -1312,4 +1312,95 @@ g_io_extension_point_set_required_type g_io_extension_ref_class +
+ginetaddress +GInetAddress +GInetAddress +g_inet_address_new_from_string +g_inet_address_new_from_bytes +g_inet_address_new_any +g_inet_address_new_loopback +g_inet_address_to_bytes +g_inet_address_to_string +g_inet_address_get_family +g_inet_address_get_is_any +g_inet_address_get_is_link_local +g_inet_address_get_is_loopback +g_inet_address_get_is_mc_global +g_inet_address_get_is_mc_link_local +g_inet_address_get_is_mc_node_local +g_inet_address_get_is_mc_org_local +g_inet_address_get_is_mc_site_local +g_inet_address_get_is_multicast +g_inet_address_get_is_site_local + +GInetAddressClass +GInetAddressPrivate +G_INET_ADDRESS +G_INET_ADDRESS_CLASS +G_INET_ADDRESS_GET_CLASS +G_IS_INET_ADDRESS +G_IS_INET_ADDRESS_CLASS +G_TYPE_INET_ADDRESS + +g_inet_address_get_type +
+
+gsocketaddress +GSocketAddress +GSocketAddress +GSocketFamily +g_socket_address_new_from_native +g_socket_address_get_family +g_socket_address_to_native +g_socket_address_get_native_size + +GSocketAddressClass +G_IS_SOCKET_ADDRESS +G_IS_SOCKET_ADDRESS_CLASS +G_SOCKET_ADDRESS +G_SOCKET_ADDRESS_CLASS +G_SOCKET_ADDRESS_GET_CLASS +G_TYPE_SOCKET_ADDRESS + +g_socket_address_get_type +
+ +
+ginetsocketaddress +GInetSocketAddress +GInetSocketAddress +g_inet_socket_address_new +g_inet_socket_address_get_address +g_inet_socket_address_get_port + +GInetSocketAddressClass +GInetSocketAddressPrivate +G_INET_SOCKET_ADDRESS +G_INET_SOCKET_ADDRESS_CLASS +G_INET_SOCKET_ADDRESS_GET_CLASS +G_IS_INET_SOCKET_ADDRESS +G_IS_INET_SOCKET_ADDRESS_CLASS +G_TYPE_INET_SOCKET_ADDRESS + +g_inet_socket_address_get_type +
+ +
+gunixsocketaddress +GUnixSocketAddress +GUnixSocketAddress +g_unix_socket_address_new + +GUnixSocketAddressClass +GUnixSocketAddressPrivate +G_IS_UNIX_SOCKET_ADDRESS +G_IS_UNIX_SOCKET_ADDRESS_CLASS +G_TYPE_UNIX_SOCKET_ADDRESS +G_UNIX_SOCKET_ADDRESS +G_UNIX_SOCKET_ADDRESS_CLASS +G_UNIX_SOCKET_ADDRESS_GET_CLASS + +g_unix_socket_address_get_type +
diff --git a/docs/reference/gio/gio.types b/docs/reference/gio/gio.types index c73282ac9..cedae876a 100644 --- a/docs/reference/gio/gio.types +++ b/docs/reference/gio/gio.types @@ -36,6 +36,8 @@ g_file_type_get_type g_filter_input_stream_get_type g_filter_output_stream_get_type g_icon_get_type +g_inet_address_get_type +g_inet_socket_address_get_type g_input_stream_get_type g_io_error_enum_get_type g_io_module_get_type @@ -55,10 +57,12 @@ g_output_stream_splice_flags_get_type g_password_save_get_type g_seekable_get_type g_simple_async_result_get_type +g_socket_address_get_type g_themed_icon_get_type g_unix_input_stream_get_type g_unix_mount_monitor_get_type g_unix_output_stream_get_type +g_unix_socket_address_get_type g_vfs_get_type g_volume_get_type g_volume_monitor_get_type diff --git a/gio/Makefile.am b/gio/Makefile.am index be6568f8b..53b30c2a6 100644 --- a/gio/Makefile.am +++ b/gio/Makefile.am @@ -132,6 +132,7 @@ unix_sources = \ gunixmount.h \ gunixmounts.c \ gunixmounts.h \ + gunixsocketaddress.c \ gunixvolume.c \ gunixvolume.h \ gunixvolumemonitor.c \ @@ -147,12 +148,13 @@ giounixinclude_HEADERS = \ gunixmounts.h \ gunixinputstream.h \ gunixoutputstream.h \ + gunixsocketaddress.h \ $(NULL) endif if OS_WIN32 appinfo_sources += gwin32appinfo.c gwin32appinfo.h -platform_libadd += -lshlwapi +platform_libadd += -lshlwapi -lws2_32 win32_sources = \ gwin32mount.c \ gwin32mount.h \ @@ -196,6 +198,8 @@ libgio_2_0_la_SOURCES = \ gfilterinputstream.c \ gfilteroutputstream.c \ gicon.c \ + ginetaddress.c \ + ginetsocketaddress.c \ ginputstream.c \ gioenums.h \ gioerror.c \ @@ -209,11 +213,13 @@ libgio_2_0_la_SOURCES = \ gmountoperation.c \ gnativevolumemonitor.c \ gnativevolumemonitor.h \ + gnetworkingprivate.h \ goutputstream.c \ gpollfilemonitor.c \ gpollfilemonitor.h \ gseekable.c \ gsimpleasyncresult.c \ + gsocketaddress.c \ gthemedicon.c \ gunionvolumemonitor.c \ gunionvolumemonitor.h \ @@ -299,6 +305,8 @@ gio_headers = \ gfilterinputstream.h \ gfilteroutputstream.h \ gicon.h \ + ginetaddress.h \ + ginetsocketaddress.h \ ginputstream.h \ gio.h \ giotypes.h \ @@ -315,6 +323,7 @@ gio_headers = \ goutputstream.h \ gseekable.h \ gsimpleasyncresult.h \ + gsocketaddress.h \ gthemedicon.h \ gvfs.h \ gvolume.h \ diff --git a/gio/ginetaddress.c b/gio/ginetaddress.c new file mode 100644 index 000000000..cc5856bff --- /dev/null +++ b/gio/ginetaddress.c @@ -0,0 +1,747 @@ +/* GIO - GLib Input, Output and Streaming Library + * + * Copyright (C) 2008 Christian Kellner, Samuel Cormier-Iijima + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General + * Public License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place, Suite 330, + * Boston, MA 02111-1307, USA. + * + * Authors: Christian Kellner + * Samuel Cormier-Iijima + */ + +#include +#include + +#include "ginetaddress.h" +#include "gioenums.h" +#include "gioenumtypes.h" +#include "glibintl.h" +#include "gnetworkingprivate.h" + +#include "gioalias.h" + +/** + * SECTION:ginetaddress + * @short_description: An IPv4/IPv6 address + * + * #GInetAddress represents an IPv4 or IPv6 internet address. + * + * To actually connect to a remote host, you will need a + * #GInetSocketAddress (which includes a #GInetAddress as well as a + * port number). + **/ + +/** + * GInetAddress: + * + * An IPv4 or IPv6 internet address. + **/ + +/* Networking initialization function, called from inside the g_once of + * g_inet_address_get_type() + */ +static void +_g_networking_init (void) +{ +#ifdef G_OS_WIN32 + WSADATA wsadata; + if (WSAStartup (MAKEWORD (2, 0), &wsadata) != 0) + g_error ("Windows Sockets could not be initialized"); +#endif +} + +G_DEFINE_TYPE_WITH_CODE (GInetAddress, g_inet_address, G_TYPE_OBJECT, + _g_networking_init ();) + +struct _GInetAddressPrivate +{ + GSocketFamily family; + union { + struct in_addr ipv4; + struct in6_addr ipv6; + } addr; +}; + +enum +{ + PROP_0, + PROP_FAMILY, + PROP_BYTES, + PROP_IS_ANY, + PROP_IS_LOOPBACK, + PROP_IS_LINK_LOCAL, + PROP_IS_SITE_LOCAL, + PROP_IS_MULTICAST, + PROP_IS_MC_GLOBAL, + PROP_IS_MC_LINK_LOCAL, + PROP_IS_MC_NODE_LOCAL, + PROP_IS_MC_ORG_LOCAL, + PROP_IS_MC_SITE_LOCAL, +}; + +static void +g_inet_address_set_property (GObject *object, + guint prop_id, + const GValue *value, + GParamSpec *pspec) +{ + GInetAddress *address = G_INET_ADDRESS (object); + + switch (prop_id) + { + case PROP_FAMILY: + address->priv->family = g_value_get_enum (value); + break; + + case PROP_BYTES: + memcpy (&address->priv->addr, g_value_get_pointer (value), + address->priv->family == AF_INET ? + sizeof (address->priv->addr.ipv4) : + sizeof (address->priv->addr.ipv6)); + break; + + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); + break; + } + +} + +static void +g_inet_address_get_property (GObject *object, + guint prop_id, + GValue *value, + GParamSpec *pspec) +{ + GInetAddress *address = G_INET_ADDRESS (object); + + switch (prop_id) + { + case PROP_FAMILY: + g_value_set_enum (value, address->priv->family); + break; + + case PROP_BYTES: + g_value_set_pointer (value, &address->priv->addr); + break; + + case PROP_IS_ANY: + g_value_set_boolean (value, g_inet_address_get_is_any (address)); + break; + + case PROP_IS_LOOPBACK: + g_value_set_boolean (value, g_inet_address_get_is_loopback (address)); + break; + + case PROP_IS_LINK_LOCAL: + g_value_set_boolean (value, g_inet_address_get_is_link_local (address)); + break; + + case PROP_IS_SITE_LOCAL: + g_value_set_boolean (value, g_inet_address_get_is_site_local (address)); + break; + + case PROP_IS_MULTICAST: + g_value_set_boolean (value, g_inet_address_get_is_multicast (address)); + break; + + case PROP_IS_MC_GLOBAL: + g_value_set_boolean (value, g_inet_address_get_is_mc_global (address)); + break; + + case PROP_IS_MC_LINK_LOCAL: + g_value_set_boolean (value, g_inet_address_get_is_mc_link_local (address)); + break; + + case PROP_IS_MC_NODE_LOCAL: + g_value_set_boolean (value, g_inet_address_get_is_mc_node_local (address)); + break; + + case PROP_IS_MC_ORG_LOCAL: + g_value_set_boolean (value, g_inet_address_get_is_mc_org_local (address)); + break; + + case PROP_IS_MC_SITE_LOCAL: + g_value_set_boolean (value, g_inet_address_get_is_mc_site_local (address)); + break; + + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); + } +} + +static void +g_inet_address_class_init (GInetAddressClass *klass) +{ + GObjectClass *gobject_class = G_OBJECT_CLASS (klass); + + g_type_class_add_private (klass, sizeof (GInetAddressPrivate)); + + gobject_class->set_property = g_inet_address_set_property; + gobject_class->get_property = g_inet_address_get_property; + + g_object_class_install_property (gobject_class, PROP_FAMILY, + g_param_spec_enum ("family", + _("Address family"), + _("The address family (IPv4 or IPv6)"), + G_TYPE_SOCKET_FAMILY, + G_SOCKET_FAMILY_INVALID, + G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NAME)); + + g_object_class_install_property (gobject_class, PROP_BYTES, + g_param_spec_pointer ("bytes", + _("Bytes"), + _("The raw address data"), + G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NAME)); + + g_object_class_install_property (gobject_class, PROP_IS_ANY, + g_param_spec_boolean ("is-any", + _("Is any"), + _("See g_inet_address_get_is_any()"), + FALSE, + G_PARAM_READABLE | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NAME)); + + g_object_class_install_property (gobject_class, PROP_IS_LINK_LOCAL, + g_param_spec_boolean ("is-link-local", + _("Is link-local"), + _("See g_inet_address_get_is_link_local()"), + FALSE, + G_PARAM_READABLE | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NAME)); + + g_object_class_install_property (gobject_class, PROP_IS_LOOPBACK, + g_param_spec_boolean ("is-loopback", + _("Is loopback"), + _("See g_inet_address_get_is_loopback()"), + FALSE, + G_PARAM_READABLE | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NAME)); + + g_object_class_install_property (gobject_class, PROP_IS_SITE_LOCAL, + g_param_spec_boolean ("is-site-local", + _("Is site-local"), + _("See g_inet_address_get_is_site_local()"), + FALSE, + G_PARAM_READABLE | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NAME)); + + g_object_class_install_property (gobject_class, PROP_IS_MULTICAST, + g_param_spec_boolean ("is-multicast", + _("Is multicast"), + _("See g_inet_address_get_is_multicast()"), + FALSE, + G_PARAM_READABLE | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NAME)); + + g_object_class_install_property (gobject_class, PROP_IS_MC_GLOBAL, + g_param_spec_boolean ("is-mc-global", + _("Is multicast global"), + _("See g_inet_address_get_is_mc_global()"), + FALSE, + G_PARAM_READABLE | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NAME)); + + g_object_class_install_property (gobject_class, PROP_IS_MC_LINK_LOCAL, + g_param_spec_boolean ("is-mc-link-local", + _("Is multicast link-local"), + _("See g_inet_address_get_is_mc_link_local()"), + FALSE, + G_PARAM_READABLE | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NAME)); + + g_object_class_install_property (gobject_class, PROP_IS_MC_NODE_LOCAL, + g_param_spec_boolean ("is-mc-node-local", + _("Is multicast node-local"), + _("See g_inet_address_get_is_mc_node_local()"), + FALSE, + G_PARAM_READABLE | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NAME)); + + g_object_class_install_property (gobject_class, PROP_IS_MC_ORG_LOCAL, + g_param_spec_boolean ("is-mc-org-local", + _("Is multicast org-local"), + _("See g_inet_address_get_is_mc_org_local()"), + FALSE, + G_PARAM_READABLE | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NAME)); + + g_object_class_install_property (gobject_class, PROP_IS_MC_SITE_LOCAL, + g_param_spec_boolean ("is-mc-site-local", + _("Is multicast site-local"), + _("See g_inet_address_get_is_mc_site_local()"), + FALSE, + G_PARAM_READABLE | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NAME)); +} + +static void +g_inet_address_init (GInetAddress *address) +{ + address->priv = G_TYPE_INSTANCE_GET_PRIVATE (address, + G_TYPE_INET_ADDRESS, + GInetAddressPrivate); +} + +/** + * g_inet_address_new_from_string: + * @string: a string representation of an IP address + * + * Parses @string as an IP address and creates a new #GInetAddress. + * + * Returns: a new #GInetAddress corresponding to @string, or %NULL if + * @string could not be parsed. + * + * Since: 2.22 + */ +GInetAddress * +g_inet_address_new_from_string (const gchar *string) +{ +#ifdef G_OS_WIN32 + struct sockaddr_storage sa; + struct sockaddr_in *sin = (struct sockaddr_in *)&sa; + struct sockaddr_in6 *sin6 = (struct sockaddr_in6 *)&sa; + gint len; +#else /* !G_OS_WIN32 */ + struct in_addr in_addr; + struct in6_addr in6_addr; +#endif + + /* Make sure _g_networking_init() has been called */ + (void) g_inet_address_get_type (); + +#ifdef G_OS_WIN32 + memset (&sa, 0, sizeof (sa)); + len = sizeof (sa); + if (WSAStringToAddress ((LPTSTR) string, AF_INET, NULL, (LPSOCKADDR) &sa, &len) == 0) + return g_inet_address_new_from_bytes ((guint8 *)&sin->sin_addr, AF_INET); + else if (WSAStringToAddress ((LPTSTR) string, AF_INET6, NULL, (LPSOCKADDR) &sa, &len) == 0) + return g_inet_address_new_from_bytes ((guint8 *)&sin6->sin6_addr, AF_INET6); + +#else /* !G_OS_WIN32 */ + + if (inet_pton (AF_INET, string, &in_addr) > 0) + return g_inet_address_new_from_bytes ((guint8 *)&in_addr, AF_INET); + else if (inet_pton (AF_INET6, string, &in6_addr) > 0) + return g_inet_address_new_from_bytes ((guint8 *)&in6_addr, AF_INET6); +#endif + + return NULL; +} + +#define G_INET_ADDRESS_FAMILY_IS_VALID(family) ((family) == AF_INET || (family) == AF_INET6) + +/** + * g_inet_address_new_from_bytes: + * @bytes: raw address data + * @family: the address family of @bytes + * + * Creates a new #GInetAddress from the given @family and @bytes. + * @bytes should be 4 bytes for %G_INET_ADDRESS_IPV4 and 16 bytes for + * %G_INET_ADDRESS_IPV6. + * + * Returns: a new #GInetAddress corresponding to @family and @bytes. + * + * Since: 2.22 + */ +GInetAddress * +g_inet_address_new_from_bytes (const guint8 *bytes, + GSocketFamily family) +{ + g_return_val_if_fail (G_INET_ADDRESS_FAMILY_IS_VALID (family), NULL); + + return g_object_new (G_TYPE_INET_ADDRESS, + "family", family, + "bytes", bytes, + NULL); +} + +/** + * g_inet_address_new_loopback: + * @family: the address family + * + * Creates a #GInetAddress for the loopback address for @family. + * + * Returns: a new #GInetAddress corresponding to the loopback address + * for @family. + * + * Since: 2.22 + */ +GInetAddress * +g_inet_address_new_loopback (GSocketFamily family) +{ + g_return_val_if_fail (G_INET_ADDRESS_FAMILY_IS_VALID (family), NULL); + + if (family == AF_INET) + { + guint8 addr[4] = {127, 0, 0, 1}; + + return g_inet_address_new_from_bytes (addr, family); + } + else + return g_inet_address_new_from_bytes (in6addr_loopback.s6_addr, family); +} + +/** + * g_inet_address_new_any: + * @family: the address family + * + * Creates a #GInetAddress for the "any" address (unassigned/"don't + * care") for @family. + * + * Returns: a new #GInetAddress corresponding to the "any" address + * for @family. + * + * Since: 2.22 + */ +GInetAddress * +g_inet_address_new_any (GSocketFamily family) +{ + g_return_val_if_fail (G_INET_ADDRESS_FAMILY_IS_VALID (family), NULL); + + if (family == AF_INET) + { + guint8 addr[4] = {0, 0, 0, 0}; + + return g_inet_address_new_from_bytes (addr, family); + } + else + return g_inet_address_new_from_bytes (in6addr_any.s6_addr, family); +} + + +/** + * g_inet_address_to_string: + * @address: a #GInetAddress + * + * Converts @address to string form. + * + * Returns: a representation of @address as a string, which should be + * freed after use. + * + * Since: 2.22 + */ +gchar * +g_inet_address_to_string (GInetAddress *address) +{ + gchar buffer[INET6_ADDRSTRLEN]; +#ifdef G_OS_WIN32 + DWORD buflen = sizeof (buffer), addrlen; + struct sockaddr_storage sa; + struct sockaddr_in *sin = (struct sockaddr_in *)&sa; + struct sockaddr_in6 *sin6 = (struct sockaddr_in6 *)&sa; +#endif + + g_return_val_if_fail (G_IS_INET_ADDRESS (address), NULL); + +#ifdef G_OS_WIN32 + sa.ss_family = address->priv->family; + if (address->priv->family == AF_INET) + { + addrlen = sizeof (*sin); + memcpy (&sin->sin_addr, &address->priv->addr.ipv4, + sizeof (sin->sin_addr)); + sin->sin_port = 0; + } + else + { + addrlen = sizeof (*sin6); + memcpy (&sin6->sin6_addr, &address->priv->addr.ipv6, + sizeof (sin6->sin6_addr)); + sin6->sin6_port = 0; + } + if (WSAAddressToString ((LPSOCKADDR) &sa, addrlen, NULL, buffer, &buflen) != 0) + return NULL; + +#else /* !G_OS_WIN32 */ + + if (address->priv->family == AF_INET) + inet_ntop (AF_INET, &address->priv->addr.ipv4, buffer, sizeof (buffer)); + else + inet_ntop (AF_INET6, &address->priv->addr.ipv6, buffer, sizeof (buffer)); +#endif + + return g_strdup (buffer); +} + +/** + * g_inet_address_to_bytes: + * @address: a #GInetAddress + * + * Gets the raw binary address data from @address. + * + * Returns: a pointer to an internal array of the bytes in @address, + * which should not be modified, stored, or freed. + * + * Since: 2.22 + */ +const guint8 * +g_inet_address_to_bytes (GInetAddress *address) +{ + g_return_val_if_fail (G_IS_INET_ADDRESS (address), NULL); + + return (guint8 *)&address->priv->addr; +} + +/** + * g_inet_address_get_family: + * @address: a #GInetAddress + * + * Gets @address's family + * + * Returns: @address's family + * + * Since: 2.22 + */ +GSocketFamily +g_inet_address_get_family (GInetAddress *address) +{ + g_return_val_if_fail (G_IS_INET_ADDRESS (address), FALSE); + + return address->priv->family; +} + +/** + * g_inet_address_get_is_any: + * @address: a #GInetAddress + * + * Tests whether @address is the "any" address for its family. + * + * Returns: %TRUE if @address is the "any" address for its family. + * + * Since: 2.22 + */ +gboolean +g_inet_address_get_is_any (GInetAddress *address) +{ + g_return_val_if_fail (G_IS_INET_ADDRESS (address), FALSE); + + if (address->priv->family == AF_INET) + { + guint32 addr4 = g_ntohl (address->priv->addr.ipv4.s_addr); + + return addr4 == INADDR_ANY; + } + else + return IN6_IS_ADDR_UNSPECIFIED (&address->priv->addr.ipv6.s6_addr); +} + +/** + * g_inet_address_get_is_loopback: + * @address: a #GInetAddress + * + * Tests whether @address is the loopback address for its family. + * + * Returns: %TRUE if @address is the loopback address for its family. + * + * Since: 2.22 + */ +gboolean +g_inet_address_get_is_loopback (GInetAddress *address) +{ + g_return_val_if_fail (G_IS_INET_ADDRESS (address), FALSE); + + if (address->priv->family == AF_INET) + { + guint32 addr4 = g_ntohl (address->priv->addr.ipv4.s_addr); + + /* 127.0.0.0/8 */ + return ((addr4 & 0xff000000) == 0x7f000000); + } + else + return IN6_IS_ADDR_LOOPBACK (&address->priv->addr.ipv6.s6_addr); +} + +/** + * g_inet_address_get_is_link_local: + * @address: a #GInetAddress + * + * Tests whether @address is a link-local address (that is, if it + * identifies a host on a local network that is not connected to the + * Internet). + * + * Returns: %TRUE if @address is a link-local address. + * + * Since: 2.22 + */ +gboolean +g_inet_address_get_is_link_local (GInetAddress *address) +{ + g_return_val_if_fail (G_IS_INET_ADDRESS (address), FALSE); + + if (address->priv->family == AF_INET) + { + guint32 addr4 = g_ntohl (address->priv->addr.ipv4.s_addr); + + /* 169.254.0.0/16 */ + return ((addr4 & 0xffff0000) == 0xa9fe0000); + } + else + return IN6_IS_ADDR_LINKLOCAL (&address->priv->addr.ipv6.s6_addr); +} + +/** + * g_inet_address_get_is_site_local: + * @address: a #GInetAddress + * + * Tests whether @address is a site-local address such as 10.0.0.1 + * (that is, the address identifies a host on a local network that can + * not be reached directly from the Internet, but which may have + * outgoing Internet connectivity via a NAT or firewall). + * + * Returns: %TRUE if @address is a site-local address. + * + * Since: 2.22 + */ +gboolean +g_inet_address_get_is_site_local (GInetAddress *address) +{ + g_return_val_if_fail (G_IS_INET_ADDRESS (address), FALSE); + + if (address->priv->family == AF_INET) + { + guint32 addr4 = g_ntohl (address->priv->addr.ipv4.s_addr); + + /* 10.0.0.0/8, 172.16.0.0/12, 192.168.0.0/16 */ + return ((addr4 & 0xff000000) == 0x0a000000 || + (addr4 & 0xfff00000) == 0xac100000 || + (addr4 & 0xffff0000) == 0xc0a80000); + } + else + return IN6_IS_ADDR_SITELOCAL (&address->priv->addr.ipv6.s6_addr); +} + +/** + * g_inet_address_get_is_multicast: + * @address: a #GInetAddress + * + * Tests whether @address is a multicast address. + * + * Returns: %TRUE if @address is a multicast address. + * + * Since: 2.22 + */ +gboolean +g_inet_address_get_is_multicast (GInetAddress *address) +{ + g_return_val_if_fail (G_IS_INET_ADDRESS (address), FALSE); + + if (address->priv->family == AF_INET) + { + guint32 addr4 = g_ntohl (address->priv->addr.ipv4.s_addr); + + return IN_MULTICAST (addr4); + } + else + return IN6_IS_ADDR_MULTICAST (&address->priv->addr.ipv6.s6_addr); +} + +/** + * g_inet_address_get_is_mc_global: + * @address: a #GInetAddress + * + * Tests whether @address is a global multicast address. + * + * Returns: %TRUE if @address is a global multicast address. + * + * Since: 2.22 + */ +gboolean +g_inet_address_get_is_mc_global (GInetAddress *address) +{ + g_return_val_if_fail (G_IS_INET_ADDRESS (address), FALSE); + + if (address->priv->family == AF_INET) + return FALSE; + else + return IN6_IS_ADDR_MC_GLOBAL (&address->priv->addr.ipv6.s6_addr); +} + +/** + * g_inet_address_get_is_mc_link_local: + * @address: a #GInetAddress + * + * Tests whether @address is a link-local multicast address. + * + * Returns: %TRUE if @address is a link-local multicast address. + * + * Since: 2.22 + */ +gboolean +g_inet_address_get_is_mc_link_local (GInetAddress *address) +{ + g_return_val_if_fail (G_IS_INET_ADDRESS (address), FALSE); + + if (address->priv->family == AF_INET) + return FALSE; + else + return IN6_IS_ADDR_MC_LINKLOCAL (&address->priv->addr.ipv6.s6_addr); +} + +/** + * g_inet_address_get_is_mc_node_local: + * @address: a #GInetAddress + * + * Tests whether @address is a node-local multicast address. + * + * Returns: %TRUE if @address is a node-local multicast address. + * + * Since: 2.22 + */ +gboolean +g_inet_address_get_is_mc_node_local (GInetAddress *address) +{ + g_return_val_if_fail (G_IS_INET_ADDRESS (address), FALSE); + + if (address->priv->family == AF_INET) + return FALSE; + else + return IN6_IS_ADDR_MC_NODELOCAL (&address->priv->addr.ipv6.s6_addr); +} + +/** + * g_inet_address_get_is_mc_org_local: + * @address: a #GInetAddress + * + * Tests whether @address is an organization-local multicast address. + * + * Returns: %TRUE if @address is an organization-local multicast address. + * + * Since: 2.22 + */ +gboolean +g_inet_address_get_is_mc_org_local (GInetAddress *address) +{ + g_return_val_if_fail (G_IS_INET_ADDRESS (address), FALSE); + + if (address->priv->family == AF_INET) + return FALSE; + else + return IN6_IS_ADDR_MC_ORGLOCAL (&address->priv->addr.ipv6.s6_addr); +} + +/** + * g_inet_address_get_is_mc_site_local: + * @address: a #GInetAddress + * + * Tests whether @address is a site-local multicast address. + * + * Returns: %TRUE if @address is a site-local multicast address. + * + * Since: 2.22 + */ +gboolean +g_inet_address_get_is_mc_site_local (GInetAddress *address) +{ + g_return_val_if_fail (G_IS_INET_ADDRESS (address), FALSE); + + if (address->priv->family == AF_INET) + return FALSE; + else + return IN6_IS_ADDR_MC_SITELOCAL (&address->priv->addr.ipv6.s6_addr); +} + +#define __G_INET_ADDRESS_C__ +#include "gioaliasdef.c" diff --git a/gio/ginetaddress.h b/gio/ginetaddress.h new file mode 100644 index 000000000..3f9e4997e --- /dev/null +++ b/gio/ginetaddress.h @@ -0,0 +1,101 @@ +/* GIO - GLib Input, Output and Streaming Library + * + * Copyright (C) 2008 Christian Kellner, Samuel Cormier-Iijima + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General + * Public License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place, Suite 330, + * Boston, MA 02111-1307, USA. + * + * Authors: Christian Kellner + * Samuel Cormier-Iijima + */ + +#if !defined (__GIO_GIO_H_INSIDE__) && !defined (GIO_COMPILATION) +#error "Only can be included directly." +#endif + +#ifndef __G_INET_ADDRESS_H__ +#define __G_INET_ADDRESS_H__ + +#include + +G_BEGIN_DECLS + +#define G_TYPE_INET_ADDRESS (g_inet_address_get_type ()) +#define G_INET_ADDRESS(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), G_TYPE_INET_ADDRESS, GInetAddress)) +#define G_INET_ADDRESS_CLASS(k) (G_TYPE_CHECK_CLASS_CAST((k), G_TYPE_INET_ADDRESS, GInetAddressClass)) +#define G_IS_INET_ADDRESS(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), G_TYPE_INET_ADDRESS)) +#define G_IS_INET_ADDRESS_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), G_TYPE_INET_ADDRESS)) +#define G_INET_ADDRESS_GET_CLASS(o) (G_TYPE_INSTANCE_GET_CLASS ((o), G_TYPE_INET_ADDRESS, GInetAddressClass)) + +typedef struct _GInetAddressClass GInetAddressClass; +typedef struct _GInetAddressPrivate GInetAddressPrivate; + +struct _GInetAddress +{ + GObject parent_instance; + + /*< private >*/ + GInetAddressPrivate *priv; +}; + +struct _GInetAddressClass +{ + GObjectClass parent_class; + + gchar * (*to_string) (GInetAddress *address); + const guint8 * (*to_bytes) (GInetAddress *address); +}; + +GType g_inet_address_get_type (void) G_GNUC_CONST; + +GInetAddress * g_inet_address_new_from_string (const gchar *string); + +GInetAddress * g_inet_address_new_from_bytes (const guint8 *bytes, + GSocketFamily family); + +GInetAddress * g_inet_address_new_loopback (GSocketFamily family); + +GInetAddress * g_inet_address_new_any (GSocketFamily family); + +gchar * g_inet_address_to_string (GInetAddress *address); + +const guint8 * g_inet_address_to_bytes (GInetAddress *address); + +GSocketFamily g_inet_address_get_family (GInetAddress *address); + +gboolean g_inet_address_get_is_any (GInetAddress *address); + +gboolean g_inet_address_get_is_loopback (GInetAddress *address); + +gboolean g_inet_address_get_is_link_local (GInetAddress *address); + +gboolean g_inet_address_get_is_site_local (GInetAddress *address); + +gboolean g_inet_address_get_is_multicast (GInetAddress *address); + +gboolean g_inet_address_get_is_mc_global (GInetAddress *address); + +gboolean g_inet_address_get_is_mc_link_local (GInetAddress *address); + +gboolean g_inet_address_get_is_mc_node_local (GInetAddress *address); + +gboolean g_inet_address_get_is_mc_org_local (GInetAddress *address); + +gboolean g_inet_address_get_is_mc_site_local (GInetAddress *address); + +G_END_DECLS + +#endif /* __G_INET_ADDRESS_H__ */ + diff --git a/gio/ginetsocketaddress.c b/gio/ginetsocketaddress.c new file mode 100644 index 000000000..b8275a8d4 --- /dev/null +++ b/gio/ginetsocketaddress.c @@ -0,0 +1,306 @@ +/* GIO - GLib Input, Output and Streaming Library + * + * Copyright (C) 2008 Christian Kellner, Samuel Cormier-Iijima + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General + * Public License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place, Suite 330, + * Boston, MA 02111-1307, USA. + * + * Authors: Christian Kellner + * Samuel Cormier-Iijima + */ + +#include +#include +#include + +#include "ginetsocketaddress.h" +#include "ginetaddress.h" +#include "gnetworkingprivate.h" + +#include "gioalias.h" + +/** + * SECTION:ginetsocketaddress + * @short_description: Internet socket addresses + * + * An IPv4 or IPv6 socket address; that is, the combination of a + * #GInetAddress and a port number. + **/ + +/** + * GInetSocketAddress: + * + * An IPv4 or IPv6 socket address, corresponding to a struct + * sockaddr_in or struct sockaddr_in6. + **/ +G_DEFINE_TYPE (GInetSocketAddress, g_inet_socket_address, G_TYPE_SOCKET_ADDRESS); + +enum { + PROP_0, + PROP_ADDRESS, + PROP_PORT +}; + +struct _GInetSocketAddressPrivate +{ + GInetAddress *address; + guint16 port; +}; + +static void +g_inet_socket_address_finalize (GObject *object) +{ + GInetSocketAddress *address G_GNUC_UNUSED = G_INET_SOCKET_ADDRESS (object); + + if (G_OBJECT_CLASS (g_inet_socket_address_parent_class)->finalize) + (*G_OBJECT_CLASS (g_inet_socket_address_parent_class)->finalize) (object); +} + +static void +g_inet_socket_address_dispose (GObject *object) +{ + GInetSocketAddress *address G_GNUC_UNUSED = G_INET_SOCKET_ADDRESS (object); + + g_object_unref (address->priv->address); + + if (G_OBJECT_CLASS (g_inet_socket_address_parent_class)->dispose) + (*G_OBJECT_CLASS (g_inet_socket_address_parent_class)->dispose) (object); +} + +static void +g_inet_socket_address_get_property (GObject *object, + guint prop_id, + GValue *value, + GParamSpec *pspec) +{ + GInetSocketAddress *address = G_INET_SOCKET_ADDRESS (object); + + switch (prop_id) + { + case PROP_ADDRESS: + g_value_set_object (value, address->priv->address); + break; + + case PROP_PORT: + g_value_set_uint (value, address->priv->port); + break; + + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); + } +} + +static void +g_inet_socket_address_set_property (GObject *object, + guint prop_id, + const GValue *value, + GParamSpec *pspec) +{ + GInetSocketAddress *address = G_INET_SOCKET_ADDRESS (object); + + switch (prop_id) + { + case PROP_ADDRESS: + address->priv->address = g_object_ref (g_value_get_object (value)); + break; + + case PROP_PORT: + address->priv->port = (guint16) g_value_get_uint (value); + break; + + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); + } +} + +static GSocketFamily +g_inet_socket_address_get_family (GSocketAddress *address) +{ + GInetSocketAddress *addr; + + g_return_val_if_fail (G_IS_INET_SOCKET_ADDRESS (address), 0); + + addr = G_INET_SOCKET_ADDRESS (address); + + return g_inet_address_get_family (addr->priv->address); +} + +static gssize +g_inet_socket_address_get_native_size (GSocketAddress *address) +{ + GInetSocketAddress *addr; + GSocketFamily family; + + g_return_val_if_fail (G_IS_INET_SOCKET_ADDRESS (address), 0); + + addr = G_INET_SOCKET_ADDRESS (address); + family = g_inet_address_get_family (addr->priv->address); + + if (family == AF_INET) + return sizeof (struct sockaddr_in); + else if (family == AF_INET6) + return sizeof (struct sockaddr_in6); + else + return -1; +} + +static gboolean +g_inet_socket_address_to_native (GSocketAddress *address, + gpointer dest, + gsize destlen) +{ + GInetSocketAddress *addr; + GSocketFamily family; + + g_return_val_if_fail (G_IS_INET_SOCKET_ADDRESS (address), 0); + + addr = G_INET_SOCKET_ADDRESS (address); + family = g_inet_address_get_family (addr->priv->address); + + if (family == AF_INET) + { + struct sockaddr_in *sock = (struct sockaddr_in *) dest; + + if (destlen < sizeof (*sock)) + return FALSE; + + sock->sin_family = AF_INET; + sock->sin_port = g_htons (addr->priv->port); + memcpy (&(sock->sin_addr.s_addr), g_inet_address_to_bytes (addr->priv->address), sizeof (sock->sin_addr)); + memset (sock->sin_zero, 0, sizeof (sock->sin_zero)); + return TRUE; + } + else if (family == AF_INET6) + { + struct sockaddr_in6 *sock = (struct sockaddr_in6 *) dest; + + if (destlen < sizeof (*sock)) + return FALSE; + + memset (sock, 0, sizeof (sock)); + sock->sin6_family = AF_INET6; + sock->sin6_port = g_htons (addr->priv->port); + memcpy (&(sock->sin6_addr.s6_addr), g_inet_address_to_bytes (addr->priv->address), sizeof (sock->sin6_addr)); + return TRUE; + } + else + return FALSE; +} + +static void +g_inet_socket_address_class_init (GInetSocketAddressClass *klass) +{ + GObjectClass *gobject_class = G_OBJECT_CLASS (klass); + GSocketAddressClass *gsocketaddress_class = G_SOCKET_ADDRESS_CLASS (klass); + + g_type_class_add_private (klass, sizeof (GInetSocketAddressPrivate)); + + gobject_class->finalize = g_inet_socket_address_finalize; + gobject_class->dispose = g_inet_socket_address_dispose; + gobject_class->set_property = g_inet_socket_address_set_property; + gobject_class->get_property = g_inet_socket_address_get_property; + + gsocketaddress_class->get_family = g_inet_socket_address_get_family; + gsocketaddress_class->to_native = g_inet_socket_address_to_native; + gsocketaddress_class->get_native_size = g_inet_socket_address_get_native_size; + + g_object_class_install_property (gobject_class, PROP_ADDRESS, + g_param_spec_object ("address", + "address", + "address", + G_TYPE_INET_ADDRESS, + G_PARAM_CONSTRUCT_ONLY | G_PARAM_READWRITE | G_PARAM_STATIC_NAME | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NICK)); + + g_object_class_install_property (gobject_class, PROP_PORT, + g_param_spec_uint ("port", + "port", + "port", + 0, + 65535, + 0, + G_PARAM_CONSTRUCT_ONLY | G_PARAM_READWRITE | G_PARAM_STATIC_NAME | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NICK)); +} + +static void +g_inet_socket_address_init (GInetSocketAddress *address) +{ + address->priv = G_TYPE_INSTANCE_GET_PRIVATE (address, + G_TYPE_INET_SOCKET_ADDRESS, + GInetSocketAddressPrivate); + + address->priv->address = NULL; + address->priv->port = 0; +} + +/** + * g_inet_socket_address_new: + * @address: a #GInetAddress + * @port: a port number + * + * Creates a new #GInetSocketAddress for @address and @port. + * + * Returns: a new #GInetSocketAddress + * + * Since: 2.22 + */ +GSocketAddress * +g_inet_socket_address_new (GInetAddress *address, + guint16 port) +{ + return g_object_new (G_TYPE_INET_SOCKET_ADDRESS, + "address", address, + "port", port, + NULL); +} + +/** + * g_inet_socket_address_get_address: + * @address: a #GInetSocketAddress + * + * Gets @address's #GInetAddress. + * + * Returns: the #GInetAddress for @address, which must be + * g_object_ref()'d if it will be stored + * + * Since: 2.22 + */ +GInetAddress * +g_inet_socket_address_get_address (GInetSocketAddress *address) +{ + g_return_val_if_fail (G_IS_INET_SOCKET_ADDRESS (address), NULL); + + return address->priv->address; +} + +/** + * g_inet_socket_address_get_port: + * @address: a #GInetSocketAddress + * + * Gets @address's port. + * + * Returns: the port for @address + * + * Since: 2.22 + */ +guint16 +g_inet_socket_address_get_port (GInetSocketAddress *address) +{ + g_return_val_if_fail (G_IS_INET_SOCKET_ADDRESS (address), 0); + + return address->priv->port; +} + +#define __G_INET_SOCKET_ADDRESS_C__ +#include "gioaliasdef.c" diff --git a/gio/ginetsocketaddress.h b/gio/ginetsocketaddress.h new file mode 100644 index 000000000..b455ac57d --- /dev/null +++ b/gio/ginetsocketaddress.h @@ -0,0 +1,69 @@ +/* GIO - GLib Input, Output and Streaming Library + * + * Copyright (C) 2008 Christian Kellner, Samuel Cormier-Iijima + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General + * Public License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place, Suite 330, + * Boston, MA 02111-1307, USA. + * + * Authors: Christian Kellner + * Samuel Cormier-Iijima + */ + +#if !defined (__GIO_GIO_H_INSIDE__) && !defined (GIO_COMPILATION) +#error "Only can be included directly." +#endif + +#ifndef __G_INET_SOCKET_ADDRESS_H__ +#define __G_INET_SOCKET_ADDRESS_H__ + +#include + +G_BEGIN_DECLS + +#define G_TYPE_INET_SOCKET_ADDRESS (g_inet_socket_address_get_type ()) +#define G_INET_SOCKET_ADDRESS(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), G_TYPE_INET_SOCKET_ADDRESS, GInetSocketAddress)) +#define G_INET_SOCKET_ADDRESS_CLASS(k) (G_TYPE_CHECK_CLASS_CAST((k), G_TYPE_INET_SOCKET_ADDRESS, GInetSocketAddressClass)) +#define G_IS_INET_SOCKET_ADDRESS(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), G_TYPE_INET_SOCKET_ADDRESS)) +#define G_IS_INET_SOCKET_ADDRESS_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), G_TYPE_INET_SOCKET_ADDRESS)) +#define G_INET_SOCKET_ADDRESS_GET_CLASS(o) (G_TYPE_INSTANCE_GET_CLASS ((o), G_TYPE_INET_SOCKET_ADDRESS, GInetSocketAddressClass)) + +typedef struct _GInetSocketAddressClass GInetSocketAddressClass; +typedef struct _GInetSocketAddressPrivate GInetSocketAddressPrivate; + +struct _GInetSocketAddress +{ + GSocketAddress parent_instance; + + /*< private >*/ + GInetSocketAddressPrivate *priv; +}; + +struct _GInetSocketAddressClass +{ + GSocketAddressClass parent_class; +}; + +GType g_inet_socket_address_get_type (void) G_GNUC_CONST; + +GSocketAddress *g_inet_socket_address_new (GInetAddress *address, + guint16 port); + +GInetAddress * g_inet_socket_address_get_address (GInetSocketAddress *address); + +guint16 g_inet_socket_address_get_port (GInetSocketAddress *address); + +G_END_DECLS + +#endif /* __G_INET_SOCKET_ADDRESS_H__ */ diff --git a/gio/gio.h b/gio/gio.h index e3a0b141e..6e809bab2 100644 --- a/gio/gio.h +++ b/gio/gio.h @@ -49,6 +49,8 @@ #include #include #include +#include +#include #include #include #include @@ -64,6 +66,7 @@ #include #include #include +#include #include #include #include diff --git a/gio/gio.symbols b/gio/gio.symbols index 4dc5917c3..99ad117d1 100644 --- a/gio/gio.symbols +++ b/gio/gio.symbols @@ -833,6 +833,7 @@ g_output_stream_splice_flags_get_type G_GNUC_CONST g_ask_password_flags_get_type G_GNUC_CONST g_password_save_get_type G_GNUC_CONST g_emblem_origin_get_type G_GNUC_CONST +g_socket_family_get_type G_GNUC_CONST #endif #endif @@ -857,3 +858,53 @@ g_emblem_get_origin #endif #endif +#if IN_HEADER(__G_INET_ADDRESS_H__) +#if IN_FILE(__G_INET_ADDRESS_C__) +g_inet_address_new_from_string +g_inet_address_new_from_bytes +g_inet_address_new_any +g_inet_address_new_loopback +g_inet_address_get_family +g_inet_address_get_type G_GNUC_CONST +g_inet_address_get_is_any +g_inet_address_get_is_link_local +g_inet_address_get_is_loopback +g_inet_address_get_is_mc_global +g_inet_address_get_is_mc_link_local +g_inet_address_get_is_mc_node_local +g_inet_address_get_is_mc_org_local +g_inet_address_get_is_mc_site_local +g_inet_address_get_is_multicast +g_inet_address_get_is_site_local +g_inet_address_to_bytes +g_inet_address_to_string +#endif +#endif + +#if IN_HEADER(__G_INET_SOCKET_ADDRESS_H__) +#if IN_FILE(__G_INET_SOCKET_ADDRESS_C__) +g_inet_socket_address_get_address +g_inet_socket_address_get_port +g_inet_socket_address_get_type G_GNUC_CONST +g_inet_socket_address_new +#endif +#endif + +#if IN_HEADER(__G_UNIX_SOCKET_ADDRESS_H__) +#if IN_FILE(__G_UNIX_SOCKET_ADDRESS_C__) +#ifdef G_OS_UNIX +g_unix_socket_address_get_type G_GNUC_CONST +g_unix_socket_address_new +#endif +#endif +#endif + +#if IN_HEADER(__G_SOCKET_ADDRESS_H__) +#if IN_FILE(__G_SOCKET_ADDRESS_C__) +g_socket_address_new_from_native +g_socket_address_get_type G_GNUC_CONST +g_socket_address_get_family +g_socket_address_get_native_size +g_socket_address_to_native +#endif +#endif diff --git a/gio/gioenums.h b/gio/gioenums.h index 3bb50fff8..e6e6dfcaf 100644 --- a/gio/gioenums.h +++ b/gio/gioenums.h @@ -477,6 +477,26 @@ typedef enum { } GEmblemOrigin; +/** + * GSocketFamily: + * @G_SOCKET_FAMILY_INVALID: no address family + * @G_SOCKET_FAMILY_IPV4: the IPv4 family + * @G_SOCKET_FAMILY_IPV6: the IPv6 family + * @G_SOCKET_FAMILY_UNIX: the UNIX domain family + * + * The protocol family of a #GSocketAddress. (These values are + * identical to the system defines %AF_INET, %AF_INET6 and %AF_UNIX, + * if available.) + */ +typedef enum { + G_SOCKET_FAMILY_INVALID, +#ifdef GLIB_SYSDEF_AF_UNIX + G_SOCKET_FAMILY_UNIX = GLIB_SYSDEF_AF_UNIX, +#endif + G_SOCKET_FAMILY_IPV4 = GLIB_SYSDEF_AF_INET, + G_SOCKET_FAMILY_IPV6 = GLIB_SYSDEF_AF_INET6 +} GSocketFamily; + G_END_DECLS #endif /* __GIO_ENUMS_H__ */ diff --git a/gio/giotypes.h b/gio/giotypes.h index 981c19561..6ea1c1b0e 100644 --- a/gio/giotypes.h +++ b/gio/giotypes.h @@ -75,6 +75,8 @@ typedef struct _GFilenameCompleter GFilenameCompleter; typedef struct _GIcon GIcon; /* Dummy typedef */ +typedef struct _GInetAddress GInetAddress; +typedef struct _GInetSocketAddress GInetSocketAddress; typedef struct _GInputStream GInputStream; typedef struct _GIOModule GIOModule; typedef struct _GIOExtensionPoint GIOExtensionPoint; @@ -97,9 +99,12 @@ typedef struct _GMemoryOutputStream GMemoryOutputStream; **/ typedef struct _GMount GMount; /* Dummy typedef */ typedef struct _GMountOperation GMountOperation; +typedef struct _GNetworkAddress GNetworkAddress; +typedef struct _GNetworkService GNetworkService; typedef struct _GOutputStream GOutputStream; typedef struct _GSeekable GSeekable; typedef struct _GSimpleAsyncResult GSimpleAsyncResult; +typedef struct _GSocketAddress GSocketAddress; typedef struct _GThemedIcon GThemedIcon; typedef struct _GVfs GVfs; /* Dummy typedef */ diff --git a/gio/gnetworkingprivate.h b/gio/gnetworkingprivate.h new file mode 100644 index 000000000..a90d2645d --- /dev/null +++ b/gio/gnetworkingprivate.h @@ -0,0 +1,53 @@ +/* GIO - GLib Input, Output and Streaming Library + * + * Copyright (C) 2008 Red Hat, Inc. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General + * Public License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place, Suite 330, + * Boston, MA 02111-1307, USA. + */ + +#ifndef __G_NETWORKINGPRIVATE_H__ +#define __G_NETWORKINGPRIVATE_H__ + +#ifdef G_OS_WIN32 + +#define WINVER 0x0501 // FIXME? +#include +#undef interface +#include +#include + +#else /* !G_OS_WIN32 */ + +#define BIND_4_COMPAT + +#include +#include +/* We're supposed to define _GNU_SOURCE to get EAI_NODATA, but that + * won't actually work since has already been included at + * this point. So we define __USE_GNU instead. + */ +#define __USE_GNU +#include +#undef __USE_GNU +#include +#include +#include +#include +#include + +#endif + +#endif /* __G_NETWORKINGPRIVATE_H__ */ diff --git a/gio/gsocketaddress.c b/gio/gsocketaddress.c new file mode 100644 index 000000000..33e8ffdd4 --- /dev/null +++ b/gio/gsocketaddress.c @@ -0,0 +1,233 @@ +/* GIO - GLib Input, Output and Streaming Library + * + * Copyright (C) 2008 Christian Kellner, Samuel Cormier-Iijima + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General + * Public License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place, Suite 330, + * Boston, MA 02111-1307, USA. + * + * Authors: Christian Kellner + * Samuel Cormier-Iijima + */ + +#include +#include + +#include "gsocketaddress.h" +#include "ginetaddress.h" +#include "ginetsocketaddress.h" +#include "gnetworkingprivate.h" +#include "glibintl.h" +#include "gioenumtypes.h" + +#ifdef G_OS_UNIX +#include "gunixsocketaddress.h" +#endif + +#include "gioalias.h" + +/** + * SECTION:gsocketaddress + * @short_description: Abstract base class representing endpoints for + * socket communication + * + * #GSocketAddress is the equivalent of struct sockaddr + * in the BSD sockets API. This is an abstract class; use + * #GInetSocketAddress for internet sockets, or #GUnixSocketAddress + * for UNIX domain sockets. + **/ + +/** + * GSocketAddress: + * + * A socket endpoint address, corresponding to struct sockaddr + * or one of its subtypes. + **/ + +enum +{ + PROP_NONE, + PROP_FAMILY +}; + +G_DEFINE_ABSTRACT_TYPE (GSocketAddress, g_socket_address, G_TYPE_OBJECT); + +/** + * g_socket_address_get_family: + * @address: a #GSocketAddress + * + * Gets the socket family type of @address. + * + * Returns: the socket family type of @address. + * + * Since: 2.22 + */ +GSocketFamily +g_socket_address_get_family (GSocketAddress *address) +{ + g_return_val_if_fail (G_IS_SOCKET_ADDRESS (address), 0); + + return G_SOCKET_ADDRESS_GET_CLASS (address)->get_family (address); +} + +static void +g_socket_address_get_property (GObject *object, guint prop_id, + GValue *value, GParamSpec *pspec) +{ + GSocketAddress *address = G_SOCKET_ADDRESS (object); + + switch (prop_id) + { + case PROP_FAMILY: + g_value_set_enum (value, g_socket_address_get_family (address)); + break; + + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); + } +} + +static void +g_socket_address_class_init (GSocketAddressClass *klass) +{ + GObjectClass *gobject_class = G_OBJECT_CLASS (klass); + + gobject_class->get_property = g_socket_address_get_property; + + g_object_class_install_property (gobject_class, PROP_FAMILY, + g_param_spec_enum ("family", + _("Address family"), + _("The family of the socket address"), + G_TYPE_SOCKET_FAMILY, + G_SOCKET_FAMILY_INVALID, + G_PARAM_READABLE | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB | G_PARAM_STATIC_NAME)); +} + +static void +g_socket_address_init (GSocketAddress *address) +{ + +} + +/** + * g_socket_address_get_native_size: + * @address: a #GSocketAddress + * + * Gets the size of @address's native struct sockaddr. + * You can use this to allocate memory to pass to + * g_socket_address_to_native(). + * + * Returns: the size of the native struct sockaddr that + * @address represents + * + * Since: 2.22 + */ +gssize +g_socket_address_get_native_size (GSocketAddress *address) +{ + g_return_val_if_fail (G_IS_SOCKET_ADDRESS (address), -1); + + return G_SOCKET_ADDRESS_GET_CLASS (address)->get_native_size (address); +} + +/** + * g_socket_address_to_native: + * @address: a #GSocketAddress + * @dest: a pointer to a memory location that will contain the native + * struct sockaddr. + * @destlen: the size of @dest. Must be at least as large as + * g_socket_address_get_native_size(). + * + * Converts a #GSocketAddress to a native struct + * sockaddr, which can be passed to low-level functions like + * connect() or bind(). + * + * Returns: %TRUE if @dest was filled in, %FALSE if @address is invalid + * or @destlen is too small. + * + * Since: 2.22 + */ +gboolean +g_socket_address_to_native (GSocketAddress *address, + gpointer dest, + gsize destlen) +{ + g_return_val_if_fail (G_IS_SOCKET_ADDRESS (address), FALSE); + + return G_SOCKET_ADDRESS_GET_CLASS (address)->to_native (address, dest, destlen); +} + +/** + * g_socket_address_new_from_native: + * @native: a pointer to a struct sockaddr + * @len: the size of the memory location pointed to by @native + * + * Creates a #GSocketAddress subclass corresponding to the native + * struct sockaddr @native. + * + * Returns: a new #GSocketAddress if @native could successfully be converted, + * otherwise %NULL. + * + * Since: 2.22 + */ +GSocketAddress * +g_socket_address_new_from_native (gpointer native, + gsize len) +{ + gshort family; + + if (len < sizeof (gshort)) + return NULL; + + family = ((struct sockaddr *) native)->sa_family; + + if (family == AF_UNSPEC) + return NULL; + + if (family == AF_INET) + { + struct sockaddr_in *addr = (struct sockaddr_in *) native; + GInetAddress *iaddr = g_inet_address_new_from_bytes ((guint8 *) &(addr->sin_addr), AF_INET); + GSocketAddress *sockaddr; + + sockaddr = g_inet_socket_address_new (iaddr, g_ntohs (addr->sin_port)); + g_object_unref (iaddr); + return sockaddr; + } + + if (family == AF_INET6) + { + struct sockaddr_in6 *addr = (struct sockaddr_in6 *) native; + GInetAddress *iaddr = g_inet_address_new_from_bytes ((guint8 *) &(addr->sin6_addr), AF_INET6); + GSocketAddress *sockaddr; + + sockaddr = g_inet_socket_address_new (iaddr, g_ntohs (addr->sin6_port)); + g_object_unref (iaddr); + return sockaddr; + } + +#ifdef G_OS_UNIX + if (family == AF_UNIX) + { + struct sockaddr_un *addr = (struct sockaddr_un *) native; + + return g_unix_socket_address_new (addr->sun_path); + } +#endif + + return NULL; +} + +#define __G_SOCKET_ADDRESS_C__ +#include "gioaliasdef.c" diff --git a/gio/gsocketaddress.h b/gio/gsocketaddress.h new file mode 100644 index 000000000..1649ba6a7 --- /dev/null +++ b/gio/gsocketaddress.h @@ -0,0 +1,77 @@ +/* GIO - GLib Input, Output and Streaming Library + * + * Copyright (C) 2008 Christian Kellner, Samuel Cormier-Iijima + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General + * Public License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place, Suite 330, + * Boston, MA 02111-1307, USA. + * + * Authors: Christian Kellner + * Samuel Cormier-Iijima + */ + +#if !defined (__GIO_GIO_H_INSIDE__) && !defined (GIO_COMPILATION) +#error "Only can be included directly." +#endif + +#ifndef __G_SOCKET_ADDRESS_H__ +#define __G_SOCKET_ADDRESS_H__ + +#include + +G_BEGIN_DECLS + +#define G_TYPE_SOCKET_ADDRESS (g_socket_address_get_type ()) +#define G_SOCKET_ADDRESS(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), G_TYPE_SOCKET_ADDRESS, GSocketAddress)) +#define G_SOCKET_ADDRESS_CLASS(k) (G_TYPE_CHECK_CLASS_CAST((k), G_TYPE_SOCKET_ADDRESS, GSocketAddressClass)) +#define G_IS_SOCKET_ADDRESS(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), G_TYPE_SOCKET_ADDRESS)) +#define G_IS_SOCKET_ADDRESS_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), G_TYPE_SOCKET_ADDRESS)) +#define G_SOCKET_ADDRESS_GET_CLASS(o) (G_TYPE_INSTANCE_GET_CLASS ((o), G_TYPE_SOCKET_ADDRESS, GSocketAddressClass)) + +typedef struct _GSocketAddressClass GSocketAddressClass; + +struct _GSocketAddress +{ + GObject parent_instance; +}; + +struct _GSocketAddressClass +{ + GObjectClass parent_class; + + GSocketFamily (*get_family) (GSocketAddress *address); + + gssize (*get_native_size) (GSocketAddress *address); + + gboolean (*to_native) (GSocketAddress *address, + gpointer dest, + gsize destlen); +}; + +GType g_socket_address_get_type (void) G_GNUC_CONST; + +GSocketFamily g_socket_address_get_family (GSocketAddress *address); + +GSocketAddress * g_socket_address_new_from_native (gpointer native, + gsize len); + +gboolean g_socket_address_to_native (GSocketAddress *address, + gpointer dest, + gsize destlen); + +gssize g_socket_address_get_native_size (GSocketAddress *address); + +G_END_DECLS + +#endif /* __G_SOCKET_ADDRESS_H__ */ diff --git a/gio/gunixsocketaddress.c b/gio/gunixsocketaddress.c new file mode 100644 index 000000000..0b1b7e352 --- /dev/null +++ b/gio/gunixsocketaddress.c @@ -0,0 +1,206 @@ +/* GIO - GLib Input, Output and Streaming Library + * + * Copyright (C) 2008 Christian Kellner, Samuel Cormier-Iijima + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General + * Public License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place, Suite 330, + * Boston, MA 02111-1307, USA. + * + * Authors: Christian Kellner + * Samuel Cormier-Iijima + */ + +#include +#include +#include + +#include "gunixsocketaddress.h" +#include "glibintl.h" +#include "gnetworkingprivate.h" + +#include "gioalias.h" + +/** + * SECTION:gunixsocketaddress + * @short_description: Unix socket addresses + * + * Support for UNIX-domain (aka local) sockets. + **/ + +/** + * GUnixSocketAddress: + * + * A UNIX-domain (local) socket address, corresponding to a + * struct sockaddr_un. + **/ +G_DEFINE_TYPE (GUnixSocketAddress, g_unix_socket_address, G_TYPE_SOCKET_ADDRESS); + +enum +{ + PROP_0, + PROP_PATH, +}; + +struct _GUnixSocketAddressPrivate +{ + char *path; +}; + +static void +g_unix_socket_address_finalize (GObject *object) +{ + GUnixSocketAddress *address G_GNUC_UNUSED = G_UNIX_SOCKET_ADDRESS (object); + + g_free (address->priv->path); + + if (G_OBJECT_CLASS (g_unix_socket_address_parent_class)->finalize) + (G_OBJECT_CLASS (g_unix_socket_address_parent_class)->finalize) (object); +} + +static void +g_unix_socket_address_dispose (GObject *object) +{ + GUnixSocketAddress *address G_GNUC_UNUSED = G_UNIX_SOCKET_ADDRESS (object); + + if (G_OBJECT_CLASS (g_unix_socket_address_parent_class)->dispose) + (*G_OBJECT_CLASS (g_unix_socket_address_parent_class)->dispose) (object); +} + +static void +g_unix_socket_address_get_property (GObject *object, + guint prop_id, + GValue *value, + GParamSpec *pspec) +{ + GUnixSocketAddress *address = G_UNIX_SOCKET_ADDRESS (object); + + switch (prop_id) + { + case PROP_PATH: + g_value_set_string (value, address->priv->path); + break; + + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); + } +} + +static GSocketFamily +g_unix_socket_address_get_family (GSocketAddress *address) +{ + g_assert (PF_UNIX == G_SOCKET_FAMILY_UNIX); + + return G_SOCKET_FAMILY_UNIX; +} + +static void +g_unix_socket_address_set_property (GObject *object, + guint prop_id, + const GValue *value, + GParamSpec *pspec) +{ + GUnixSocketAddress *address = G_UNIX_SOCKET_ADDRESS (object); + + switch (prop_id) + { + case PROP_PATH: + g_free (address->priv->path); + address->priv->path = g_value_dup_string (value); + break; + + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); + } +} + +static gssize +g_unix_socket_address_get_native_size (GSocketAddress *address) +{ + return sizeof (struct sockaddr_un); +} + +static gboolean +g_unix_socket_address_to_native (GSocketAddress *address, + gpointer dest, + gsize destlen) +{ + GUnixSocketAddress *addr = G_UNIX_SOCKET_ADDRESS (address); + struct sockaddr_un *sock; + + if (destlen < sizeof (*sock)) + return FALSE; + + sock = (struct sockaddr_un *) dest; + sock->sun_family = AF_UNIX; + g_strlcpy (sock->sun_path, addr->priv->path, sizeof (sock->sun_path)); + + return TRUE; +} + +static void +g_unix_socket_address_class_init (GUnixSocketAddressClass *klass) +{ + GObjectClass *gobject_class = G_OBJECT_CLASS (klass); + GSocketAddressClass *gsocketaddress_class = G_SOCKET_ADDRESS_CLASS (klass); + + g_type_class_add_private (klass, sizeof (GUnixSocketAddressPrivate)); + + gobject_class->finalize = g_unix_socket_address_finalize; + gobject_class->dispose = g_unix_socket_address_dispose; + gobject_class->set_property = g_unix_socket_address_set_property; + gobject_class->get_property = g_unix_socket_address_get_property; + + gsocketaddress_class->get_family = g_unix_socket_address_get_family; + gsocketaddress_class->to_native = g_unix_socket_address_to_native; + gsocketaddress_class->get_native_size = g_unix_socket_address_get_native_size; + + g_object_class_install_property (gobject_class, + PROP_PATH, + g_param_spec_string ("path", + _("Path"), + _("UNIX socket path"), + NULL, + G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY | G_PARAM_STATIC_NICK | G_PARAM_STATIC_BLURB)); +} + +static void +g_unix_socket_address_init (GUnixSocketAddress *address) +{ + address->priv = G_TYPE_INSTANCE_GET_PRIVATE (address, + G_TYPE_UNIX_SOCKET_ADDRESS, + GUnixSocketAddressPrivate); + + address->priv->path = NULL; +} + +/** + * g_unix_socket_address_new: + * @path: the socket path + * + * Creates a new #GUnixSocketAddress for @path. + * + * Returns: a new #GUnixSocketAddress + * + * Since: 2.22 + */ +GSocketAddress * +g_unix_socket_address_new (const gchar *path) +{ + return g_object_new (G_TYPE_UNIX_SOCKET_ADDRESS, + "path", path, + NULL); +} + +#define __G_UNIX_SOCKET_ADDRESS_C__ +#include "gioaliasdef.c" diff --git a/gio/gunixsocketaddress.h b/gio/gunixsocketaddress.h new file mode 100644 index 000000000..527937f9a --- /dev/null +++ b/gio/gunixsocketaddress.h @@ -0,0 +1,61 @@ +/* GIO - GLib Input, Output and Streaming Library + * + * Copyright (C) 2008 Christian Kellner, Samuel Cormier-Iijima + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General + * Public License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place, Suite 330, + * Boston, MA 02111-1307, USA. + * + * Authors: Christian Kellner + * Samuel Cormier-Iijima + */ + +#ifndef __G_UNIX_SOCKET_ADDRESS_H__ +#define __G_UNIX_SOCKET_ADDRESS_H__ + +#include + +G_BEGIN_DECLS + +#define G_TYPE_UNIX_SOCKET_ADDRESS (g_unix_socket_address_get_type ()) +#define G_UNIX_SOCKET_ADDRESS(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), G_TYPE_UNIX_SOCKET_ADDRESS, GUnixSocketAddress)) +#define G_UNIX_SOCKET_ADDRESS_CLASS(k) (G_TYPE_CHECK_CLASS_CAST((k), G_TYPE_UNIX_SOCKET_ADDRESS, GUnixSocketAddressClass)) +#define G_IS_UNIX_SOCKET_ADDRESS(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), G_TYPE_UNIX_SOCKET_ADDRESS)) +#define G_IS_UNIX_SOCKET_ADDRESS_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), G_TYPE_UNIX_SOCKET_ADDRESS)) +#define G_UNIX_SOCKET_ADDRESS_GET_CLASS(o) (G_TYPE_INSTANCE_GET_CLASS ((o), G_TYPE_UNIX_SOCKET_ADDRESS, GUnixSocketAddressClass)) + +typedef struct _GUnixSocketAddress GUnixSocketAddress; +typedef struct _GUnixSocketAddressClass GUnixSocketAddressClass; +typedef struct _GUnixSocketAddressPrivate GUnixSocketAddressPrivate; + +struct _GUnixSocketAddress +{ + GSocketAddress parent_instance; + + /*< private >*/ + GUnixSocketAddressPrivate *priv; +}; + +struct _GUnixSocketAddressClass +{ + GSocketAddressClass parent_class; +}; + +GType g_unix_socket_address_get_type (void) G_GNUC_CONST; + +GSocketAddress *g_unix_socket_address_new (const gchar *path); + +G_END_DECLS + +#endif /* __G_UNIX_SOCKET_ADDRESS_H__ */ diff --git a/glibconfig.h.win32.in b/glibconfig.h.win32.in index 92e89640f..f10fa3251 100644 --- a/glibconfig.h.win32.in +++ b/glibconfig.h.win32.in @@ -250,6 +250,9 @@ union _GSystemThread */ typedef void * GPid; +#define GLIB_SYSDEF_AF_INET 2 +#define GLIB_SYSDEF_AF_INET6 23 + G_END_DECLS #endif /* GLIBCONFIG_H */