2 * This file is part of the Palacios Virtual Machine Monitor developed
3 * by the V3VEE Project with funding from the United States National
4 * Science Foundation and the Department of Energy.
6 * The V3VEE Project is a joint project between Northwestern University
7 * and the University of New Mexico. You can find out more at
10 * Copyright (c) 2012, Jack Lange <jarusl@cs.northwestern.edu>
11 * Copyright (c) 2012, The V3VEE Project <http://www.v3vee.org>
12 * All rights reserved.
14 * Author: Jack Lange <jarusl@cs.northwestern.edu>
16 * This is free software. You are permitted to use,
17 * redistribute, and modify it as specified in the file "V3VEE_LICENSE".
22 #include <palacios/vmm_events.h>
23 #include <palacios/vm_guest.h>
27 int v3_init_events(struct v3_vm_info * vm) {
28 struct v3_event_map * map = &(vm->event_map);
31 map->events = V3_Malloc(sizeof(struct list_head) * V3_EVENT_INVALID);
33 if (map->events == NULL) {
34 PrintError("Error: could not allocate event map\n");
38 for (i = 0; i < V3_EVENT_INVALID; i++) {
39 INIT_LIST_HEAD(&(map->events[i]));
45 int v3_deinit_events(struct v3_vm_info * vm) {
46 struct v3_event_map * map = &(vm->event_map);
49 for (i = 0; i < V3_EVENT_INVALID; i++) {
50 if (!list_empty(&(map->events[i]))) {
51 struct v3_notifier * tmp_notifier = NULL;
52 struct v3_notifier * safe_notifier = NULL;
53 PrintError("Found orphan notifier for event %d. Probable memory leak detected.\n", i);
55 list_for_each_entry_safe(tmp_notifier, safe_notifier, &(map->events[i]), node) {
56 list_del(&(tmp_notifier->node));
57 V3_Free(tmp_notifier);
70 struct v3_notifier * v3_subscribe_event(struct v3_vm_info * vm,
71 v3_event_type_t event_type,
72 void (*notify)(struct guest_info * core,
73 v3_event_type_t event_type,
77 struct guest_info * current_core) {
78 struct v3_event_map * map = &(vm->event_map);
79 struct v3_notifier * notifier = NULL;
81 if (event_type >= V3_EVENT_INVALID) {
82 PrintError("Tried to request illegal event (%d)\n", event_type);
86 notifier = V3_Malloc(sizeof(struct v3_notifier));
88 if (notifier == NULL) {
89 PrintError("Error: Could not allocate notifier\n");
93 memset(notifier, 0, sizeof(struct v3_notifier));
95 notifier->notify = notify;
96 notifier->priv_data = priv_data;
97 notifier->event_type = event_type;
99 while (v3_raise_barrier(vm, current_core) == -1);
100 list_add(&(notifier->node), &(map->events[event_type]));
101 v3_lower_barrier(vm);
107 int v3_unsubscribe_event(struct v3_vm_info * vm, struct v3_notifier * notifier,
108 struct guest_info * current_core) {
109 struct v3_event_map * map = &(vm->event_map);
110 struct v3_notifier * tmp_notifier = NULL;
111 struct v3_notifier * safe_notifier = NULL;
113 if (notifier == NULL) {
114 PrintError("Could not unsubscribe invalid event notifier\n");
118 if (notifier->event_type >= V3_EVENT_INVALID) {
119 PrintError("Could not unsubscribe from invalid event\n");
123 while (v3_raise_barrier(vm, current_core) == -1);
124 list_for_each_entry_safe(tmp_notifier, safe_notifier, &(map->events[notifier->event_type]), node) {
125 if (tmp_notifier == notifier) {
126 list_del(&(tmp_notifier->node));
127 V3_Free(tmp_notifier);
130 v3_lower_barrier(vm);