diff options
author | Thanos Makatos <thanos.makatos@nutanix.com> | 2020-11-02 04:16:08 -0500 |
---|---|---|
committer | Thanos Makatos <thanos.makatos@nutanix.com> | 2020-11-05 10:49:29 -0500 |
commit | 3459c17659584501747823071dd6adbd4a2e0cd3 (patch) | |
tree | edbe765fbe46c3d14cb0ece345ee45eb5025a444 /samples/server.c | |
parent | 41914861c6bde1fd6e369cbbe28a5b3df5dd6b67 (diff) | |
download | libvfio-user-3459c17659584501747823071dd6adbd4a2e0cd3.zip libvfio-user-3459c17659584501747823071dd6adbd4a2e0cd3.tar.gz libvfio-user-3459c17659584501747823071dd6adbd4a2e0cd3.tar.bz2 |
experimental support for running the device state and copy iteration protocol
Signed-off-by: Thanos Makatos <thanos.makatos@nutanix.com>
Diffstat (limited to 'samples/server.c')
-rw-r--r-- | samples/server.c | 76 |
1 files changed, 73 insertions, 3 deletions
diff --git a/samples/server.c b/samples/server.c index 9f4d3b1..4611fb0 100644 --- a/samples/server.c +++ b/samples/server.c @@ -40,6 +40,7 @@ #include <assert.h> #include <openssl/md5.h> #include <sys/mman.h> +#include <sys/param.h> #include "../lib/muser.h" @@ -54,6 +55,11 @@ struct server_data { time_t bar0; uint8_t *bar1; struct dma_regions regions[NR_DMA_REGIONS]; + struct { + int fake_internal_state; + __u64 pending_bytes; + __u64 data_size; + } migration; }; static void @@ -205,8 +211,65 @@ static int device_reset(void *pvt) printf("device reset callback\n"); } -int main(int argc, char *argv[]) +static int +migration_device_state_transition(void *pvt, lm_migr_state_t state) { + struct server_data *server_data = pvt; + + printf("migration: transition to device state %d\n", state); + + switch (state) { + case LM_MIGR_STATE_STOP_AND_COPY: + /* TODO must be less than size of data region in migration region */ + server_data->migration.pending_bytes = sysconf(_SC_PAGESIZE); + break; + case LM_MIGR_STATE_STOP: + assert(server_data->migration.pending_bytes == 0); + break; + default: + assert(false); /* FIXME */ + } + return 0; +} + +static __u64 +migration_get_pending_bytes(void *pvt) +{ + struct server_data *server_data = pvt; + if (server_data->migration.data_size > 0) { + assert(server_data->migration.data_size <= server_data->migration.pending_bytes); + server_data->migration.pending_bytes -= server_data->migration.data_size; + } + return server_data->migration.pending_bytes; +} + +static int +migration_prepare_data(void *pvt, __u64 *offset, __u64 *size) +{ + struct server_data *server_data = pvt; + + *offset = 0; + *size = server_data->migration.data_size = MIN(server_data->migration.pending_bytes, sysconf(_SC_PAGESIZE) / 4); + return 0; +} + +static size_t +migration_read_data(void *pvt, void *buf, __u64 size, __u64 offset) +{ + struct server_data *server_data = pvt; + + assert(server_data->migration.data_size >= size); + + return 0; +} + +static size_t +migration_write_data(void *pvt, void *data, __u64 size) +{ + assert(false); +} + +int main(int argc, char *argv[]){ int ret; bool trans_sock = false, verbose = false; char opt; @@ -269,7 +332,7 @@ int main(int argc, char *argv[]) }, .reg_info[LM_DEV_MIGRATION_REG_IDX] = { /* migration region */ .flags = LM_REG_FLAG_RW, - .size = sysconf(_SC_PAGESIZE), + .size = sizeof(struct vfio_device_migration_info) + sysconf(_SC_PAGESIZE), .mmap_areas = sparse_areas, }, .irq_count[LM_DEV_INTX_IRQ_IDX] = 1, @@ -278,7 +341,14 @@ int main(int argc, char *argv[]) .reset = device_reset, .map_dma = map_dma, .unmap_dma = unmap_dma, - .pvt = &server_data + .pvt = &server_data, + .migration_callbacks = { + .transition = &migration_device_state_transition, + .get_pending_bytes = &migration_get_pending_bytes, + .prepare_data = &migration_prepare_data, + .read_data = &migration_read_data, + .write_data = &migration_write_data + } }; sigemptyset(&act.sa_mask); |