# Network filter driver generic impl APIs
NWFILTER_PARAM_CONF_SOURCES = \
conf/nwfilter_params.c conf/nwfilter_params.h \
+ conf/nwfilter_ipaddrmap.c \
+ conf/nwfilter_ipaddrmap.h \
conf/nwfilter_conf.h
-NWFILTER_CONF_SOURCES = \
+NWFILTER_CONF_SOURCES = \
$(NWFILTER_PARAM_CONF_SOURCES) \
conf/nwfilter_conf.c conf/nwfilter_conf.h
--- /dev/null
+/*
+ * nwfilter_ipaddrmap.c: IP address map for mapping interfaces to their
+ * detected/expected IP addresses
+ *
+ * Copyright (C) 2010, 2012 IBM Corp.
+ *
+ * Author:
+ * Stefan Berger <stefanb@linux.vnet.ibm.com>
+ *
+ * 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.1 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
+ */
+
+#include <config.h>
+
+#include "internal.h"
+
+#include "virterror_internal.h"
+#include "datatypes.h"
+#include "nwfilter_params.h"
+#include "nwfilter_ipaddrmap.h"
+
+#define VIR_FROM_THIS VIR_FROM_NWFILTER
+
+static virMutex ipAddressMapLock;
+static virNWFilterHashTablePtr ipAddressMap;
+
+
+/* Add an IP address to the list of IP addresses an interface is
+ * known to use. This function feeds the per-interface cache that
+ * is used to instantiate filters with variable '$IP'.
+ *
+ * @ifname: The name of the (tap) interface
+ * @addr: An IPv4 address in dotted decimal format that the (tap)
+ * interface is known to use.
+ *
+ * This function returns 0 on success, -1 otherwise
+ */
+int
+virNWFilterIPAddrMapAddIPAddr(const char *ifname, char *addr)
+{
+ int ret = -1;
+ virNWFilterVarValuePtr val;
+
+ virMutexLock(&ipAddressMapLock);
+
+ val = virHashLookup(ipAddressMap->hashTable, ifname);
+ if (!val) {
+ val = virNWFilterVarValueCreateSimple(addr);
+ if (!val) {
+ virReportOOMError();
+ goto cleanup;
+ }
+ ret = virNWFilterHashTablePut(ipAddressMap, ifname, val, 1);
+ goto cleanup;
+ } else {
+ if (virNWFilterVarValueAddValue(val, addr) < 0)
+ goto cleanup;
+ }
+
+ ret = 0;
+
+cleanup:
+ virMutexUnlock(&ipAddressMapLock);
+
+ return ret;
+}
+
+/* Delete all or a specific IP address from an interface. After this
+ * call either all or the given IP address will not be associated
+ * with the interface anymore.
+ *
+ * @ifname: The name of the (tap) interface
+ * @addr: An IPv4 address in dotted decimal format that the (tap)
+ * interface is not using anymore; provide NULL to remove all IP
+ * addresses associated with the given interface
+ *
+ * This function returns the number of IP addresses that are still
+ * known to be associated with this interface, in case of an error
+ * -1 is returned. Error conditions are:
+ * - IP addresses is not known to be associated with the interface
+ */
+int
+virNWFilterIPAddrMapDelIPAddr(const char *ifname, const char *ipaddr)
+{
+ int ret = -1;
+ virNWFilterVarValuePtr val = NULL;
+
+ virMutexLock(&ipAddressMapLock);
+
+ if (ipaddr != NULL) {
+ val = virHashLookup(ipAddressMap->hashTable, ifname);
+ if (val) {
+ if (virNWFilterVarValueGetCardinality(val) == 1 &&
+ STREQ(ipaddr,
+ virNWFilterVarValueGetNthValue(val, 0)))
+ goto remove_entry;
+ virNWFilterVarValueDelValue(val, ipaddr);
+ ret = virNWFilterVarValueGetCardinality(val);
+ }
+ } else {
+remove_entry:
+ /* remove whole entry */
+ val = virNWFilterHashTableRemoveEntry(ipAddressMap, ifname);
+ virNWFilterVarValueFree(val);
+ ret = 0;
+ }
+
+ virMutexUnlock(&ipAddressMapLock);
+
+ return ret;
+}
+
+/* Get the list of IP addresses known to be in use by an interface
+ *
+ * This function returns NULL in case no IP address is known to be
+ * associated with the interface, a virNWFilterVarValuePtr otherwise
+ * that then can contain one or multiple entries.
+ */
+virNWFilterVarValuePtr
+virNWFilterIPAddrMapGetIPAddr(const char *ifname)
+{
+ virNWFilterVarValuePtr res;
+
+ virMutexLock(&ipAddressMapLock);
+
+ res = virHashLookup(ipAddressMap->hashTable, ifname);
+
+ virMutexUnlock(&ipAddressMapLock);
+
+ return res;
+}
+
+int
+virNWFilterIPAddrMapInit(void)
+{
+ ipAddressMap = virNWFilterHashTableCreate(0);
+ if (!ipAddressMap) {
+ virReportOOMError();
+ return -1;
+ }
+
+ if (virMutexInit(&ipAddressMapLock) < 0) {
+ virNWFilterIPAddrMapShutdown();
+ return -1;
+ }
+
+ return 0;
+}
+
+void
+virNWFilterIPAddrMapShutdown(void)
+{
+ virNWFilterHashTableFree(ipAddressMap);
+ ipAddressMap = NULL;
+}
--- /dev/null
+/*
+ * nwfilter_ipaddrmap.h: IP address map for mapping interfaces to their
+ * detected/expected IP addresses
+ *
+ * Copyright (C) 2010, 2012 IBM Corp.
+ *
+ * Author:
+ * Stefan Berger <stefanb@linux.vnet.ibm.com>
+ *
+ * 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.1 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 __VIR_NWFILTER_IPADDRMAP_H
+# define __VIR_NWFILTER_IPADDRMAP_H
+
+int virNWFilterIPAddrMapInit(void);
+void virNWFilterIPAddrMapShutdown(void);
+
+int virNWFilterIPAddrMapAddIPAddr(const char *ifname, char *addr);
+int virNWFilterIPAddrMapDelIPAddr(const char *ifname,
+ const char *ipaddr);
+virNWFilterVarValuePtr virNWFilterIPAddrMapGetIPAddr(const char *ifname);
+
+#endif /* __VIR_NWFILTER_IPADDRMAP_H */
virNWFilterUnlockFilterUpdates;
+# nwfilter_ipaddrmap
+virNWFilterIPAddrMapAddIPAddr;
+virNWFilterIPAddrMapDelIPAddr;
+virNWFilterIPAddrMapGetIPAddr;
+virNWFilterIPAddrMapInit;
+virNWFilterIPAddrMapShutdown;
+
+
# nwfilter_params.h
virNWFilterHashTableCreate;
virNWFilterHashTableFree;
#include "nwfilter_gentech_driver.h"
#include "configmake.h"
+#include "nwfilter_ipaddrmap.h"
#include "nwfilter_dhcpsnoop.h"
#include "nwfilter_learnipaddr.h"
nwfilterDriverStartup(int privileged) {
char *base = NULL;
- if (virNWFilterDHCPSnoopInit() < 0)
+ if (virNWFilterIPAddrMapInit() < 0)
return -1;
if (virNWFilterLearnInit() < 0)
- return -1;
+ goto err_exit_ipaddrmapshutdown;
+ if (virNWFilterDHCPSnoopInit() < 0)
+ goto err_exit_learnshutdown;
virNWFilterTechDriversInit(privileged);
conf_init_err:
virNWFilterTechDriversShutdown();
virNWFilterDHCPSnoopShutdown();
+err_exit_learnshutdown:
virNWFilterLearnShutdown();
+err_exit_ipaddrmapshutdown:
+ virNWFilterIPAddrMapShutdown();
return -1;
}
virNWFilterTechDriversShutdown();
virNWFilterDHCPSnoopShutdown();
virNWFilterLearnShutdown();
+ virNWFilterIPAddrMapShutdown();
nwfilterDriverLock(driverState);
#include "nwfilter_gentech_driver.h"
#include "nwfilter_ebiptables_driver.h"
#include "nwfilter_dhcpsnoop.h"
+#include "nwfilter_ipaddrmap.h"
#include "nwfilter_learnipaddr.h"
#include "virnetdev.h"
#include "datatypes.h"
goto err_exit;
}
- ipaddr = virNWFilterGetIpAddrForIfname(ifname);
+ ipaddr = virNWFilterIPAddrMapGetIPAddr(ifname);
vars1 = virNWFilterCreateVarHashmap(str_macaddr, ipaddr);
if (!vars1) {
techdriver->allTeardown(ifname);
- virNWFilterDelIpAddrForIfname(ifname, NULL);
+ virNWFilterIPAddrMapDelIPAddr(ifname, NULL);
virNWFilterUnlockIface(ifname);
#include "conf/domain_conf.h"
#include "nwfilter_gentech_driver.h"
#include "nwfilter_ebiptables_driver.h"
+#include "nwfilter_ipaddrmap.h"
#include "nwfilter_learnipaddr.h"
#define VIR_FROM_THIS VIR_FROM_NWFILTER
static virMutex pendingLearnReqLock;
static virHashTablePtr pendingLearnReq;
-static virMutex ipAddressMapLock;
-static virNWFilterHashTablePtr ipAddressMap;
-
static virMutex ifaceMapLock;
static virHashTablePtr ifaceLockMap;
return res;
}
-/* Add an IP address to the list of IP addresses an interface is
- * known to use. This function feeds the per-interface cache that
- * is used to instantiate filters with variable '$IP'.
- *
- * @ifname: The name of the (tap) interface
- * @addr: An IPv4 address in dotted decimal format that the (tap)
- * interface is known to use.
- *
- * This function returns 0 on success, -1 otherwise
- */
-static int
-virNWFilterAddIpAddrForIfname(const char *ifname, char *addr)
-{
- int ret = -1;
- virNWFilterVarValuePtr val;
-
- virMutexLock(&ipAddressMapLock);
-
- val = virHashLookup(ipAddressMap->hashTable, ifname);
- if (!val) {
- val = virNWFilterVarValueCreateSimple(addr);
- if (!val) {
- virReportOOMError();
- goto cleanup;
- }
- ret = virNWFilterHashTablePut(ipAddressMap, ifname, val, 1);
- goto cleanup;
- } else {
- if (virNWFilterVarValueAddValue(val, addr) < 0)
- goto cleanup;
- }
-
- ret = 0;
-
-cleanup:
- virMutexUnlock(&ipAddressMapLock);
-
- return ret;
-}
#endif
-/* Delete all or a specific IP address from an interface. After this
- * call either all or the given IP address will not be associated
- * with the interface anymore.
- *
- * @ifname: The name of the (tap) interface
- * @addr: An IPv4 address in dotted decimal format that the (tap)
- * interface is not using anymore; provide NULL to remove all IP
- * addresses associated with the given interface
- *
- * This function returns the number of IP addresses that are still
- * known to be associated with this interface, in case of an error
- * -1 is returned. Error conditions are:
- * - IP addresses is not known to be associated with the interface
- */
-int
-virNWFilterDelIpAddrForIfname(const char *ifname, const char *ipaddr)
-{
- int ret = -1;
- virNWFilterVarValuePtr val = NULL;
-
- virMutexLock(&ipAddressMapLock);
-
- if (ipaddr != NULL) {
- val = virHashLookup(ipAddressMap->hashTable, ifname);
- if (val) {
- if (virNWFilterVarValueGetCardinality(val) == 1 &&
- STREQ(ipaddr,
- virNWFilterVarValueGetNthValue(val, 0)))
- goto remove_entry;
- virNWFilterVarValueDelValue(val, ipaddr);
- ret = virNWFilterVarValueGetCardinality(val);
- }
- } else {
-remove_entry:
- /* remove whole entry */
- val = virNWFilterHashTableRemoveEntry(ipAddressMap, ifname);
- virNWFilterVarValueFree(val);
- ret = 0;
- }
-
- virMutexUnlock(&ipAddressMapLock);
-
- return ret;
-}
-
-/* Get the list of IP addresses known to be in use by an interface
- *
- * This function returns NULL in case no IP address is known to be
- * associated with the interface, a virNWFilterVarValuePtr otherwise
- * that then can contain one or multiple entries.
- */
-virNWFilterVarValuePtr
-virNWFilterGetIpAddrForIfname(const char *ifname)
-{
- virNWFilterVarValuePtr res;
-
- virMutexLock(&ipAddressMapLock);
-
- res = virHashLookup(ipAddressMap->hashTable, ifname);
-
- virMutexUnlock(&ipAddressMapLock);
-
- return res;
-}
-
-
#ifdef HAVE_LIBPCAP
static void
char *inetaddr;
if ((inetaddr = virSocketAddrFormat(&sa)) != NULL) {
- if (virNWFilterAddIpAddrForIfname(req->ifname, inetaddr) < 0) {
+ if (virNWFilterIPAddrMapAddIPAddr(req->ifname, inetaddr) < 0) {
VIR_ERROR(_("Failed to add IP address %s to IP address "
"cache for interface %s"), inetaddr, req->ifname);
}
return -1;
}
- ipAddressMap = virNWFilterHashTableCreate(0);
- if (!ipAddressMap) {
- virReportOOMError();
- virNWFilterLearnShutdown();
- return -1;
- }
-
- if (virMutexInit(&ipAddressMapLock) < 0) {
- virNWFilterLearnShutdown();
- return -1;
- }
-
ifaceLockMap = virHashCreate(0, freeIfaceLock);
if (!ifaceLockMap) {
virNWFilterLearnShutdown();
virHashFree(pendingLearnReq);
pendingLearnReq = NULL;
- virNWFilterHashTableFree(ipAddressMap);
- ipAddressMap = NULL;
-
virHashFree(ifaceLockMap);
ifaceLockMap = NULL;
}
virNWFilterIPAddrLearnReqPtr virNWFilterLookupLearnReq(int ifindex);
int virNWFilterTerminateLearnReq(const char *ifname);
-int virNWFilterDelIpAddrForIfname(const char *ifname, const char *ipaddr);
-virNWFilterVarValuePtr virNWFilterGetIpAddrForIfname(const char *ifname);
-
int virNWFilterLockIface(const char *ifname) ATTRIBUTE_RETURN_CHECK;
void virNWFilterUnlockIface(const char *ifname);