2017-02-28 21:20:44 +00:00
|
|
|
/*
|
|
|
|
* virinterfaceobj.c: interface object handling
|
|
|
|
* (derived from interface_conf.c)
|
|
|
|
*
|
|
|
|
* 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, see
|
|
|
|
* <http://www.gnu.org/licenses/>.
|
|
|
|
*/
|
|
|
|
|
|
|
|
#include <config.h>
|
|
|
|
|
|
|
|
#include "datatypes.h"
|
|
|
|
#include "interface_conf.h"
|
|
|
|
|
|
|
|
#include "viralloc.h"
|
|
|
|
#include "virerror.h"
|
|
|
|
#include "virinterfaceobj.h"
|
|
|
|
#include "virlog.h"
|
|
|
|
#include "virstring.h"
|
|
|
|
|
|
|
|
#define VIR_FROM_THIS VIR_FROM_INTERFACE
|
|
|
|
|
|
|
|
VIR_LOG_INIT("conf.virinterfaceobj");
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/* virInterfaceObj manipulation */
|
|
|
|
|
2017-03-02 16:44:11 +00:00
|
|
|
void
|
|
|
|
virInterfaceObjLock(virInterfaceObjPtr obj)
|
2017-02-28 21:20:44 +00:00
|
|
|
{
|
|
|
|
virMutexLock(&obj->lock);
|
|
|
|
}
|
|
|
|
|
2017-03-02 16:44:11 +00:00
|
|
|
|
|
|
|
void
|
|
|
|
virInterfaceObjUnlock(virInterfaceObjPtr obj)
|
2017-02-28 21:20:44 +00:00
|
|
|
{
|
|
|
|
virMutexUnlock(&obj->lock);
|
|
|
|
}
|
|
|
|
|
2017-03-02 16:44:11 +00:00
|
|
|
|
|
|
|
void
|
|
|
|
virInterfaceObjFree(virInterfaceObjPtr iface)
|
2017-02-28 21:20:44 +00:00
|
|
|
{
|
|
|
|
if (!iface)
|
|
|
|
return;
|
|
|
|
|
|
|
|
virInterfaceDefFree(iface->def);
|
|
|
|
virMutexDestroy(&iface->lock);
|
|
|
|
VIR_FREE(iface);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2017-03-02 16:44:11 +00:00
|
|
|
/* virInterfaceObjList manipulation */
|
|
|
|
int
|
2017-03-02 16:56:43 +00:00
|
|
|
virInterfaceObjFindByMACString(virInterfaceObjListPtr interfaces,
|
|
|
|
const char *mac,
|
|
|
|
virInterfaceObjPtr *matches, int maxmatches)
|
2017-02-28 21:20:44 +00:00
|
|
|
{
|
|
|
|
size_t i;
|
|
|
|
unsigned int matchct = 0;
|
|
|
|
|
|
|
|
for (i = 0; i < interfaces->count; i++) {
|
|
|
|
|
|
|
|
virInterfaceObjLock(interfaces->objs[i]);
|
|
|
|
if (STRCASEEQ(interfaces->objs[i]->def->mac, mac)) {
|
|
|
|
matchct++;
|
|
|
|
if (matchct <= maxmatches) {
|
|
|
|
matches[matchct - 1] = interfaces->objs[i];
|
|
|
|
/* keep the lock if we're returning object to caller */
|
|
|
|
/* it is the caller's responsibility to unlock *all* matches */
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
virInterfaceObjUnlock(interfaces->objs[i]);
|
|
|
|
|
|
|
|
}
|
|
|
|
return matchct;
|
|
|
|
}
|
|
|
|
|
2017-03-02 16:44:11 +00:00
|
|
|
|
|
|
|
virInterfaceObjPtr
|
2017-03-02 16:56:43 +00:00
|
|
|
virInterfaceObjFindByName(virInterfaceObjListPtr interfaces,
|
|
|
|
const char *name)
|
2017-02-28 21:20:44 +00:00
|
|
|
{
|
|
|
|
size_t i;
|
|
|
|
|
|
|
|
for (i = 0; i < interfaces->count; i++) {
|
|
|
|
virInterfaceObjLock(interfaces->objs[i]);
|
|
|
|
if (STREQ(interfaces->objs[i]->def->name, name))
|
|
|
|
return interfaces->objs[i];
|
|
|
|
virInterfaceObjUnlock(interfaces->objs[i]);
|
|
|
|
}
|
|
|
|
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
|
2017-03-02 16:44:11 +00:00
|
|
|
|
|
|
|
void
|
|
|
|
virInterfaceObjListFree(virInterfaceObjListPtr interfaces)
|
2017-02-28 21:20:44 +00:00
|
|
|
{
|
|
|
|
size_t i;
|
|
|
|
|
|
|
|
for (i = 0; i < interfaces->count; i++)
|
|
|
|
virInterfaceObjFree(interfaces->objs[i]);
|
|
|
|
|
|
|
|
VIR_FREE(interfaces->objs);
|
|
|
|
interfaces->count = 0;
|
|
|
|
}
|
|
|
|
|
2017-03-02 16:44:11 +00:00
|
|
|
|
|
|
|
int
|
|
|
|
virInterfaceObjListClone(virInterfaceObjListPtr src,
|
|
|
|
virInterfaceObjListPtr dest)
|
2017-02-28 21:20:44 +00:00
|
|
|
{
|
|
|
|
int ret = -1;
|
|
|
|
size_t i;
|
|
|
|
unsigned int cnt;
|
|
|
|
|
|
|
|
if (!src || !dest)
|
|
|
|
goto cleanup;
|
|
|
|
|
|
|
|
virInterfaceObjListFree(dest); /* start with an empty list */
|
|
|
|
cnt = src->count;
|
|
|
|
for (i = 0; i < cnt; i++) {
|
|
|
|
virInterfaceDefPtr def = src->objs[i]->def;
|
|
|
|
virInterfaceDefPtr backup;
|
|
|
|
virInterfaceObjPtr iface;
|
|
|
|
char *xml = virInterfaceDefFormat(def);
|
|
|
|
|
|
|
|
if (!xml)
|
|
|
|
goto cleanup;
|
|
|
|
|
|
|
|
if ((backup = virInterfaceDefParseString(xml)) == NULL) {
|
|
|
|
VIR_FREE(xml);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
|
|
|
|
VIR_FREE(xml);
|
2017-03-02 16:56:43 +00:00
|
|
|
if ((iface = virInterfaceObjAssignDef(dest, backup)) == NULL)
|
2017-02-28 21:20:44 +00:00
|
|
|
goto cleanup;
|
2017-03-02 16:56:43 +00:00
|
|
|
virInterfaceObjUnlock(iface); /* locked by virInterfaceObjAssignDef */
|
2017-02-28 21:20:44 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
ret = cnt;
|
|
|
|
cleanup:
|
|
|
|
if ((ret < 0) && dest)
|
|
|
|
virInterfaceObjListFree(dest);
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
2017-03-02 16:44:11 +00:00
|
|
|
|
|
|
|
virInterfaceObjPtr
|
2017-03-02 16:56:43 +00:00
|
|
|
virInterfaceObjAssignDef(virInterfaceObjListPtr interfaces,
|
|
|
|
virInterfaceDefPtr def)
|
2017-02-28 21:20:44 +00:00
|
|
|
{
|
|
|
|
virInterfaceObjPtr iface;
|
|
|
|
|
2017-03-02 16:56:43 +00:00
|
|
|
if ((iface = virInterfaceObjFindByName(interfaces, def->name))) {
|
2017-02-28 21:20:44 +00:00
|
|
|
virInterfaceDefFree(iface->def);
|
|
|
|
iface->def = def;
|
|
|
|
|
|
|
|
return iface;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (VIR_ALLOC(iface) < 0)
|
|
|
|
return NULL;
|
|
|
|
if (virMutexInit(&iface->lock) < 0) {
|
|
|
|
virReportError(VIR_ERR_INTERNAL_ERROR,
|
|
|
|
"%s", _("cannot initialize mutex"));
|
|
|
|
VIR_FREE(iface);
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
virInterfaceObjLock(iface);
|
|
|
|
|
|
|
|
if (VIR_APPEND_ELEMENT_COPY(interfaces->objs,
|
|
|
|
interfaces->count, iface) < 0) {
|
|
|
|
virInterfaceObjFree(iface);
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
|
|
|
|
iface->def = def;
|
|
|
|
return iface;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
2017-03-02 16:44:11 +00:00
|
|
|
|
|
|
|
void
|
2017-03-02 16:56:43 +00:00
|
|
|
virInterfaceObjRemove(virInterfaceObjListPtr interfaces,
|
|
|
|
virInterfaceObjPtr iface)
|
2017-02-28 21:20:44 +00:00
|
|
|
{
|
|
|
|
size_t i;
|
|
|
|
|
|
|
|
virInterfaceObjUnlock(iface);
|
|
|
|
for (i = 0; i < interfaces->count; i++) {
|
|
|
|
virInterfaceObjLock(interfaces->objs[i]);
|
|
|
|
if (interfaces->objs[i] == iface) {
|
|
|
|
virInterfaceObjUnlock(interfaces->objs[i]);
|
|
|
|
virInterfaceObjFree(interfaces->objs[i]);
|
|
|
|
|
|
|
|
VIR_DELETE_ELEMENT(interfaces->objs, i, interfaces->count);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
virInterfaceObjUnlock(interfaces->objs[i]);
|
|
|
|
}
|
|
|
|
}
|