mirror of
https://github.com/samba-team/samba.git
synced 2025-01-08 21:18:16 +03:00
ctdb-common: Add functions for local IP address checking
This is a wrapper around getifaddrs(2), which is in libreplace, so should always be available. Some users want to set net.ipv4.ip_nonlocal_bind = 1. So, CTDB needs a way of testing if public IPs are present, without using bind(2). Doing all of this unconditionally in ctdb_sys_have_ip() will be inefficient in the recovery daemon's local IP verification if there are a lot of IP addresses. Split it this way so the interface information can be retrieved once and used multiple times. This doesn't appear to need IP canonicalisation for IPv4-mapped IPv6 addresses. Signed-off-by: Martin Schwenke <mschwenke@ddn.com> Reviewed-by: John Mulligan <jmulligan@redhat.com> Reviewed-by: Anoop C S <anoopcs@samba.org>
This commit is contained in:
parent
aab763d659
commit
cc99d0047d
@ -56,10 +56,13 @@
|
|||||||
#define ETHERTYPE_IP6 0x86dd
|
#define ETHERTYPE_IP6 0x86dd
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#include <talloc.h>
|
||||||
|
|
||||||
#include "lib/util/debug.h"
|
#include "lib/util/debug.h"
|
||||||
#include "lib/util/blocking.h"
|
#include "lib/util/blocking.h"
|
||||||
|
|
||||||
#include "protocol/protocol.h"
|
#include "protocol/protocol.h"
|
||||||
|
#include "protocol/protocol_util.h"
|
||||||
|
|
||||||
#include "common/logging.h"
|
#include "common/logging.h"
|
||||||
#include "common/system_socket.h"
|
#include "common/system_socket.h"
|
||||||
@ -84,6 +87,79 @@ static uint32_t uint16_checksum(uint8_t *data, size_t n)
|
|||||||
return sum;
|
return sum;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
struct ctdb_sys_local_ips_context {
|
||||||
|
struct ifaddrs *ifa;
|
||||||
|
};
|
||||||
|
|
||||||
|
static int ctdb_sys_local_ips_destructor(
|
||||||
|
struct ctdb_sys_local_ips_context *ips_ctx)
|
||||||
|
{
|
||||||
|
freeifaddrs(ips_ctx->ifa);
|
||||||
|
ips_ctx->ifa = NULL;
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int ctdb_sys_local_ips_init(TALLOC_CTX *ctx,
|
||||||
|
struct ctdb_sys_local_ips_context **ips_ctx)
|
||||||
|
{
|
||||||
|
struct ctdb_sys_local_ips_context *t = NULL;
|
||||||
|
int ret = 0;
|
||||||
|
|
||||||
|
t = talloc(ctx, struct ctdb_sys_local_ips_context);
|
||||||
|
if (t == NULL) {
|
||||||
|
return ENOMEM;
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = getifaddrs(&t->ifa);
|
||||||
|
if (ret != 0) {
|
||||||
|
ret = errno;
|
||||||
|
talloc_free(t);
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
talloc_set_destructor(t, ctdb_sys_local_ips_destructor);
|
||||||
|
*ips_ctx = t;
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool ctdb_sys_local_ip_check(const struct ctdb_sys_local_ips_context *ips_ctx,
|
||||||
|
const ctdb_sock_addr *addr)
|
||||||
|
{
|
||||||
|
struct ifaddrs *ifa = NULL;
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
for (ifa = ips_ctx->ifa; ifa != NULL; ifa = ifa->ifa_next) {
|
||||||
|
ctdb_sock_addr sock_addr;
|
||||||
|
bool match;
|
||||||
|
|
||||||
|
if (ifa->ifa_addr == NULL)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
/* Ignore non-IPv4/IPv6 interfaces */
|
||||||
|
switch (ifa->ifa_addr->sa_family) {
|
||||||
|
case AF_INET:
|
||||||
|
case AF_INET6:
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = ctdb_sock_addr_from_sockaddr(ifa->ifa_addr, &sock_addr);
|
||||||
|
if (ret != 0) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
match = ctdb_sock_addr_same_ip(&sock_addr, addr);
|
||||||
|
if (match) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* See if the given IP is currently on an interface
|
* See if the given IP is currently on an interface
|
||||||
*/
|
*/
|
||||||
|
@ -20,8 +20,16 @@
|
|||||||
#ifndef __CTDB_SYSTEM_SOCKET_H__
|
#ifndef __CTDB_SYSTEM_SOCKET_H__
|
||||||
#define __CTDB_SYSTEM_SOCKET_H__
|
#define __CTDB_SYSTEM_SOCKET_H__
|
||||||
|
|
||||||
|
#include <talloc.h>
|
||||||
|
|
||||||
#include "protocol/protocol.h"
|
#include "protocol/protocol.h"
|
||||||
|
|
||||||
|
struct ctdb_sys_local_ips_context;
|
||||||
|
|
||||||
|
int ctdb_sys_local_ips_init(TALLOC_CTX *ctx,
|
||||||
|
struct ctdb_sys_local_ips_context **ips_ctx);
|
||||||
|
bool ctdb_sys_local_ip_check(const struct ctdb_sys_local_ips_context *ips_ctx,
|
||||||
|
const ctdb_sock_addr *addr);
|
||||||
bool ctdb_sys_have_ip(ctdb_sock_addr *addr);
|
bool ctdb_sys_have_ip(ctdb_sock_addr *addr);
|
||||||
|
|
||||||
int ctdb_sys_send_arp(const ctdb_sock_addr *addr, const char *iface);
|
int ctdb_sys_send_arp(const ctdb_sock_addr *addr, const char *iface);
|
||||||
|
10
ctdb/wscript
10
ctdb/wscript
@ -415,7 +415,15 @@ def build(bld):
|
|||||||
bld.SAMBA_SUBSYSTEM('ctdb-system',
|
bld.SAMBA_SUBSYSTEM('ctdb-system',
|
||||||
source=bld.SUBDIR('common',
|
source=bld.SUBDIR('common',
|
||||||
'system_socket.c system.c'),
|
'system_socket.c system.c'),
|
||||||
deps='replace talloc tevent tdb pcap samba-util')
|
deps='''ctdb-protocol
|
||||||
|
ctdb-protocol-util
|
||||||
|
pcap
|
||||||
|
replace
|
||||||
|
samba-util
|
||||||
|
talloc
|
||||||
|
tdb
|
||||||
|
tevent
|
||||||
|
''')
|
||||||
|
|
||||||
bld.SAMBA_SUBSYSTEM('ctdb-common',
|
bld.SAMBA_SUBSYSTEM('ctdb-common',
|
||||||
source=bld.SUBDIR('common',
|
source=bld.SUBDIR('common',
|
||||||
|
Loading…
Reference in New Issue
Block a user