2
0

replay-net.c 2.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101
  1. /*
  2. * replay-net.c
  3. *
  4. * Copyright (c) 2010-2016 Institute for System Programming
  5. * of the Russian Academy of Sciences.
  6. *
  7. * This work is licensed under the terms of the GNU GPL, version 2 or later.
  8. * See the COPYING file in the top-level directory.
  9. *
  10. */
  11. #include "qemu/osdep.h"
  12. #include "qemu/error-report.h"
  13. #include "sysemu/replay.h"
  14. #include "replay-internal.h"
  15. #include "net/net.h"
  16. #include "net/filter.h"
  17. #include "qemu/iov.h"
  18. struct ReplayNetState {
  19. NetFilterState *nfs;
  20. int id;
  21. };
  22. typedef struct NetEvent {
  23. uint8_t id;
  24. uint32_t flags;
  25. uint8_t *data;
  26. size_t size;
  27. } NetEvent;
  28. static NetFilterState **network_filters;
  29. static int network_filters_count;
  30. ReplayNetState *replay_register_net(NetFilterState *nfs)
  31. {
  32. ReplayNetState *rns = g_new0(ReplayNetState, 1);
  33. rns->nfs = nfs;
  34. rns->id = network_filters_count++;
  35. network_filters = g_realloc(network_filters,
  36. network_filters_count
  37. * sizeof(*network_filters));
  38. network_filters[network_filters_count - 1] = nfs;
  39. return rns;
  40. }
  41. void replay_unregister_net(ReplayNetState *rns)
  42. {
  43. network_filters[rns->id] = NULL;
  44. g_free(rns);
  45. }
  46. void replay_net_packet_event(ReplayNetState *rns, unsigned flags,
  47. const struct iovec *iov, int iovcnt)
  48. {
  49. NetEvent *event = g_new(NetEvent, 1);
  50. event->flags = flags;
  51. event->data = g_malloc(iov_size(iov, iovcnt));
  52. event->size = iov_size(iov, iovcnt);
  53. event->id = rns->id;
  54. iov_to_buf(iov, iovcnt, 0, event->data, event->size);
  55. replay_add_event(REPLAY_ASYNC_EVENT_NET, event, NULL, 0);
  56. }
  57. void replay_event_net_run(void *opaque)
  58. {
  59. NetEvent *event = opaque;
  60. struct iovec iov = {
  61. .iov_base = (void *)event->data,
  62. .iov_len = event->size
  63. };
  64. assert(event->id < network_filters_count);
  65. qemu_netfilter_pass_to_next(network_filters[event->id]->netdev,
  66. event->flags, &iov, 1, network_filters[event->id]);
  67. g_free(event->data);
  68. g_free(event);
  69. }
  70. void replay_event_net_save(void *opaque)
  71. {
  72. NetEvent *event = opaque;
  73. replay_put_byte(event->id);
  74. replay_put_dword(event->flags);
  75. replay_put_array(event->data, event->size);
  76. }
  77. void *replay_event_net_load(void)
  78. {
  79. NetEvent *event = g_new(NetEvent, 1);
  80. event->id = replay_get_byte();
  81. event->flags = replay_get_dword();
  82. replay_get_array_alloc(&event->data, &event->size);
  83. return event;
  84. }