Skip to content

Commit c6263a2

Browse files
committed
GUACAMOLE-261: Implement Spice protocol support.
1 parent b20afa2 commit c6263a2

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

67 files changed

+9876
-0
lines changed

Makefile.am

+5
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@ DIST_SUBDIRS = \
3737
src/pulse \
3838
src/protocols/kubernetes \
3939
src/protocols/rdp \
40+
src/protocols/spice \
4041
src/protocols/ssh \
4142
src/protocols/telnet \
4243
src/protocols/vnc
@@ -65,6 +66,10 @@ if ENABLE_RDP
6566
SUBDIRS += src/protocols/rdp
6667
endif
6768

69+
if ENABLE_SPICE
70+
SUBDIRS += src/protocols/spice
71+
endif
72+
6873
if ENABLE_SSH
6974
SUBDIRS += src/protocols/ssh
7075
endif

configure.ac

+24
Original file line numberDiff line numberDiff line change
@@ -634,6 +634,27 @@ then
634634

635635
fi
636636

637+
#
638+
# spice-glib
639+
#
640+
641+
have_spice_glib=disabled
642+
AC_ARG_WITH([spice],
643+
[AS_HELP_STRING([--with-spice],
644+
[support SPICE @<:@default=check@:>@])],
645+
[],
646+
[with_spice=check])
647+
648+
if test "x$with_spice" != "xno"
649+
then
650+
have_spice_glib=yes
651+
PKG_CHECK_MODULES([GLIB2], [glib-2.0],, [have_spice_glib=no])
652+
PKG_CHECK_MODULES([SPICE], [spice-client-glib-2.0],, [have_spice_glib=no])
653+
fi
654+
655+
AM_CONDITIONAL([ENABLE_SPICE], [test "x${have_spice_glib}" = "xyes"])
656+
AC_SUBST(SPICE_LIBS)
657+
637658

638659
#
639660
# FreeRDP 2 (libfreerdp2, libfreerdp-client2, and libwinpr2)
@@ -1188,6 +1209,7 @@ AC_CONFIG_FILES([Makefile
11881209
src/protocols/kubernetes/tests/Makefile
11891210
src/protocols/rdp/Makefile
11901211
src/protocols/rdp/tests/Makefile
1212+
src/protocols/spice/Makefile
11911213
src/protocols/ssh/Makefile
11921214
src/protocols/telnet/Makefile
11931215
src/protocols/vnc/Makefile])
@@ -1199,6 +1221,7 @@ AC_OUTPUT
11991221

12001222
AM_COND_IF([ENABLE_KUBERNETES], [build_kubernetes=yes], [build_kubernetes=no])
12011223
AM_COND_IF([ENABLE_RDP], [build_rdp=yes], [build_rdp=no])
1224+
AM_COND_IF([ENABLE_SPICE], [build_spice=yes], [build_spice=no])
12021225
AM_COND_IF([ENABLE_SSH], [build_ssh=yes], [build_ssh=no])
12031226
AM_COND_IF([ENABLE_TELNET], [build_telnet=yes], [build_telnet=no])
12041227
AM_COND_IF([ENABLE_VNC], [build_vnc=yes], [build_vnc=no])
@@ -1260,6 +1283,7 @@ $PACKAGE_NAME version $PACKAGE_VERSION
12601283

12611284
Kubernetes .... ${build_kubernetes}
12621285
RDP ........... ${build_rdp}
1286+
SPICE ......... ${build_spice}
12631287
SSH ........... ${build_ssh}
12641288
Telnet ........ ${build_telnet}
12651289
VNC ........... ${build_vnc}

src/protocols/spice/Makefile.am

+139
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,139 @@
1+
#
2+
# Licensed to the Apache Software Foundation (ASF) under one
3+
# or more contributor license agreements. See the NOTICE file
4+
# distributed with this work for additional information
5+
# regarding copyright ownership. The ASF licenses this file
6+
# to you under the Apache License, Version 2.0 (the
7+
# "License"); you may not use this file except in compliance
8+
# with the License. You may obtain a copy of the License at
9+
#
10+
# http://www.apache.org/licenses/LICENSE-2.0
11+
#
12+
# Unless required by applicable law or agreed to in writing,
13+
# software distributed under the License is distributed on an
14+
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15+
# KIND, either express or implied. See the License for the
16+
# specific language governing permissions and limitations
17+
# under the License.
18+
#
19+
# NOTE: Parts of this file (Makefile.am) are automatically transcluded verbatim
20+
# into Makefile.in. Though the build system (GNU Autotools) automatically adds
21+
# its own license boilerplate to the generated Makefile.in, that boilerplate
22+
# does not apply to the transcluded portions of Makefile.am which are licensed
23+
# to you by the ASF under the Apache License, Version 2.0, as described above.
24+
#
25+
26+
AUTOMAKE_OPTIONS = foreign
27+
ACLOCAL_AMFLAGS = -I m4
28+
29+
lib_LTLIBRARIES = libguac-client-spice.la
30+
31+
nodist_libguac_client_spice_la_SOURCES = \
32+
_generated_keymaps.c
33+
34+
libguac_client_spice_la_SOURCES = \
35+
argv.c \
36+
auth.c \
37+
channels/audio.c \
38+
channels/clipboard.c \
39+
channels/cursor.c \
40+
channels/display.c \
41+
channels/file.c \
42+
channels/file-download.c \
43+
channels/file-ls.c \
44+
channels/file-upload.c \
45+
client.c \
46+
decompose.c \
47+
input.c \
48+
keyboard.c \
49+
keymap.c \
50+
log.c \
51+
settings.c \
52+
spice.c \
53+
user.c
54+
55+
noinst_HEADERS = \
56+
argv.h \
57+
auth.h \
58+
channels/audio.h \
59+
channels/clipboard.h \
60+
channels/cursor.h \
61+
channels/display.h \
62+
channels/file.h \
63+
channels/file-download.h \
64+
channels/file-ls.h \
65+
channels/file-upload.h \
66+
client.h \
67+
decompose.h \
68+
input.h \
69+
keyboard.h \
70+
keymap.h \
71+
log.h \
72+
settings.h \
73+
spice.h \
74+
user.h
75+
76+
libguac_client_spice_la_CFLAGS = \
77+
-Werror -Wall -pedantic -Iinclude \
78+
@COMMON_INCLUDE@ \
79+
@COMMON_SSH_INCLUDE@ \
80+
@LIBGUAC_INCLUDE@ \
81+
@GLIB2_CFLAGS@ \
82+
@SPICE_CFLAGS@
83+
84+
libguac_client_spice_la_LDFLAGS = \
85+
-version-info 0:0:0 \
86+
@CAIRO_LIBS@ \
87+
@GLIB2_LIBS@ \
88+
@SPICE_LIBS@
89+
90+
libguac_client_spice_la_LIBADD = \
91+
@COMMON_LTLIB@ \
92+
@LIBGUAC_LTLIB@
93+
94+
# Optional SFTP support
95+
if ENABLE_COMMON_SSH
96+
libguac_client_spice_la_SOURCES += sftp.c
97+
noinst_HEADERS += sftp.h
98+
libguac_client_spice_la_LIBADD += @COMMON_SSH_LTLIB@
99+
endif
100+
101+
#
102+
# Autogenerated keymaps and channel wrapper functions
103+
#
104+
105+
CLEANFILES = \
106+
_generated_keymaps.c
107+
108+
BUILT_SOURCES = \
109+
_generated_keymaps.c
110+
111+
spice_keymaps = \
112+
$(srcdir)/keymaps/base.keymap \
113+
$(srcdir)/keymaps/failsafe.keymap \
114+
$(srcdir)/keymaps/de_de_qwertz.keymap \
115+
$(srcdir)/keymaps/de_ch_qwertz.keymap \
116+
$(srcdir)/keymaps/en_gb_qwerty.keymap \
117+
$(srcdir)/keymaps/en_us_qwerty.keymap \
118+
$(srcdir)/keymaps/es_es_qwerty.keymap \
119+
$(srcdir)/keymaps/es_latam_qwerty.keymap \
120+
$(srcdir)/keymaps/fr_be_azerty.keymap \
121+
$(srcdir)/keymaps/fr_ca_qwerty.keymap \
122+
$(srcdir)/keymaps/fr_ch_qwertz.keymap \
123+
$(srcdir)/keymaps/fr_fr_azerty.keymap \
124+
$(srcdir)/keymaps/hu_hu_qwertz.keymap \
125+
$(srcdir)/keymaps/it_it_qwerty.keymap \
126+
$(srcdir)/keymaps/ja_jp_qwerty.keymap \
127+
$(srcdir)/keymaps/no_no_qwerty.keymap \
128+
$(srcdir)/keymaps/pl_pl_qwerty.keymap \
129+
$(srcdir)/keymaps/pt_br_qwerty.keymap \
130+
$(srcdir)/keymaps/sv_se_qwerty.keymap \
131+
$(srcdir)/keymaps/da_dk_qwerty.keymap \
132+
$(srcdir)/keymaps/tr_tr_qwerty.keymap
133+
134+
_generated_keymaps.c: $(spice_keymaps) $(srcdir)/keymaps/generate.pl
135+
$(AM_V_GEN) $(srcdir)/keymaps/generate.pl $(spice_keymaps)
136+
137+
EXTRA_DIST = \
138+
$(spice_keymaps) \
139+
keymaps/generate.pl

src/protocols/spice/argv.c

+53
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
/*
2+
* Licensed to the Apache Software Foundation (ASF) under one
3+
* or more contributor license agreements. See the NOTICE file
4+
* distributed with this work for additional information
5+
* regarding copyright ownership. The ASF licenses this file
6+
* to you under the Apache License, Version 2.0 (the
7+
* "License"); you may not use this file except in compliance
8+
* with the License. You may obtain a copy of the License at
9+
*
10+
* http://www.apache.org/licenses/LICENSE-2.0
11+
*
12+
* Unless required by applicable law or agreed to in writing,
13+
* software distributed under the License is distributed on an
14+
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15+
* KIND, either express or implied. See the License for the
16+
* specific language governing permissions and limitations
17+
* under the License.
18+
*/
19+
20+
#include "config.h"
21+
#include "argv.h"
22+
#include "spice.h"
23+
24+
#include <guacamole/protocol.h>
25+
#include <guacamole/socket.h>
26+
#include <guacamole/user.h>
27+
28+
#include <pthread.h>
29+
#include <stdlib.h>
30+
#include <string.h>
31+
32+
int guac_spice_argv_callback(guac_user* user, const char* mimetype,
33+
const char* name, const char* value, void* data) {
34+
35+
guac_client* client = user->client;
36+
guac_spice_client* spice_client = (guac_spice_client*) client->data;
37+
guac_spice_settings* settings = spice_client->settings;
38+
39+
/* Update username */
40+
if (strcmp(name, GUAC_SPICE_ARGV_USERNAME) == 0) {
41+
free(settings->username);
42+
settings->username = strdup(value);
43+
}
44+
45+
/* Update password */
46+
else if (strcmp(name, GUAC_SPICE_ARGV_PASSWORD) == 0) {
47+
free(settings->password);
48+
settings->password = strdup(value);
49+
}
50+
51+
return 0;
52+
53+
}

src/protocols/spice/argv.h

+47
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
/*
2+
* Licensed to the Apache Software Foundation (ASF) under one
3+
* or more contributor license agreements. See the NOTICE file
4+
* distributed with this work for additional information
5+
* regarding copyright ownership. The ASF licenses this file
6+
* to you under the Apache License, Version 2.0 (the
7+
* "License"); you may not use this file except in compliance
8+
* with the License. You may obtain a copy of the License at
9+
*
10+
* http://www.apache.org/licenses/LICENSE-2.0
11+
*
12+
* Unless required by applicable law or agreed to in writing,
13+
* software distributed under the License is distributed on an
14+
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15+
* KIND, either express or implied. See the License for the
16+
* specific language governing permissions and limitations
17+
* under the License.
18+
*/
19+
20+
#ifndef GUAC_SPICE_ARGV_H
21+
#define GUAC_SPICE_ARGV_H
22+
23+
#include "config.h"
24+
25+
#include <guacamole/argv.h>
26+
#include <guacamole/user.h>
27+
28+
/**
29+
* Handles a received argument value from a Guacamole "argv" instruction,
30+
* updating the given connection parameter.
31+
*/
32+
guac_argv_callback guac_spice_argv_callback;
33+
34+
/**
35+
* The name of the parameter Guacamole will use to specify/update the username
36+
* for the Spice connection.
37+
*/
38+
#define GUAC_SPICE_ARGV_USERNAME "username"
39+
40+
/**
41+
* The name of the parameter Guacamole will use to specify/update the password
42+
* for the Spice connection.
43+
*/
44+
#define GUAC_SPICE_ARGV_PASSWORD "password"
45+
46+
#endif /* GUAC_SPICE_ARGV_H */
47+

src/protocols/spice/auth.c

+71
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
/*
2+
* Licensed to the Apache Software Foundation (ASF) under one
3+
* or more contributor license agreements. See the NOTICE file
4+
* distributed with this work for additional information
5+
* regarding copyright ownership. The ASF licenses this file
6+
* to you under the Apache License, Version 2.0 (the
7+
* "License"); you may not use this file except in compliance
8+
* with the License. You may obtain a copy of the License at
9+
*
10+
* http://www.apache.org/licenses/LICENSE-2.0
11+
*
12+
* Unless required by applicable law or agreed to in writing,
13+
* software distributed under the License is distributed on an
14+
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15+
* KIND, either express or implied. See the License for the
16+
* specific language governing permissions and limitations
17+
* under the License.
18+
*/
19+
20+
#include "config.h"
21+
22+
#include "argv.h"
23+
#include "auth.h"
24+
#include "spice.h"
25+
26+
#include <guacamole/argv.h>
27+
#include <guacamole/client.h>
28+
#include <guacamole/protocol.h>
29+
#include <guacamole/socket.h>
30+
#include <guacamole/string.h>
31+
32+
#include <glib-unix.h>
33+
#include <pthread.h>
34+
#include <string.h>
35+
36+
gboolean guac_spice_get_credentials(guac_client* client) {
37+
38+
guac_spice_client* spice_client = ((guac_spice_client*) client->data);
39+
guac_spice_settings* settings = spice_client->settings;
40+
41+
char* params[3] = {NULL};
42+
int i = 0;
43+
44+
/* Check if username is not provided. */
45+
if (settings->username == NULL) {
46+
guac_argv_register(GUAC_SPICE_ARGV_USERNAME, guac_spice_argv_callback, NULL, 0);
47+
params[i] = GUAC_SPICE_ARGV_USERNAME;
48+
i++;
49+
}
50+
51+
/* Check if password is not provided. */
52+
if (settings->password == NULL) {
53+
guac_argv_register(GUAC_SPICE_ARGV_PASSWORD, guac_spice_argv_callback, NULL, 0);
54+
params[i] = GUAC_SPICE_ARGV_PASSWORD;
55+
i++;
56+
}
57+
58+
params[i] = NULL;
59+
60+
/* If we have empty parameters, request them and await response. */
61+
if (i > 0) {
62+
guac_client_owner_send_required(client, (const char**) params);
63+
guac_argv_await((const char**) params);
64+
return true;
65+
}
66+
67+
guac_client_log(client, GUAC_LOG_DEBUG,
68+
"Unable to retrieve any credentials from the user.");
69+
return false;
70+
71+
}

0 commit comments

Comments
 (0)