From c4abcad9d9608d00124f93cf7331efff0e23719a Mon Sep 17 00:00:00 2001 From: root Date: Mon, 6 Oct 2008 04:00:16 +0200 Subject: [PATCH] more updates --- handler_virt.c | 64 +++++++++++++++++++++++++++++++++++++++++++++++---- handler_virt.h | 7 +----- handler_virt_tender.c | 31 ++++++++++++++++--------- handler_virt_tender.h | 21 ++++++++++++++++- node/Makefile | 2 +- node/main.c | 13 ++++++++++- node/migrate.c | 7 +++--- node/node.h | 6 +++++ node/publish.c | 23 ++++++++++++++++-- node/xenistoobig.sh | 1 + 10 files changed, 146 insertions(+), 29 deletions(-) rewrite handler_virt_tender.h (100%) diff --git a/handler_virt.c b/handler_virt.c index 3909405..2a61bdc 100644 --- a/handler_virt.c +++ b/handler_virt.c @@ -289,6 +289,7 @@ cherokee_handler_virt_init (cherokee_handler_virt_t *hdl) else if (strcmp(this+9, "Save") == 0) hdl->action = domainSave; else if (strcmp(this+9, "Restore") == 0) hdl->action = domainRestore; + else if (strcmp(this+9, "Migrate") == 0) hdl->action = domainMigrate_args; else if (strcmp(this+9, "AttachDevice") == 0) hdl->action = domainAttachDevice_args; @@ -567,7 +568,9 @@ virt_virt_function(cherokee_handler_virt_t *hdl, virDomainPtr dom, virConnectPtr cherokee_buffer_add_va (&path, "/mnt/netapp/users/%s/%s/memory", hdl->user.buf, hdl->vm.buf); if (stat(path.buf, &statbuf) == 0) { - char *destination = create_tender(hdl, virDomainGetName(dom), virDomainGetMaxMemory(dom)); + char *destination = create_tender(HDL_CLUSTERSTATS_PROPS(hdl)->client, + HDL_CLUSTERSTATS_PROPS(hdl)->threaded_poll, + virDomainGetName(dom), virDomainGetMaxMemory(dom)); if (destination == NULL) { TRACE("virt", "Nobody wants %s, poor vm!\n", destination); @@ -581,13 +584,16 @@ virt_virt_function(cherokee_handler_virt_t *hdl, virDomainPtr dom, virConnectPtr cherokee_buffer_add_long10(buf, -1); } else { cherokee_buffer_add_va (&uri, "xen://%s/", destination); + + TRACE("virt", "We will transfer to: %s\n", uri.buf); + virConnNew = virConnectOpen (uri.buf); if (virConnNew == NULL) { TRACE("virt", "Can't connect to %s\n", uri.buf); cherokee_buffer_add_long10(buf, -1); } else { - cherokee_buffer_add_long10(buf, virDomainRestore(virConn, path.buf)); + cherokee_buffer_add_long10(buf, virDomainRestore(virConnNew, path.buf)); virConnectClose(virConn); virConn = virConnNew; /* TODO: Here I actually want virConnNew to be virConn */ @@ -608,6 +614,54 @@ virt_virt_function(cherokee_handler_virt_t *hdl, virDomainPtr dom, virConnectPtr break; } + case domainMigrate_args: { + void *destination; + ret_t ret; + + ret = cherokee_avl_get_ptr (conn->arguments, "destination", &destination); + + if (ret != ret_ok) { + destination = create_tender(HDL_CLUSTERSTATS_PROPS(hdl)->client, + HDL_CLUSTERSTATS_PROPS(hdl)->threaded_poll, + virDomainGetName(dom), virDomainGetMaxMemory(dom)); + } + + if (destination == NULL) { + TRACE("virt", "Nobody wants %s, poor vm!\n", destination); + cherokee_buffer_add_long10(buf, -1); + } else { + virConnectPtr virConnNew; + cherokee_buffer_t uri = CHEROKEE_BUF_INIT; + cherokee_buffer_add_va (&uri, "xen://%s/", destination); + TRACE("virt", "We will transfer to: %s\n", uri.buf); + virConnNew = virConnectOpen (uri.buf); + if (virConnNew == NULL) { + TRACE("virt", "Can't connect to %s\n", uri.buf); + cherokee_buffer_add_long10(buf, -1); + } else { + /* TODO: voodoo oplossen, pointers virConnNew/domNew gaat niet werken */ + virDomainPtr domNew = virDomainMigrate(dom, virConnNew, VIR_MIGRATE_LIVE, NULL, NULL, 0); + + if (domNew) { + virDomainFree(dom); + dom = domNew; + + virConnectClose(virConn); + virConn = virConnNew; + + cherokee_buffer_add_long10(buf, 0); + } else { + cherokee_buffer_add_long10(buf, -1); + } + } + cherokee_buffer_mrproper(&uri); + free(destination); + } + + return ret_ok; + break; + } + case domainUndefine: { int result; if ((result = virDomainUndefine(dom)) != 0) { @@ -811,8 +865,9 @@ virt_virt_function(cherokee_handler_virt_t *hdl, virDomainPtr dom, virConnectPtr char *destination; cherokee_buffer_t xmlDesc = CHEROKEE_BUF_INIT; save_xml(hdl, dom, &xmlDesc); - - destination = create_tender(hdl, virDomainGetName(dom), virDomainGetMaxMemory(dom)); + destination = create_tender(HDL_CLUSTERSTATS_PROPS(hdl)->client, + HDL_CLUSTERSTATS_PROPS(hdl)->threaded_poll, + virDomainGetName(dom), virDomainGetMaxMemory(dom)); if (destination == NULL) { TRACE("virt", "Nobody wants %s, poor vm!\n", destination); @@ -1329,6 +1384,7 @@ virt_build_page (cherokee_handler_virt_t *hdl) /* Maybe do something smart with ENUM, begin_args, end_args... */ if ((hdl->action == domainDefineXML_args) || (hdl->action == domainAttachDevice_args) || + (hdl->action == domainMigrate_args) || (hdl->action == storageVolGetXMLDesc_args) || (hdl->action == storageVolDelete_args) || (hdl->action == storageVolSetPassword_args) || diff --git a/handler_virt.h b/handler_virt.h index f580883..8d5f37b 100644 --- a/handler_virt.h +++ b/handler_virt.h @@ -76,6 +76,7 @@ typedef struct { domainDestroy, domainReboot, domainRestore, + domainMigrate_args, domainSave, domainShutdown, domainInterfaceStats, @@ -100,12 +101,6 @@ typedef struct { } action; } cherokee_handler_virt_t; -typedef struct { - const char *name; - char *dom; - float cost; -} tender_t; - #define HDL_VIRT(x) ((cherokee_handler_virt_t *)(x)) #define PROP_VIRT(x) ((cherokee_handler_virt_props_t *)(x)) #define HDL_VIRT_PROPS(x) (PROP_VIRT(MODULE(x)->props)) diff --git a/handler_virt_tender.c b/handler_virt_tender.c index 715b42d..529c75c 100644 --- a/handler_virt_tender.c +++ b/handler_virt_tender.c @@ -1,8 +1,15 @@ -#include "handler_virt.h" -#include "handler_clusterstats.h" #include "handler_virt_tender.h" -#include #include +#include +#include +#include +#include + +#ifdef NOTRACE + #define TRACE(...) +#else + #include +#endif #include #include @@ -13,6 +20,7 @@ #include #include #include +#include static void entry_group_callback(AvahiEntryGroup *g, AvahiEntryGroupState state, AVAHI_GCC_UNUSED void *userdata) { switch (state) { @@ -106,8 +114,9 @@ static void tender_resolve_callback( if (amount < tender->cost) { /* TODO: LOCK */ tender->cost = amount; + free(tender->dom); tender->dom = strdup(host_name); - TRACE("tender", "We will consider his offer!"); + TRACE("tender", "We will consider %ss offer!\n", tender->dom); } avahi_free(cost); @@ -165,7 +174,7 @@ static void tender_browse_callback( } } -char * create_tender(cherokee_handler_virt_t *hdl, const char *name, unsigned long memory) { +char * create_tender(AvahiClient *client, AvahiThreadedPoll *threaded_poll, const char *name, unsigned long memory) { char txt[255]; tender_t best_tender; @@ -176,15 +185,15 @@ char * create_tender(cherokee_handler_virt_t *hdl, const char *name, unsigned lo best_tender.cost = FLT_MAX; best_tender.dom = NULL; - avahi_threaded_poll_lock(HDL_CLUSTERSTATS_PROPS(hdl)->threaded_poll); - AvahiServiceBrowser *sb = avahi_service_browser_new(HDL_CLUSTERSTATS_PROPS(hdl)->client, AVAHI_IF_UNSPEC, + avahi_threaded_poll_lock(threaded_poll); + AvahiServiceBrowser *sb = avahi_service_browser_new(client, AVAHI_IF_UNSPEC, AVAHI_PROTO_UNSPEC, "_tender._tcp", NULL, 0, tender_browse_callback, &best_tender); if (sb == NULL) { TRACE("avahi", "For whatever reason the sb is NULL\n"); } else { - AvahiEntryGroup *group = avahi_entry_group_new(HDL_CLUSTERSTATS_PROPS(hdl)->client, entry_group_callback, NULL); + AvahiEntryGroup *group = avahi_entry_group_new(client, entry_group_callback, NULL); if (group == NULL) { TRACE("avahi", "For whatever reason the group is NULL\n"); @@ -192,17 +201,17 @@ char * create_tender(cherokee_handler_virt_t *hdl, const char *name, unsigned lo avahi_entry_group_add_service(group, AVAHI_IF_UNSPEC, AVAHI_PROTO_UNSPEC, 0, best_tender.name, "_offer._tcp", NULL, NULL, 651, txt, NULL, NULL); avahi_entry_group_commit(group); - avahi_threaded_poll_unlock(HDL_CLUSTERSTATS_PROPS(hdl)->threaded_poll); + avahi_threaded_poll_unlock(threaded_poll); sleep(3); /* we are for quick bidding ;) */ - avahi_threaded_poll_lock(HDL_CLUSTERSTATS_PROPS(hdl)->threaded_poll); + avahi_threaded_poll_lock(threaded_poll); avahi_entry_group_free(group); } avahi_service_browser_free(sb); } - avahi_threaded_poll_unlock(HDL_CLUSTERSTATS_PROPS(hdl)->threaded_poll); + avahi_threaded_poll_unlock(threaded_poll); return best_tender.dom; } diff --git a/handler_virt_tender.h b/handler_virt_tender.h dissimilarity index 100% index 0d9355e..f5c9394 100644 --- a/handler_virt_tender.h +++ b/handler_virt_tender.h @@ -1 +1,20 @@ -char * create_tender(cherokee_handler_virt_t *hdl, const char *name, unsigned long memory); +#include + +#include +#include +#include + +#include +#include +#include +#include +#include +#include + +typedef struct { + const char *name; + char *dom; + float cost; +} tender_t; + +char * create_tender(AvahiClient *client, AvahiThreadedPoll *threaded_poll, const char *name, unsigned long memory); diff --git a/node/Makefile b/node/Makefile index 427aa11..004720b 100644 --- a/node/Makefile +++ b/node/Makefile @@ -1,2 +1,2 @@ all: - gcc -g -I/usr/include/avahi -I/usr/include/libvirt -lvirt -lavahi-client -Wall avahi.c main.c publish.c tender.c -o node + gcc -g -DNOTRACE -I/usr/include/avahi -I/usr/include/libvirt -lvirt -lavahi-client -Wall avahi.c main.c tender.c migrate.c ../handler_virt_tender.c publish.c -o node diff --git a/node/main.c b/node/main.c index fce15cf..2bdcc59 100644 --- a/node/main.c +++ b/node/main.c @@ -4,13 +4,24 @@ #include #include #include +#include #include "node.h" void terminate(int sig) { - if (offerServiceBrowser) + pid_t pid; + + if (offerServiceBrowser) { avahi_service_browser_free(offerServiceBrowser); + offerServiceBrowser = NULL; + } + pid = fork(); + + if (pid == 0) { + migrate_everything(); + exit(0); + } } int main(AVAHI_GCC_UNUSED int argc, AVAHI_GCC_UNUSED char*argv[]) { diff --git a/node/migrate.c b/node/migrate.c index b2c944e..bea12f3 100644 --- a/node/migrate.c +++ b/node/migrate.c @@ -7,6 +7,7 @@ #include #include #include +#include #include #include @@ -16,7 +17,7 @@ #include "../handler_virt_tender.h" -int migrate_domain(AvahiClient *client, virDomainPtr dom) { +int migrate_domain(AvahiClient *client, AvahiThreadedPoll *threaded_poll, virDomainPtr dom) { int ret = -1; unsigned long memory; char *target; @@ -24,7 +25,7 @@ int migrate_domain(AvahiClient *client, virDomainPtr dom) { virConnectPtr dconn; memory = virDomainGetMaxMemory(dom); - target = create_tender(client, NULL, virDomainGetName(dom), virDomainGetMaxMemory(dom)); + target = create_tender(client, threaded_poll, virDomainGetName(dom), virDomainGetMaxMemory(dom)); snprintf(destination, 1022, "xen://%s/", target); destination[1023] = '\0'; @@ -35,7 +36,7 @@ int migrate_domain(AvahiClient *client, virDomainPtr dom) { if (dconn) { virDomainPtr desDom; - desDom = virDomainMigrate(dom, dconn, VIR_MIGRATE_LIVE, NULL, NULL, 1000); + desDom = virDomainMigrate(dom, dconn, VIR_MIGRATE_LIVE, NULL, NULL, 0); if (desDom) { ret = 0; diff --git a/node/node.h b/node/node.h index ea04bc4..f845df5 100644 --- a/node/node.h +++ b/node/node.h @@ -9,10 +9,14 @@ #include #include +#include #include #include +#include + AvahiSimplePoll *simple_poll; +AvahiServiceBrowser *offerServiceBrowser; #define POLL 5 @@ -24,3 +28,5 @@ int pull_tender(const char *name); void remove_everything(); void pull_all(); int has_tender(const char *name); +int migrate_domain(AvahiClient *client, AvahiThreadedPoll *threaded_poll, virDomainPtr dom); +void migrate_everything(); diff --git a/node/publish.c b/node/publish.c index 63750f6..d5d25bb 100644 --- a/node/publish.c +++ b/node/publish.c @@ -7,6 +7,7 @@ #include #include #include +#include #include @@ -68,19 +69,27 @@ void remove_everything() { } } -void migrate_everything(AvahiClient *c) { +void migrate_everything() { if (domus) { virConnectPtr conn; conn = virConnectOpen(NULL); if (conn) { int i; + AvahiThreadedPoll *threaded_poll = NULL; + AvahiClient *client = NULL; + + if ((threaded_poll = avahi_threaded_poll_new())) { + if ((client = avahi_client_new(avahi_threaded_poll_get(threaded_poll), 0, NULL, NULL, NULL))) + avahi_threaded_poll_start(threaded_poll); + } + for (i = 0; i < domu_count; i++) { virDomainPtr dom; dom = virDomainLookupByID (conn, domus[i].domainid); if (dom) { - if (migrate_domain(c, dom) != 0) { + if (client == NULL || migrate_domain(client, threaded_poll, dom) != 0) { virDomainShutdown(dom); } @@ -88,6 +97,16 @@ void migrate_everything(AvahiClient *c) { } } + + if (threaded_poll) { + if (client) { + avahi_threaded_poll_stop(threaded_poll); + avahi_client_free(client); + } + + avahi_threaded_poll_free(threaded_poll); + } + virConnectClose(conn); } } diff --git a/node/xenistoobig.sh b/node/xenistoobig.sh index 9681679..f5ffdd6 100755 --- a/node/xenistoobig.sh +++ b/node/xenistoobig.sh @@ -1,6 +1,7 @@ #!/bin/sh while [ 1 ]; do if [ `ps aux | grep "xend start" | awk '{ SUM += $6 } END { print SUM }'` -ge 120000 ]; then + echo "Xen is too big!" killall xend; /etc/init.d/xend zap; /etc/init.d/xend start fi sleep 600 -- 2.11.4.GIT