File:  [Qemu by Fabrice Bellard] / qemu / migration-fd.c
Revision 1.1.1.2 (vendor branch): download - view: text, annotated - select for diffs
Tue Apr 24 18:23:10 2018 UTC (3 years, 1 month ago) by root
Branches: qemu, MAIN
CVS tags: qemu0150, qemu0141, qemu0140, qemu0130, HEAD
qemu 0.13.0

    1: /*
    2:  * QEMU live migration via generic fd
    3:  *
    4:  * Copyright Red Hat, Inc. 2009
    5:  *
    6:  * Authors:
    7:  *  Chris Lalancette <clalance@redhat.com>
    8:  *
    9:  * This work is licensed under the terms of the GNU GPL, version 2.  See
   10:  * the COPYING file in the top-level directory.
   11:  *
   12:  */
   13: 
   14: #include "qemu-common.h"
   15: #include "qemu_socket.h"
   16: #include "migration.h"
   17: #include "monitor.h"
   18: #include "qemu-char.h"
   19: #include "sysemu.h"
   20: #include "buffered_file.h"
   21: #include "block.h"
   22: #include "qemu_socket.h"
   23: 
   24: //#define DEBUG_MIGRATION_FD
   25: 
   26: #ifdef DEBUG_MIGRATION_FD
   27: #define DPRINTF(fmt, ...) \
   28:     do { printf("migration-fd: " fmt, ## __VA_ARGS__); } while (0)
   29: #else
   30: #define DPRINTF(fmt, ...) \
   31:     do { } while (0)
   32: #endif
   33: 
   34: static int fd_errno(FdMigrationState *s)
   35: {
   36:     return errno;
   37: }
   38: 
   39: static int fd_write(FdMigrationState *s, const void * buf, size_t size)
   40: {
   41:     return write(s->fd, buf, size);
   42: }
   43: 
   44: static int fd_close(FdMigrationState *s)
   45: {
   46:     DPRINTF("fd_close\n");
   47:     if (s->fd != -1) {
   48:         close(s->fd);
   49:         s->fd = -1;
   50:     }
   51:     return 0;
   52: }
   53: 
   54: MigrationState *fd_start_outgoing_migration(Monitor *mon,
   55: 					    const char *fdname,
   56: 					    int64_t bandwidth_limit,
   57: 					    int detach,
   58: 					    int blk,
   59: 					    int inc)
   60: {
   61:     FdMigrationState *s;
   62: 
   63:     s = qemu_mallocz(sizeof(*s));
   64: 
   65:     s->fd = monitor_get_fd(mon, fdname);
   66:     if (s->fd == -1) {
   67:         DPRINTF("fd_migration: invalid file descriptor identifier\n");
   68:         goto err_after_alloc;
   69:     }
   70: 
   71:     if (fcntl(s->fd, F_SETFL, O_NONBLOCK) == -1) {
   72:         DPRINTF("Unable to set nonblocking mode on file descriptor\n");
   73:         goto err_after_open;
   74:     }
   75: 
   76:     s->get_error = fd_errno;
   77:     s->write = fd_write;
   78:     s->close = fd_close;
   79:     s->mig_state.cancel = migrate_fd_cancel;
   80:     s->mig_state.get_status = migrate_fd_get_status;
   81:     s->mig_state.release = migrate_fd_release;
   82: 
   83:     s->mig_state.blk = blk;
   84:     s->mig_state.shared = inc;
   85: 
   86:     s->state = MIG_STATE_ACTIVE;
   87:     s->mon = NULL;
   88:     s->bandwidth_limit = bandwidth_limit;
   89: 
   90:     if (!detach) {
   91:         migrate_fd_monitor_suspend(s, mon);
   92:     }
   93: 
   94:     migrate_fd_connect(s);
   95:     return &s->mig_state;
   96: 
   97: err_after_open:
   98:     close(s->fd);
   99: err_after_alloc:
  100:     qemu_free(s);
  101:     return NULL;
  102: }
  103: 
  104: static void fd_accept_incoming_migration(void *opaque)
  105: {
  106:     QEMUFile *f = opaque;
  107: 
  108:     process_incoming_migration(f);
  109:     qemu_set_fd_handler2(qemu_stdio_fd(f), NULL, NULL, NULL, NULL);
  110:     qemu_fclose(f);
  111: }
  112: 
  113: int fd_start_incoming_migration(const char *infd)
  114: {
  115:     int fd;
  116:     QEMUFile *f;
  117: 
  118:     DPRINTF("Attempting to start an incoming migration via fd\n");
  119: 
  120:     fd = strtol(infd, NULL, 0);
  121:     f = qemu_fdopen(fd, "rb");
  122:     if(f == NULL) {
  123:         DPRINTF("Unable to apply qemu wrapper to file descriptor\n");
  124:         return -errno;
  125:     }
  126: 
  127:     qemu_set_fd_handler2(fd, NULL, fd_accept_incoming_migration, NULL, f);
  128: 
  129:     return 0;
  130: }

unix.superglobalmegacorp.com