network_event.c 7.6 KB
Newer Older
1 2 3
/*
 * network_event.c: network event queue processing helpers
 *
4
 * Copyright (C) 2014 Red Hat, Inc.
5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31
 * Copyright (C) 2013 SUSE LINUX Products GmbH, Nuernberg, Germany.
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library.  If not, see
 * <http://www.gnu.org/licenses/>.
 *
 * Author: Cedric Bosdonnat
 */

#include <config.h>

#include "network_event.h"
#include "object_event.h"
#include "object_event_private.h"
#include "datatypes.h"
#include "virlog.h"

32 33
VIR_LOG_INIT("conf.network_event");

34
struct _virNetworkEvent {
35 36
    virObjectEvent parent;

37
    /* Unused attribute to allow for subclass creation */
38 39 40 41 42 43 44 45
    bool dummy;
};
typedef struct _virNetworkEvent virNetworkEvent;
typedef virNetworkEvent *virNetworkEventPtr;

struct _virNetworkEventLifecycle {
    virNetworkEvent parent;

46
    int type;
47
    int detail;
48 49 50 51
};
typedef struct _virNetworkEventLifecycle virNetworkEventLifecycle;
typedef virNetworkEventLifecycle *virNetworkEventLifecyclePtr;

52
static virClassPtr virNetworkEventClass;
53
static virClassPtr virNetworkEventLifecycleClass;
54
static void virNetworkEventDispose(void *obj);
55 56 57 58 59
static void virNetworkEventLifecycleDispose(void *obj);

static int
virNetworkEventsOnceInit(void)
{
60
    if (!(virNetworkEventClass =
61
          virClassNew(virClassForObjectEvent(),
62 63 64 65 66 67
                      "virNetworkEvent",
                      sizeof(virNetworkEvent),
                      virNetworkEventDispose)))
        return -1;
    if (!(virNetworkEventLifecycleClass =
          virClassNew(virNetworkEventClass,
68 69 70 71 72 73 74 75 76
                      "virNetworkEventLifecycle",
                      sizeof(virNetworkEventLifecycle),
                      virNetworkEventLifecycleDispose)))
        return -1;
    return 0;
}

VIR_ONCE_GLOBAL_INIT(virNetworkEvents)

77
static void
78 79 80 81 82 83 84
virNetworkEventDispose(void *obj)
{
    virNetworkEventPtr event = obj;
    VIR_DEBUG("obj=%p", event);
}


85
static void
86 87 88 89 90 91 92
virNetworkEventLifecycleDispose(void *obj)
{
    virNetworkEventLifecyclePtr event = obj;
    VIR_DEBUG("obj=%p", event);
}


93
static void
94 95
virNetworkEventDispatchDefaultFunc(virConnectPtr conn,
                                   virObjectEventPtr event,
96 97
                                   virConnectObjectEventGenericCallback cb,
                                   void *cbopaque)
98 99 100 101 102
{
    virNetworkPtr net = virGetNetwork(conn, event->meta.name, event->meta.uuid);
    if (!net)
        return;

103
    switch ((virNetworkEventID)event->eventID) {
104 105 106 107 108 109 110
    case VIR_NETWORK_EVENT_ID_LIFECYCLE:
        {
            virNetworkEventLifecyclePtr networkLifecycleEvent;

            networkLifecycleEvent = (virNetworkEventLifecyclePtr)event;
            ((virConnectNetworkEventLifecycleCallback)cb)(conn, net,
                                                          networkLifecycleEvent->type,
111
                                                          networkLifecycleEvent->detail,
112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131
                                                          cbopaque);
            goto cleanup;
        }

    case VIR_NETWORK_EVENT_ID_LAST:
        break;
    }
    VIR_WARN("Unexpected event ID %d", event->eventID);

cleanup:
    virNetworkFree(net);
}


/**
 * virNetworkEventStateRegisterID:
 * @conn: connection to associate with callback
 * @state: object event state
 * @net: network to filter on or NULL for all networks
 * @eventID: ID of the event type to register for
132 133
 * @cb: function to invoke when event occurs
 * @opaque: data blob to pass to @callback
134 135 136
 * @freecb: callback to free @opaque
 * @callbackID: filled with callback ID
 *
137 138 139
 * Register the function @cb with connection @conn, from @state, for
 * events of type @eventID, and return the registration handle in
 * @callbackID.
140 141 142 143 144 145 146 147
 *
 * Returns: the number of callbacks now registered, or -1 on error
 */
int
virNetworkEventStateRegisterID(virConnectPtr conn,
                               virObjectEventStatePtr state,
                               virNetworkPtr net,
                               int eventID,
148
                               virConnectNetworkEventGenericCallback cb,
149 150 151 152
                               void *opaque,
                               virFreeCallback freecb,
                               int *callbackID)
{
153 154 155
    if (virNetworkEventsInitialize() < 0)
        return -1;

156
    return virObjectEventStateRegisterID(conn, state, net ? net->uuid : NULL,
157 158
                                         NULL, NULL,
                                         virNetworkEventClass, eventID,
159
                                         VIR_OBJECT_EVENT_CALLBACK(cb),
160 161
                                         opaque, freecb,
                                         false, callbackID, false);
162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196
}


/**
 * virNetworkEventStateRegisterClient:
 * @conn: connection to associate with callback
 * @state: object event state
 * @net: network to filter on or NULL for all networks
 * @eventID: ID of the event type to register for
 * @cb: function to invoke when event occurs
 * @opaque: data blob to pass to @callback
 * @freecb: callback to free @opaque
 * @callbackID: filled with callback ID
 *
 * Register the function @cb with connection @conn, from @state, for
 * events of type @eventID, and return the registration handle in
 * @callbackID.  This version is intended for use on the client side
 * of RPC.
 *
 * Returns: the number of callbacks now registered, or -1 on error
 */
int
virNetworkEventStateRegisterClient(virConnectPtr conn,
                                   virObjectEventStatePtr state,
                                   virNetworkPtr net,
                                   int eventID,
                                   virConnectNetworkEventGenericCallback cb,
                                   void *opaque,
                                   virFreeCallback freecb,
                                   int *callbackID)
{
    if (virNetworkEventsInitialize() < 0)
        return -1;

    return virObjectEventStateRegisterID(conn, state, net ? net->uuid : NULL,
197
                                         NULL, NULL,
198 199
                                         virNetworkEventClass, eventID,
                                         VIR_OBJECT_EVENT_CALLBACK(cb),
200 201
                                         opaque, freecb,
                                         false, callbackID, true);
202 203
}

204 205 206 207 208 209 210 211 212 213

/**
 * virNetworkEventLifecycleNew:
 * @name: name of the network object the event describes
 * @uuid: uuid of the network object the event describes
 * @type: type of lifecycle event
 * @detail: more details about @type
 *
 * Create a new network lifecycle event.
 */
214 215 216
virObjectEventPtr
virNetworkEventLifecycleNew(const char *name,
                            const unsigned char *uuid,
217 218
                            int type,
                            int detail)
219 220 221 222 223 224 225
{
    virNetworkEventLifecyclePtr event;

    if (virNetworkEventsInitialize() < 0)
        return NULL;

    if (!(event = virObjectEventNew(virNetworkEventLifecycleClass,
226
                                    virNetworkEventDispatchDefaultFunc,
227
                                    VIR_NETWORK_EVENT_ID_LIFECYCLE,
228 229 230 231
                                    0, name, uuid)))
        return NULL;

    event->type = type;
232
    event->detail = detail;
233 234 235

    return (virObjectEventPtr)event;
}