added Socket::joinMulticastGroup() and Socket::leaveMulticastGroup()
This commit is contained in:
parent
72345c7280
commit
05c2905a0a
@ -95,6 +95,8 @@ public:
|
|||||||
qse_ssize_t receive (void* buf, qse_size_t len, SocketAddress& srcaddr) QSE_CPP_NOEXCEPT;
|
qse_ssize_t receive (void* buf, qse_size_t len, SocketAddress& srcaddr) QSE_CPP_NOEXCEPT;
|
||||||
|
|
||||||
/* TODO: sendmsg, recvmsg */
|
/* TODO: sendmsg, recvmsg */
|
||||||
|
int joinMulticastGroup (const SocketAddress& mcaddr, const SocketAddress& ifaddr);
|
||||||
|
int leaveMulticastGroup (const SocketAddress& mcaddr, const SocketAddress& ifaddr);
|
||||||
|
|
||||||
// utility functions to retrieve network configuration information.
|
// utility functions to retrieve network configuration information.
|
||||||
int getIfceIndex (const qse_mchar_t* name);
|
int getIfceIndex (const qse_mchar_t* name);
|
||||||
|
@ -67,10 +67,13 @@ public:
|
|||||||
void setIpaddr (const qse_ip4ad_t* ipaddr) QSE_CPP_NOEXCEPT;
|
void setIpaddr (const qse_ip4ad_t* ipaddr) QSE_CPP_NOEXCEPT;
|
||||||
void setIpaddr (const qse_ip6ad_t* ipaddr) QSE_CPP_NOEXCEPT;
|
void setIpaddr (const qse_ip6ad_t* ipaddr) QSE_CPP_NOEXCEPT;
|
||||||
|
|
||||||
|
const qse_ip4ad_t* getIp4addr () const QSE_CPP_NOEXCEPT;
|
||||||
|
const qse_ip6ad_t* getIp6addr () const QSE_CPP_NOEXCEPT;
|
||||||
|
|
||||||
qse_uint16_t getPort() const QSE_CPP_NOEXCEPT; // in network-byte order
|
qse_uint16_t getPort() const QSE_CPP_NOEXCEPT; // in network-byte order
|
||||||
void setPort (qse_uint16_t port) QSE_CPP_NOEXCEPT; // in network-byte order
|
void setPort (qse_uint16_t port) QSE_CPP_NOEXCEPT; // in network-byte order
|
||||||
|
|
||||||
qse_uint32_t getScopeId () QSE_CPP_NOEXCEPT; // in network-byte order
|
qse_uint32_t getScopeId () const QSE_CPP_NOEXCEPT; // in network-byte order
|
||||||
void setScopeId (qse_uint32_t scope_id) QSE_CPP_NOEXCEPT; // in network-byte order
|
void setScopeId (qse_uint32_t scope_id) QSE_CPP_NOEXCEPT; // in network-byte order
|
||||||
|
|
||||||
int set (const qse_skad_t* skad) QSE_CPP_NOEXCEPT;
|
int set (const qse_skad_t* skad) QSE_CPP_NOEXCEPT;
|
||||||
|
@ -35,6 +35,7 @@
|
|||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
#include <fcntl.h>
|
#include <fcntl.h>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
|
#include <netinet/in.h>
|
||||||
|
|
||||||
#if defined(HAVE_NET_IF_H)
|
#if defined(HAVE_NET_IF_H)
|
||||||
# include <net/if.h>
|
# include <net/if.h>
|
||||||
@ -590,6 +591,88 @@ qse_ssize_t Socket::receive (void* buf, qse_size_t len, SocketAddress& srcaddr)
|
|||||||
return n;
|
return n;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int Socket::joinMulticastGroup (const SocketAddress& mcaddr, const SocketAddress& ifaddr)
|
||||||
|
{
|
||||||
|
int family = mcaddr.getFamily(); // ((struct sockaddr*)mcaddr.getAddrPtr())->sa_family
|
||||||
|
|
||||||
|
if (family != ifaddr.getFamily())
|
||||||
|
{
|
||||||
|
this->setErrorCode (E_EINVAL);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (family)
|
||||||
|
{
|
||||||
|
#if defined(AF_INET)
|
||||||
|
case AF_INET:
|
||||||
|
{
|
||||||
|
|
||||||
|
struct ip_mreq mreq;
|
||||||
|
QSE_MEMSET (&mreq, 0, QSE_SIZEOF(mreq));
|
||||||
|
|
||||||
|
mreq.imr_multiaddr = *(struct in_addr*)mcaddr.getIp4addr();
|
||||||
|
mreq.imr_interface = *(struct in_addr*)ifaddr.getIp4addr();
|
||||||
|
return ::setsockopt(this->handle, IPPROTO_IP, IP_ADD_MEMBERSHIP, &mreq, QSE_SIZEOF(mreq));
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if defined(AF_INET6)
|
||||||
|
case AF_INET6:
|
||||||
|
{
|
||||||
|
struct ipv6_mreq mreq;
|
||||||
|
QSE_MEMSET (&mreq, 0, QSE_SIZEOF(mreq));
|
||||||
|
|
||||||
|
mreq.ipv6mr_multiaddr = *(struct in6_addr*)mcaddr.getIp6addr();
|
||||||
|
mreq.ipv6mr_interface = ifaddr.getScopeId();
|
||||||
|
return ::setsockopt(this->handle, IPPROTO_IPV6, IPV6_JOIN_GROUP, &mreq, QSE_SIZEOF(mreq));
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
this->setErrorCode (E_ENOIMPL);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
int Socket::leaveMulticastGroup (const SocketAddress& mcaddr, const SocketAddress& ifaddr)
|
||||||
|
{
|
||||||
|
int family = mcaddr.getFamily(); // ((struct sockaddr*)mcaddr.getAddrPtr())->sa_family
|
||||||
|
|
||||||
|
if (family != ifaddr.getFamily())
|
||||||
|
{
|
||||||
|
this->setErrorCode (E_EINVAL);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (family)
|
||||||
|
{
|
||||||
|
#if defined(AF_INET)
|
||||||
|
case AF_INET:
|
||||||
|
{
|
||||||
|
struct ip_mreq mreq;
|
||||||
|
QSE_MEMSET (&mreq, 0, QSE_SIZEOF(mreq));
|
||||||
|
|
||||||
|
mreq.imr_multiaddr = *(struct in_addr*)mcaddr.getIp4addr();
|
||||||
|
mreq.imr_interface = *(struct in_addr*)ifaddr.getIp4addr();
|
||||||
|
return ::setsockopt(this->handle, IPPROTO_IP, IP_DROP_MEMBERSHIP, &mreq, QSE_SIZEOF(mreq));
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if defined(AF_INET6)
|
||||||
|
case AF_INET6:
|
||||||
|
{
|
||||||
|
struct ipv6_mreq mreq;
|
||||||
|
QSE_MEMSET (&mreq, 0, QSE_SIZEOF(mreq));
|
||||||
|
|
||||||
|
mreq.ipv6mr_multiaddr = *(struct in6_addr*)mcaddr.getIp6addr();
|
||||||
|
mreq.ipv6mr_interface = ifaddr.getScopeId();
|
||||||
|
return ::setsockopt(this->handle, IPPROTO_IPV6, IPV6_LEAVE_GROUP, &mreq, QSE_SIZEOF(mreq));
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
this->setErrorCode (E_ENOIMPL);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
int Socket::getIfceIndex (const qse_mchar_t* name)
|
int Socket::getIfceIndex (const qse_mchar_t* name)
|
||||||
{
|
{
|
||||||
@ -674,7 +757,7 @@ int Socket::getIfceAddress (const qse_wchar_t* name, SocketAddress* addr)
|
|||||||
|
|
||||||
int Socket::getIfceNetmask(const qse_mchar_t* name, SocketAddress* addr)
|
int Socket::getIfceNetmask(const qse_mchar_t* name, SocketAddress* addr)
|
||||||
{
|
{
|
||||||
#if defined(SIOCGIFADDR)
|
#if defined(SIOCGIFNETMASK)
|
||||||
return this->get_ifce_address(SIOCGIFNETMASK, name, false, addr);
|
return this->get_ifce_address(SIOCGIFNETMASK, name, false, addr);
|
||||||
#else
|
#else
|
||||||
this->setErrorCode (E_ENOIMPL);
|
this->setErrorCode (E_ENOIMPL);
|
||||||
@ -684,7 +767,7 @@ int Socket::getIfceNetmask(const qse_mchar_t* name, SocketAddress* addr)
|
|||||||
|
|
||||||
int Socket::getIfceNetmask (const qse_wchar_t* name, SocketAddress* addr)
|
int Socket::getIfceNetmask (const qse_wchar_t* name, SocketAddress* addr)
|
||||||
{
|
{
|
||||||
#if defined(SIOCGIFADDR)
|
#if defined(SIOCGIFNETMASK)
|
||||||
return this->get_ifce_address(SIOCGIFNETMASK, name, true, addr);
|
return this->get_ifce_address(SIOCGIFNETMASK, name, true, addr);
|
||||||
#else
|
#else
|
||||||
this->setErrorCode (E_ENOIMPL);
|
this->setErrorCode (E_ENOIMPL);
|
||||||
@ -694,7 +777,7 @@ int Socket::getIfceNetmask (const qse_wchar_t* name, SocketAddress* addr)
|
|||||||
|
|
||||||
int Socket::getIfceBroadcast(const qse_mchar_t* name, SocketAddress* addr)
|
int Socket::getIfceBroadcast(const qse_mchar_t* name, SocketAddress* addr)
|
||||||
{
|
{
|
||||||
#if defined(SIOCGIFADDR)
|
#if defined(SIOCGIFBRDADDR)
|
||||||
return this->get_ifce_address(SIOCGIFBRDADDR, name, false, addr);
|
return this->get_ifce_address(SIOCGIFBRDADDR, name, false, addr);
|
||||||
#else
|
#else
|
||||||
this->setErrorCode (E_ENOIMPL);
|
this->setErrorCode (E_ENOIMPL);
|
||||||
@ -704,7 +787,7 @@ int Socket::getIfceBroadcast(const qse_mchar_t* name, SocketAddress* addr)
|
|||||||
|
|
||||||
int Socket::getIfceBroadcast (const qse_wchar_t* name, SocketAddress* addr)
|
int Socket::getIfceBroadcast (const qse_wchar_t* name, SocketAddress* addr)
|
||||||
{
|
{
|
||||||
#if defined(SIOCGIFADDR)
|
#if defined(SIOCGIFBRDADDR)
|
||||||
return this->get_ifce_address(SIOCGIFBRDADDR, name, true, addr);
|
return this->get_ifce_address(SIOCGIFBRDADDR, name, true, addr);
|
||||||
#else
|
#else
|
||||||
this->setErrorCode (E_ENOIMPL);
|
this->setErrorCode (E_ENOIMPL);
|
||||||
|
@ -139,6 +139,30 @@ void SocketAddress::setIpaddr (const qse_ip6ad_t* ipaddr) QSE_CPP_NOEXCEPT
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const qse_ip4ad_t* SocketAddress::getIp4addr () const QSE_CPP_NOEXCEPT
|
||||||
|
{
|
||||||
|
#if defined(AF_INET)
|
||||||
|
if (FAMILY(&this->skad) == AF_INET)
|
||||||
|
{
|
||||||
|
struct sockaddr_in* v4 = (struct sockaddr_in*)&this->skad;
|
||||||
|
return (const qse_ip4ad_t*)&v4->sin_addr;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
return QSE_NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
const qse_ip6ad_t* SocketAddress::getIp6addr () const QSE_CPP_NOEXCEPT
|
||||||
|
{
|
||||||
|
#if defined(AF_INET6)
|
||||||
|
if (FAMILY(&this->skad) == AF_INET6)
|
||||||
|
{
|
||||||
|
struct sockaddr_in6* v6 = (struct sockaddr_in6*)&this->skad;
|
||||||
|
return (const qse_ip6ad_t*)&v6->sin6_addr;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
return QSE_NULL;
|
||||||
|
}
|
||||||
|
|
||||||
qse_uint16_t SocketAddress::getPort () const QSE_CPP_NOEXCEPT
|
qse_uint16_t SocketAddress::getPort () const QSE_CPP_NOEXCEPT
|
||||||
{
|
{
|
||||||
switch (FAMILY(&this->skad))
|
switch (FAMILY(&this->skad))
|
||||||
@ -187,7 +211,7 @@ void SocketAddress::setPort (qse_uint16_t port) QSE_CPP_NOEXCEPT
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
qse_uint32_t SocketAddress::getScopeId () QSE_CPP_NOEXCEPT
|
qse_uint32_t SocketAddress::getScopeId () const QSE_CPP_NOEXCEPT
|
||||||
{
|
{
|
||||||
switch (FAMILY(&this->skad))
|
switch (FAMILY(&this->skad))
|
||||||
{
|
{
|
||||||
|
Loading…
Reference in New Issue
Block a user