This patch ports the Test driver to use the network XML apis. Basically the 'struct _testNet' is removed, and replaced by usage of the generic virNetworkObjPtr and virNetworkDefPtr objects. The XML parser and formatters are ripped out and replaced by calls to the generic APIs in network_conf.h. Finally there is just alot of cleanup of all the individual network driver implementations to adjust to the style of the new APIs used. test.c | 477 ++++++++++++++++------------------------------------------------- 1 file changed, 121 insertions(+), 356 deletions(-) Regards, Daniel diff -r 77e5fcbd24b7 src/test.c --- a/src/test.c Sun Jun 22 17:55:31 2008 -0400 +++ b/src/test.c Sun Jun 22 17:56:04 2008 -0400 @@ -46,6 +46,7 @@ #include "uuid.h" #include "capabilities.h" #include "memory.h" +#include "network_conf.h" /* Flags that determine the action to take on a shutdown or crash of a domain */ @@ -85,26 +86,6 @@ typedef struct _testDom testDom; typedef struct _testDom *testDomPtr; -struct _testNet { - int active; - int config; - int running; - char name[20]; - char bridge[20]; - unsigned char uuid[VIR_UUID_BUFLEN]; - int forward; - char forwardDev[IF_NAMESIZE]; - char ipAddress[INET_ADDRSTRLEN]; - char ipNetmask[INET_ADDRSTRLEN]; - - char dhcpStart[INET_ADDRSTRLEN]; - char dhcpEnd[INET_ADDRSTRLEN]; - - int autostart; -}; -typedef struct _testNet testNet; -typedef struct _testNet *testNetPtr; - #define MAX_DOMAINS 20 #define MAX_NETWORKS 20 #define MAX_CPUS 128 @@ -125,8 +106,7 @@ virNodeInfo nodeInfo; int numDomains; testDom domains[MAX_DOMAINS]; - int numNetworks; - testNet networks[MAX_NETWORKS]; + virNetworkObjPtr networks; int numCells; testCell cells[MAX_CELLS]; }; @@ -161,17 +141,18 @@ privdom = &privconn->domains[domidx]; #define GET_NETWORK(net, ret) \ - int netidx; \ testConnPtr privconn; \ - testNetPtr privnet; \ + virNetworkObjPtr privnet; \ \ privconn = (testConnPtr)net->conn->privateData; \ - if ((netidx = getNetworkIndex(net)) < 0) { \ - testError((net)->conn, NULL, (net), VIR_ERR_INVALID_ARG, \ - __FUNCTION__); \ - return (ret); \ - } \ - privnet = &privconn->networks[netidx]; + do { \ + if ((privnet = virNetworkFindByName(privconn->networks, \ + (net)->name)) == NULL) { \ + testError((net)->conn, NULL, (net), VIR_ERR_INVALID_ARG, \ + __FUNCTION__); \ + return (ret); \ + } \ + } while (0) #define GET_CONNECTION(conn, ret) \ testConnPtr privconn; \ @@ -423,191 +404,54 @@ } -static int testLoadNetwork(virConnectPtr conn, - xmlDocPtr xml) { - xmlNodePtr root = NULL; - xmlXPathContextPtr ctxt = NULL; - char *name = NULL, *bridge = NULL; - unsigned char uuid[VIR_UUID_BUFLEN]; - char *str; - char *ipaddress = NULL, *ipnetmask = NULL, *dhcpstart = NULL, *dhcpend = NULL; - int forward; - char *forwardDev = NULL; - int handle = -1, i; +#define MAX_NETWORK_XML_LEN 16000 + +static virNetworkObjPtr +testLoadNetworkFromFile(virConnectPtr conn, + const char *filename) { + char *data; + virNetworkDefPtr def; GET_CONNECTION(conn, -1); - root = xmlDocGetRootElement(xml); - if ((root == NULL) || (!xmlStrEqual(root->name, BAD_CAST "network"))) { - testError(conn, NULL, NULL, VIR_ERR_XML_ERROR, _("network")); - goto error; + if (virFileReadAll(filename, MAX_NETWORK_XML_LEN, &data) < 0) { + testError(conn, NULL, NULL, VIR_ERR_INTERNAL_ERROR, _("load network definition file")); + return NULL; } - ctxt = xmlXPathNewContext(xml); - if (ctxt == NULL) { - testError(conn, NULL, NULL, VIR_ERR_INTERNAL_ERROR, _("creating xpath context")); - goto error; + if ((def = virNetworkDefParse(conn, data, filename)) == NULL) { + VIR_FREE(data); + return NULL; } + VIR_FREE(data); - name = virXPathString("string(/network/name[1])", ctxt); - if (name == NULL) { - testError(conn, NULL, NULL, VIR_ERR_INTERNAL_ERROR, _("network name")); - goto error; - } - - bridge = virXPathString("string(/network/bridge[1]/@name)", ctxt); - - str = virXPathString("string(/network/uuid[1])", ctxt); - if (str == NULL) { - testError(conn, NULL, NULL, VIR_ERR_XML_ERROR, _("network uuid")); - goto error; - } - if (virUUIDParse(str, uuid) < 0) { - testError(conn, NULL, NULL, VIR_ERR_XML_ERROR, _("network uuid")); - goto error; - } - VIR_FREE(str); - - - forward = virXPathBoolean("count(/network/forward) != 0", ctxt); - if (forward < 0) { - testError(conn, NULL, NULL, VIR_ERR_XML_ERROR, _("network forward")); - goto error; - } - - forwardDev = virXPathString("string(/network/forward/@dev)", ctxt); - - - ipaddress = virXPathString("string(/network/ip/@address)", ctxt); - if (ipaddress == NULL) { - testError(conn, NULL, NULL, VIR_ERR_XML_ERROR, _("ip address")); - goto error; - } - ipnetmask = virXPathString("string(/network/ip/@netmask)", ctxt); - if (ipnetmask == NULL) { - testError(conn, NULL, NULL, VIR_ERR_XML_ERROR, _("ip netmask")); - goto error; - } - dhcpstart = virXPathString("string(/network/ip/dhcp/range[1]/@start)", ctxt); - if (dhcpstart == NULL) { - testError(conn, NULL, NULL, VIR_ERR_XML_ERROR, _("ip address")); - goto error; - } - dhcpend = virXPathString("string(/network/ip/dhcp/range[1]/@end)", ctxt); - if (dhcpend == NULL) { - testError(conn, NULL, NULL, VIR_ERR_XML_ERROR, _("ip address")); - goto error; - } - - for (i = 0 ; i < MAX_NETWORKS ; i++) { - if (!privconn->networks[i].active) { - handle = i; - break; - } - } - if (handle < 0) - return (-1); - - privconn->networks[handle].active = 1; - privconn->networks[handle].running = 1; - strncpy(privconn->networks[handle].name, name, sizeof(privconn->networks[handle].name)-1); - privconn->networks[handle].name[sizeof(privconn->networks[handle].name)-1] = '\0'; - strncpy(privconn->networks[handle].bridge, bridge ? bridge : name, sizeof(privconn->networks[handle].bridge)-1); - privconn->networks[handle].bridge[sizeof(privconn->networks[handle].bridge)-1] = '\0'; - VIR_FREE(name); - name = NULL; - if (bridge) { - VIR_FREE(bridge); - bridge = NULL; - } - - memmove(privconn->networks[handle].uuid, uuid, VIR_UUID_BUFLEN); - privconn->networks[handle].forward = forward; - if (forwardDev) { - strncpy(privconn->networks[handle].forwardDev, forwardDev, sizeof(privconn->networks[handle].forwardDev)-1); - privconn->networks[handle].forwardDev[sizeof(privconn->networks[handle].forwardDev)-1] = '\0'; - VIR_FREE(forwardDev); - } - - strncpy(privconn->networks[handle].ipAddress, ipaddress, sizeof(privconn->networks[handle].ipAddress)-1); - privconn->networks[handle].ipAddress[sizeof(privconn->networks[handle].ipAddress)-1] = '\0'; - VIR_FREE(ipaddress); - strncpy(privconn->networks[handle].ipNetmask, ipnetmask, sizeof(privconn->networks[handle].ipNetmask)-1); - privconn->networks[handle].ipNetmask[sizeof(privconn->networks[handle].ipNetmask)-1] = '\0'; - VIR_FREE(ipnetmask); - strncpy(privconn->networks[handle].dhcpStart, dhcpstart, sizeof(privconn->networks[handle].dhcpStart)-1); - privconn->networks[handle].dhcpStart[sizeof(privconn->networks[handle].dhcpStart)-1] = '\0'; - VIR_FREE(dhcpstart); - strncpy(privconn->networks[handle].dhcpEnd, dhcpend, sizeof(privconn->networks[handle].dhcpEnd)-1); - privconn->networks[handle].dhcpEnd[sizeof(privconn->networks[handle].dhcpEnd)-1] = '\0'; - VIR_FREE(dhcpend); - xmlXPathFreeContext(ctxt); - return (handle); - - error: - xmlXPathFreeContext(ctxt); - VIR_FREE (forwardDev); - VIR_FREE(ipaddress); - VIR_FREE(ipnetmask); - VIR_FREE(dhcpstart); - VIR_FREE(dhcpend); - VIR_FREE(name); - return (-1); + return virNetworkAssignDef(conn, &privconn->networks, + def); } -static int testLoadNetworkFromDoc(virConnectPtr conn, - const char *doc) { - int ret; - xmlDocPtr xml; - if (!(xml = xmlReadDoc(BAD_CAST doc, "network.xml", NULL, - XML_PARSE_NOENT | XML_PARSE_NONET | - XML_PARSE_NOERROR | XML_PARSE_NOWARNING))) { - testError(conn, NULL, NULL, VIR_ERR_XML_ERROR, _("network")); - return (-1); - } - - ret = testLoadNetwork(conn, xml); - - xmlFreeDoc(xml); - - return (ret); -} - - -static int testLoadNetworkFromFile(virConnectPtr conn, - const char *filename) { - int ret, fd; - xmlDocPtr xml; - - if ((fd = open(filename, O_RDONLY)) < 0) { - testError(conn, NULL, NULL, VIR_ERR_INTERNAL_ERROR, _("load network definition file")); - return (-1); - } - - if (!(xml = xmlReadFd(fd, filename, NULL, - XML_PARSE_NOENT | XML_PARSE_NONET | - XML_PARSE_NOERROR | XML_PARSE_NOWARNING))) { - testError(conn, NULL, NULL, VIR_ERR_XML_ERROR, _("network")); - return (-1); - } - - ret = testLoadNetwork(conn, xml); - - xmlFreeDoc(xml); - close(fd); - - return (ret); -} +static const char *defaultNetworkXML = +"<network>" +" <name>default</name>" +" <bridge name='virbr0' />" +" <forward/>" +" <ip address='192.168.122.1' netmask='255.255.255.0'>" +" <dhcp>" +" <range start='192.168.122.2' end='192.168.122.254' />" +" </dhcp>" +" </ip>" +"</network>"; static int testOpenDefault(virConnectPtr conn) { int u; struct timeval tv; testConnPtr privconn; + virNetworkDefPtr netdef; + virNetworkObjPtr netobj; + if (VIR_ALLOC(privconn) < 0) { testError(conn, NULL, NULL, VIR_ERR_NO_MEMORY, "testConn"); return VIR_DRV_OPEN_ERROR; } - memset(privconn, 0, sizeof(testConn)); if (gettimeofday(&tv, NULL) < 0) { testError(NULL, NULL, NULL, VIR_ERR_INTERNAL_ERROR, _("getting time of day")); @@ -636,21 +480,15 @@ privconn->domains[0].info.cpuTime = ((tv.tv_sec * 1000ll * 1000ll * 1000ll) + (tv.tv_usec * 1000ll)); - privconn->numNetworks = 1; - privconn->networks[0].active = 1; - privconn->networks[0].config = 1; - privconn->networks[0].running = 1; - strcpy(privconn->networks[0].name, "default"); - strcpy(privconn->networks[0].bridge, "default"); - for (u = 0 ; u < VIR_UUID_BUFLEN ; u++) { - privconn->networks[0].uuid[u] = (u * 75)%255; + if (!(netdef = virNetworkDefParse(conn, defaultNetworkXML, "default.xml"))) { + return VIR_DRV_OPEN_ERROR; } - privconn->networks[0].forward = 1; - strcpy(privconn->networks[0].forwardDev, "eth0"); - strcpy(privconn->networks[0].ipAddress, "192.168.122.1"); - strcpy(privconn->networks[0].ipNetmask, "255.255.255.0"); - strcpy(privconn->networks[0].dhcpStart, "192.168.122.128"); - strcpy(privconn->networks[0].dhcpEnd, "192.168.122.253"); + if (!(netobj = virNetworkAssignDef(conn, &privconn->networks, netdef))) { + virNetworkDefFree(netdef); + return VIR_DRV_OPEN_ERROR; + } + netobj->active = 1; + netobj->persistent = 1; // Numa setup privconn->numCells = 2; @@ -736,7 +574,6 @@ conn->privateData = privconn; privconn->nextDomID = 1; privconn->numDomains = 0; - privconn->numNetworks = 0; privconn->numCells = 0; strncpy(privconn->path, file, PATH_MAX-1); privconn->path[PATH_MAX-1] = '\0'; @@ -840,21 +677,20 @@ ret = virXPathNodeSet("/node/network", ctxt, &networks); if (ret > 0) { for (i = 0 ; i < ret ; i++) { + virNetworkObjPtr net; xmlChar *netFile = xmlGetProp(networks[i], BAD_CAST "file"); char *absFile = testBuildFilename(file, (const char *)netFile); - int handle; VIR_FREE(netFile); if (!absFile) { testError(NULL, NULL, NULL, VIR_ERR_INTERNAL_ERROR, _("resolving network filename")); goto error; } - if ((handle = testLoadNetworkFromFile(conn, absFile)) < 0) { + if ((net = testLoadNetworkFromFile(conn, absFile)) == NULL) { VIR_FREE(absFile); goto error; } - privconn->networks[handle].config = 1; - VIR_FREE(absFile); - privconn->numNetworks++; + net->persistent = 1; + net->configFile = absFile; } if (networks != NULL) { VIR_FREE(networks); @@ -892,17 +728,6 @@ if (STREQ(domain->name, privconn->domains[i].name)) return (i); } - } - return (-1); -} - -static int getNetworkIndex(virNetworkPtr network) { - int i; - GET_CONNECTION(network->conn, -1); - - for (i = 0 ; i < MAX_NETWORKS ; i++) { - if (STREQ(network->name, privconn->networks[i].name)) - return (i); } return (-1); } @@ -1742,160 +1567,131 @@ static virNetworkPtr testLookupNetworkByUUID(virConnectPtr conn, const unsigned char *uuid) { - int i, idx = -1; + virNetworkObjPtr net = NULL; GET_CONNECTION(conn, NULL); - for (i = 0 ; i < MAX_NETWORKS ; i++) { - if (privconn->networks[i].active && - memcmp(uuid, privconn->networks[i].uuid, VIR_UUID_BUFLEN) == 0) { - idx = i; - break; - } - } - - if (idx < 0) { + if ((net = virNetworkFindByUUID(privconn->networks, uuid)) == NULL) { testError (conn, NULL, NULL, VIR_ERR_NO_NETWORK, NULL); return NULL; } - return virGetNetwork(conn, privconn->networks[idx].name, privconn->networks[idx].uuid); + return virGetNetwork(conn, net->def->name, net->def->uuid); } static virNetworkPtr testLookupNetworkByName(virConnectPtr conn, - const char *name) + const char *name) { - int i, idx = -1; + virNetworkObjPtr net = NULL; GET_CONNECTION(conn, NULL); - for (i = 0 ; i < MAX_NETWORKS ; i++) { - if (privconn->networks[i].active && - STREQ(name, privconn->networks[i].name)) { - idx = i; - break; - } - } - - if (idx < 0) { + if ((net = virNetworkFindByName(privconn->networks, name)) == NULL) { testError (conn, NULL, NULL, VIR_ERR_NO_NETWORK, NULL); return NULL; } - return virGetNetwork(conn, privconn->networks[idx].name, privconn->networks[idx].uuid); + return virGetNetwork(conn, net->def->name, net->def->uuid); } static int testNumNetworks(virConnectPtr conn) { - int numInactive = 0, i; + int numActive = 0; + virNetworkObjPtr net; GET_CONNECTION(conn, -1); - for (i = 0 ; i < MAX_NETWORKS ; i++) { - if (!privconn->networks[i].active || - !privconn->networks[i].running) - continue; - numInactive++; + net = privconn->networks; + while (net) { + if (virNetworkIsActive(net)) + numActive++; + net = net->next; } - return (numInactive); + return numActive; } static int testListNetworks(virConnectPtr conn, char **const names, int nnames) { - int n = 0, i; + int n = 0; + virNetworkObjPtr net; GET_CONNECTION(conn, -1); - for (i = 0, n = 0 ; i < MAX_NETWORKS && n < nnames ; i++) { - if (privconn->networks[i].active && - privconn->networks[i].running) { - names[n++] = strdup(privconn->networks[i].name); - } + net = privconn->networks; + while (net && n < nnames) { + if (virNetworkIsActive(net)) + names[n++] = strdup(net->def->name); + net = net->next; } - return (n); + return n; } static int testNumDefinedNetworks(virConnectPtr conn) { - int numInactive = 0, i; + int numInactive = 0; + virNetworkObjPtr net; GET_CONNECTION(conn, -1); - for (i = 0 ; i < MAX_NETWORKS ; i++) { - if (!privconn->networks[i].active || - privconn->networks[i].running) - continue; - numInactive++; + net = privconn->networks; + while (net) { + if (!virNetworkIsActive(net)) + numInactive++; + net = net->next; } - return (numInactive); + return numInactive; } static int testListDefinedNetworks(virConnectPtr conn, char **const names, int nnames) { - int n = 0, i; + int n = 0; + virNetworkObjPtr net; GET_CONNECTION(conn, -1); - for (i = 0, n = 0 ; i < MAX_NETWORKS && n < nnames ; i++) { - if (privconn->networks[i].active && - !privconn->networks[i].running) { - names[n++] = strdup(privconn->networks[i].name); - } + net = privconn->networks; + while (net && n < nnames) { + if (!virNetworkIsActive(net)) + names[n++] = strdup(net->def->name); + net = net->next; } - return (n); + return n; } static virNetworkPtr testNetworkCreate(virConnectPtr conn, const char *xml) { - int handle = -1; - virNetworkPtr net; + virNetworkDefPtr def; + virNetworkObjPtr net; GET_CONNECTION(conn, NULL); - if (xml == NULL) { - testError(conn, NULL, NULL, VIR_ERR_INVALID_ARG, __FUNCTION__); - return (NULL); - } + if ((def = virNetworkDefParse(conn, xml, NULL)) == NULL) + return NULL; - if (privconn->numNetworks == MAX_NETWORKS) { - testError(conn, NULL, NULL, VIR_ERR_INTERNAL_ERROR, _("too many networks")); - return (NULL); - } + if ((net = virNetworkAssignDef(conn, &privconn->networks, + def)) == NULL) + return NULL; + net->active = 1; - if ((handle = testLoadNetworkFromDoc(conn, xml)) < 0) - return (NULL); - privconn->networks[handle].config = 0; - - net = virGetNetwork(conn, privconn->networks[handle].name, privconn->networks[handle].uuid); - if (net == NULL) return NULL; - privconn->numNetworks++; - return (net); + return virGetNetwork(conn, def->name, def->uuid); } static virNetworkPtr testNetworkDefine(virConnectPtr conn, const char *xml) { - int handle = -1; - virNetworkPtr net; + virNetworkDefPtr def; + virNetworkObjPtr net; GET_CONNECTION(conn, NULL); - if (xml == NULL) { - testError(conn, NULL, NULL, VIR_ERR_INVALID_ARG, __FUNCTION__); - return (NULL); - } + if ((def = virNetworkDefParse(conn, xml, NULL)) == NULL) + return NULL; - if (privconn->numNetworks == MAX_NETWORKS) { - testError(conn, NULL, NULL, VIR_ERR_INTERNAL_ERROR, _("too many networks")); - return (NULL); - } + if ((net = virNetworkAssignDef(conn, &privconn->networks, + def)) == NULL) + return NULL; + net->persistent = 1; - if ((handle = testLoadNetworkFromDoc(conn, xml)) < 0) - return (NULL); - - net = virGetNetwork(conn, privconn->networks[handle].name, privconn->networks[handle].uuid); - privconn->networks[handle].config = 1; - if (net == NULL) return NULL; - privconn->numNetworks++; - return (net); + return virGetNetwork(conn, def->name, def->uuid); } static int testNetworkUndefine(virNetworkPtr network) { GET_NETWORK(network, -1); - if (privnet->running) { + if (virNetworkIsActive(privnet)) { testError(network->conn, NULL, network, VIR_ERR_INTERNAL_ERROR, _("Network is still running")); return (-1); } - privnet->active = 0; + virNetworkRemoveInactive(&privconn->networks, + privnet); return (0); } @@ -1903,13 +1699,13 @@ static int testNetworkStart(virNetworkPtr network) { GET_NETWORK(network, -1); - if (privnet->running) { + if (virNetworkIsActive(privnet)) { testError(network->conn, NULL, network, VIR_ERR_INTERNAL_ERROR, _("Network is already running")); return (-1); } - privnet->running = 1; + privnet->active = 1; return (0); } @@ -1917,55 +1713,24 @@ static int testNetworkDestroy(virNetworkPtr network) { GET_NETWORK(network, -1); - if (privnet->config) { - privnet->running = 0; - } else { - privnet->active = 0; + privnet->active = 0; + if (!privnet->persistent) { + virNetworkRemoveInactive(&privconn->networks, + privnet); } return (0); } static char *testNetworkDumpXML(virNetworkPtr network, int flags ATTRIBUTE_UNUSED) { - virBuffer buf = VIR_BUFFER_INITIALIZER; - unsigned char *uuid; - char uuidstr[VIR_UUID_STRING_BUFLEN]; GET_NETWORK(network, NULL); - virBufferAddLit(&buf, "<network>\n"); - virBufferVSprintf(&buf, " <name>%s</name>\n", network->name); - uuid = network->uuid; - virUUIDFormat(uuid, uuidstr); - virBufferVSprintf(&buf, " <uuid>%s</uuid>\n", uuidstr); - virBufferVSprintf(&buf, " <bridge name='%s'/>\n", privnet->bridge); - if (privnet->forward) { - if (privnet->forwardDev[0]) - virBufferVSprintf(&buf, " <forward dev='%s'/>\n", privnet->forwardDev); - else - virBufferAddLit(&buf, " <forward/>\n"); - } - - virBufferVSprintf(&buf, " <ip address='%s' netmask='%s'>\n", - privnet->ipAddress, privnet->ipNetmask); - virBufferAddLit(&buf, " <dhcp>\n"); - virBufferVSprintf(&buf, " <range start='%s' end='%s'/>\n", - privnet->dhcpStart, privnet->dhcpEnd); - virBufferAddLit(&buf, " </dhcp>\n"); - virBufferAddLit(&buf, " </ip>\n"); - - virBufferAddLit(&buf, "</network>\n"); - - if (virBufferError(&buf)) { - testError(network->conn, NULL, network, VIR_ERR_NO_MEMORY, __FUNCTION__); - return NULL; - } - - return virBufferContentAndReset(&buf); + return virNetworkDefFormat(network->conn, privnet->def); } static char *testNetworkGetBridgeName(virNetworkPtr network) { char *bridge; GET_NETWORK(network, NULL); - bridge = strdup(privnet->bridge); + bridge = privnet->def->bridge ? strdup(privnet->def->bridge) : NULL; if (!bridge) { testError(network->conn, NULL, network, VIR_ERR_NO_MEMORY, "network"); return NULL; -- |: Red Hat, Engineering, London -o- http://people.redhat.com/berrange/ :| |: http://libvirt.org -o- http://virt-manager.org -o- http://ovirt.org :| |: http://autobuild.org -o- http://search.cpan.org/~danberr/ :| |: GnuPG: 7D3B9505 -o- F3C9 553F A1DA 4AC2 5648 23C1 B3DF F742 7D3B 9505 :| -- Libvir-list mailing list Libvir-list@xxxxxxxxxx https://www.redhat.com/mailman/listinfo/libvir-list