[Spice-devel] [PATCH] server: add channel notifications.
Hans de Goede
hdegoede at redhat.com
Tue Oct 12 02:12:43 PDT 2010
Ack.
On 10/12/2010 10:58 AM, Gerd Hoffmann wrote:
> This patch adds a channel event callback to the spice core interface.
> This new callback will be called for three events:
>
> (1) A new connection has been established.
> (2) The channel is ready (i.e. authentication is done,
> link message verification passed all tests, channel
> is ready to use).
> (3) Channel was disconnected.
>
> Qemu will use this to send notifications to the management app.
>
> Signed-off-by: Gerd Hoffmann<kraxel at redhat.com>
> ---
> server/reds.c | 31 ++++++++++++++++++++++++++++---
> server/reds.h | 2 ++
> server/spice.h | 19 ++++++++++++++++++-
> 3 files changed, 48 insertions(+), 4 deletions(-)
>
> diff --git a/server/reds.c b/server/reds.c
> index 5fafe40..fcdda79 100644
> --- a/server/reds.c
> +++ b/server/reds.c
> @@ -385,6 +385,13 @@ static ChannelSecurityOptions *find_channel_security(int id)
> return now;
> }
>
> +static void reds_channel_event(RedsStreamContext *peer, int event)
> +{
> + if (core->base.minor_version< 3 || core->channel_event == NULL)
> + return;
> + core->channel_event(event,&peer->info);
> +}
> +
> static int reds_write(void *ctx, void *buf, size_t size)
> {
> int return_code;
> @@ -409,6 +416,7 @@ static int reds_read(void *ctx, void *buf, size_t size)
>
> static int reds_free(RedsStreamContext *peer)
> {
> + reds_channel_event(peer, SPICE_CHANNEL_EVENT_DISCONNECTED);
> close(peer->socket);
> free(peer);
> return 0;
> @@ -471,6 +479,7 @@ static int reds_ssl_writev(void *ctx, const struct iovec *vector, int count)
>
> static int reds_ssl_free(RedsStreamContext *peer)
> {
> + reds_channel_event(peer, SPICE_CHANNEL_EVENT_DISCONNECTED);
> SSL_free(peer->ssl);
> close(peer->socket);
> free(peer);
> @@ -1980,12 +1989,20 @@ static int reds_send_link_error(RedLinkInfo *link, uint32_t error)
> sizeof(reply));
> }
>
> -static void reds_show_new_channel(RedLinkInfo *link)
> +static void reds_show_new_channel(RedLinkInfo *link, int connection_id)
> {
> red_printf("channel %d:%d, connected successfully, over %s link",
> link->link_mess->channel_type,
> link->link_mess->channel_id,
> link->peer->ssl == NULL ? "Non Secure" : "Secure");
> + /* add info + send event */
> + if (link->peer->ssl) {
> + link->peer->info.flags |= SPICE_CHANNEL_EVENT_FLAG_TLS;
> + }
> + link->peer->info.connection_id = connection_id;
> + link->peer->info.type = link->link_mess->channel_type;
> + link->peer->info.id = link->link_mess->channel_id;
> + reds_channel_event(link->peer, SPICE_CHANNEL_EVENT_INITIALIZED);
> }
>
> static void reds_send_link_result(RedLinkInfo *link, uint32_t error)
> @@ -2038,7 +2055,7 @@ static void reds_handle_main_link(RedLinkInfo *link)
> reds->peer = link->peer;
> reds->in_handler.shut = FALSE;
>
> - reds_show_new_channel(link);
> + reds_show_new_channel(link, connection_id);
> __reds_release_link(link);
> if (vdagent) {
> SpiceCharDeviceInterface *sif;
> @@ -2530,7 +2547,7 @@ static void reds_handle_other_links(RedLinkInfo *link)
> }
>
> reds_send_link_result(link, SPICE_LINK_ERR_OK);
> - reds_show_new_channel(link);
> + reds_show_new_channel(link, reds->link_id);
> if (link_mess->channel_type == SPICE_CHANNEL_INPUTS&& !link->peer->ssl) {
> RedsOutItem *item;
> SpiceMsgNotify notify;
> @@ -2813,6 +2830,14 @@ static RedLinkInfo *__reds_accept_connection(int listen_socket)
> peer = spice_new0(RedsStreamContext, 1);
> link->peer = peer;
> peer->socket = socket;
> +
> + /* gather info + send event */
> + peer->info.llen = sizeof(peer->info.laddr);
> + peer->info.plen = sizeof(peer->info.paddr);
> + getsockname(peer->socket, (struct sockaddr*)(&peer->info.laddr),&peer->info.llen);
> + getpeername(peer->socket, (struct sockaddr*)(&peer->info.paddr),&peer->info.plen);
> + reds_channel_event(peer, SPICE_CHANNEL_EVENT_CONNECTED);
> +
> openssl_init(link);
>
> return link;
> diff --git a/server/reds.h b/server/reds.h
> index 6eed02b..e95aea5 100644
> --- a/server/reds.h
> +++ b/server/reds.h
> @@ -35,6 +35,8 @@ typedef struct RedsStreamContext {
> int shutdown;
> SSL *ssl;
>
> + SpiceChannelEventInfo info;
> +
> int (*cb_write)(void *, void *, int);
> int (*cb_read)(void *, void *, int);
>
> diff --git a/server/spice.h b/server/spice.h
> index 6f4c782..e630402 100644
> --- a/server/spice.h
> +++ b/server/spice.h
> @@ -42,18 +42,34 @@ struct SpiceBaseInstance {
>
> #define SPICE_INTERFACE_CORE "core"
> #define SPICE_INTERFACE_CORE_MAJOR 1
> -#define SPICE_INTERFACE_CORE_MINOR 2
> +#define SPICE_INTERFACE_CORE_MINOR 3
> typedef struct SpiceCoreInterface SpiceCoreInterface;
>
> #define SPICE_WATCH_EVENT_READ (1<< 0)
> #define SPICE_WATCH_EVENT_WRITE (1<< 1)
>
> +#define SPICE_CHANNEL_EVENT_CONNECTED 1
> +#define SPICE_CHANNEL_EVENT_INITIALIZED 2
> +#define SPICE_CHANNEL_EVENT_DISCONNECTED 3
> +
> +#define SPICE_CHANNEL_EVENT_FLAG_TLS (1<< 0)
> +
> typedef struct SpiceWatch SpiceWatch;
> typedef void (*SpiceWatchFunc)(int fd, int event, void *opaque);
>
> typedef struct SpiceTimer SpiceTimer;
> typedef void (*SpiceTimerFunc)(void *opaque);
>
> +typedef struct SpiceChannelEventInfo {
> + int connection_id;
> + int type;
> + int id;
> + int flags;
> + struct sockaddr laddr;
> + struct sockaddr paddr;
> + socklen_t llen, plen;
> +} SpiceChannelEventInfo;
> +
> struct SpiceCoreInterface {
> SpiceBaseInterface base;
>
> @@ -66,6 +82,7 @@ struct SpiceCoreInterface {
> void (*watch_update_mask)(SpiceWatch *watch, int event_mask);
> void (*watch_remove)(SpiceWatch *watch);
>
> + void (*channel_event)(int event, SpiceChannelEventInfo *info);
> };
>
> /* qxl interface */
More information about the Spice-devel
mailing list