Commit 0adea730 authored by Laurent Bigonville's avatar Laurent Bigonville

Update upstream source from tag 'upstream/0.18.0'

Update to upstream version '0.18.0'
with Debian dir 7c28a35f9676cbe5b5f21a7bbfab85a1b03e7e43
parents ef168c8c 392198b7
spice-vdagent
spice-vdagentd
*.o
*~
.pc
Makefile.in
aclocal.m4
compile
configure
depcomp
missing
......@@ -4,46 +4,89 @@ NULL =
bin_PROGRAMS = src/spice-vdagent
sbin_PROGRAMS = src/spice-vdagentd
src_spice_vdagent_CFLAGS = $(X_CFLAGS) $(SPICE_CFLAGS) $(GLIB2_CFLAGS) $(ALSA_CFLAGS) -DUDSCS_NO_SERVER
src_spice_vdagent_LDADD = $(X_LIBS) $(SPICE_LIBS) $(GLIB2_LIBS) $(ALSA_LIBS)
src_spice_vdagent_SOURCES = src/vdagent.c \
src/vdagent-x11.c \
src/vdagent-x11-randr.c \
src/vdagent-file-xfers.c \
src/vdagent-audio.c \
src/udscs.c
src_spice_vdagentd_CFLAGS = $(DBUS_CFLAGS) $(LIBSYSTEMD_LOGIN_CFLAGS) \
$(PCIACCESS_CFLAGS) $(SPICE_CFLAGS) $(GLIB2_CFLAGS) $(PIE_CFLAGS)
src_spice_vdagentd_LDADD = $(DBUS_LIBS) $(LIBSYSTEMD_LOGIN_LIBS) \
$(PCIACCESS_LIBS) $(SPICE_LIBS) $(GLIB2_LIBS) $(PIE_LDFLAGS)
src_spice_vdagentd_SOURCES = src/vdagentd.c \
src/vdagentd-uinput.c \
src/vdagentd-xorg-conf.c \
src/vdagent-virtio-port.c \
src/udscs.c
common_sources = \
src/udscs.c \
src/udscs.h \
src/vdagentd-proto-strings.h \
src/vdagentd-proto.h \
$(NULL)
src_spice_vdagent_CFLAGS = \
$(X_CFLAGS) \
$(SPICE_CFLAGS) \
$(GLIB2_CFLAGS) \
$(GTK_CFLAGS) \
$(ALSA_CFLAGS) \
-I$(srcdir)/src \
-DUDSCS_NO_SERVER \
$(NULL)
src_spice_vdagent_LDADD = \
$(X_LIBS) \
$(SPICE_LIBS) \
$(GLIB2_LIBS) \
$(GTK_LIBS) \
$(ALSA_LIBS) \
$(NULL)
src_spice_vdagent_SOURCES = \
$(common_sources) \
src/vdagent/audio.c \
src/vdagent/audio.h \
src/vdagent/clipboard.c \
src/vdagent/clipboard.h \
src/vdagent/file-xfers.c \
src/vdagent/file-xfers.h \
src/vdagent/x11-priv.h \
src/vdagent/x11-randr.c \
src/vdagent/x11.c \
src/vdagent/x11.h \
src/vdagent/vdagent.c \
$(NULL)
src_spice_vdagentd_CFLAGS = \
$(DBUS_CFLAGS) \
$(LIBSYSTEMD_DAEMON_CFLAGS) \
$(LIBSYSTEMD_LOGIN_CFLAGS) \
$(PCIACCESS_CFLAGS) \
$(SPICE_CFLAGS) \
$(GLIB2_CFLAGS) \
$(PIE_CFLAGS) \
-I$(srcdir)/src \
$(NULL)
src_spice_vdagentd_LDADD = \
$(DBUS_LIBS) \
$(LIBSYSTEMD_DAEMON_LIBS) \
$(LIBSYSTEMD_LOGIN_LIBS) \
$(PCIACCESS_LIBS) \
$(SPICE_LIBS) \
$(GLIB2_LIBS) \
$(PIE_LDFLAGS) \
$(NULL)
src_spice_vdagentd_SOURCES = \
$(common_sources) \
src/vdagentd/vdagentd.c \
src/vdagentd/session-info.h \
src/vdagentd/uinput.c \
src/vdagentd/uinput.h \
src/vdagentd/xorg-conf.c \
src/vdagentd/xorg-conf.h \
src/vdagentd/virtio-port.c \
src/vdagentd/virtio-port.h \
$(NULL)
if HAVE_CONSOLE_KIT
src_spice_vdagentd_SOURCES += src/console-kit.c
src_spice_vdagentd_SOURCES += src/vdagentd/console-kit.c
else
if HAVE_LIBSYSTEMD_LOGIN
src_spice_vdagentd_SOURCES += src/systemd-login.c
src_spice_vdagentd_SOURCES += src/vdagentd/systemd-login.c
else
src_spice_vdagentd_SOURCES += src/dummy-session-info.c
src_spice_vdagentd_SOURCES += src/vdagentd/dummy-session-info.c
endif
endif
noinst_HEADERS = src/session-info.h \
src/udscs.h \
src/vdagent-audio.h \
src/vdagent-file-xfers.h \
src/vdagent-virtio-port.h \
src/vdagent-x11.h \
src/vdagent-x11-priv.h \
src/vdagentd-proto.h \
src/vdagentd-proto-strings.h \
src/vdagentd-uinput.h \
src/vdagentd-xorg-conf.h
xdgautostartdir = $(sysconfdir)/xdg/autostart
xdgautostart_DATA = $(top_srcdir)/data/spice-vdagent.desktop
......@@ -65,9 +108,9 @@ if INIT_SCRIPT_SYSTEMD
systemdunitdir = $(SYSTEMDSYSTEMUNITDIR)
systemdunit_DATA = \
$(top_srcdir)/data/spice-vdagentd.service \
$(top_srcdir)/data/spice-vdagentd.target
$(top_srcdir)/data/spice-vdagentd.socket
udevrulesdir = /lib/udev/rules.d
udevrulesdir = $(udevdir)/rules.d
udevrules_DATA = $(top_srcdir)/data/70-spice-vdagentd.rules
tmpfilesdir = $(prefix)/lib/tmpfiles.d
......@@ -75,17 +118,18 @@ tmpfiles_DATA = $(top_srcdir)/data/tmpfiles.d/spice-vdagentd.conf
endif
manpagedir = $(mandir)/man1
manpage_DATA = data/spice-vdagent.1 \
data/spice-vdagentd.1
manpage_DATA = \
data/spice-vdagent.1 \
data/spice-vdagentd.1 \
$(NULL)
EXTRA_DIST = \
NEWS \
README.RHEL-5 \
data/70-spice-vdagentd.rules \
data/spice-vdagent.desktop \
data/spice-vdagentd \
data/spice-vdagentd.service \
data/spice-vdagentd.target \
data/spice-vdagentd.socket \
data/tmpfiles.d/spice-vdagentd.conf \
data/xorg.conf.RHEL-5 \
$(NULL)
......
This diff is collapsed.
Overview of changes in SPICE vdagent 0.18.0
===========================================
- Add GTK+ framework to handle x11 backend such as clipboard
- Deprecate X11 backend in favor of GTK+ framework
- Ask pkg-config to appropriate directory to install udev rules
- Fix leak of udscs's file descriptor
- Better quote directory path when calling xdg-open to save file transfer
- Bump GLib to 2.34
- Add systemd socket activation (rhbz#1340160)
- Add support to detailed errors on file transfers
- Add check for available free space in guest before starting a file transfer
- Use better names for duplicated files on file transfer
- Improve support on big endian guests (#5)
- Use IdleHint to check if a session is locked over console-kit (rhbz#1412673)
- Fixes double free on errors over udscs by improving memory ownership
- Hide autostart file on Unity
- Improve command line messages for vdagentd
- Fix typo in --enable-static-uinput configure option
- Code repository moved to gitlab.freedesktop.org
Overview of changes in SPICE vdagent 0.17.0
===========================================
......
......@@ -20,12 +20,12 @@ Features:
* Automatic adjustment of the X-session resolution to the client resolution
* Support of copy and paste (text and images) between the active X-session
and the client. This supports both the primary selection and the clipboard.
* Support for transfering files from the client to the agent
* Support for transferring files from the client to the agent
* Full support for multiple displays using Xrandr, this requires a new
enough xorg-x11-drv-qxl driver, as well as a new enough host.
* Limited support for multiple displays using Xinerama, prerequisites:
* A new enough Xorg-server. For Fedora atleast Fedora-17, for RHEL-6 atleast
xorg-x11-server-1.10.4-6.el6_2.3
* A new enough Xorg server: Fedora 17 or greater, for RHEL 6
xorg-x11-server-1.10.4-6.el6_2.3 or greater.
* A vm configured with multiple qxl devices
* A guest running the latest spice-vdagent
Then connect to the vm with the multiple monitor client which you want to
......
spice-vdagent and RHEL-5 README
-------------------------------
spice-vdagent can also be used inside RHEL-5 guests, if, and only if, they
are hosted on a host which uses virtio-serial as the agent channel. Note
that older hosts, such as qemu shipped with RHEL-5 for example, use
a custom pci device (the spicevmc device) for the agent channel and
there is no Linux support for this device so spice-vdagent does not work
inside guests hosted on such hosts! Hosts based on RHEL-6 or Fedora 15
and newer for example, are fine.
spice-vdagent relies on ConsoleKit to determine the active session, since
RHEL-5 has no ConsoleKit it cannot do this on RHEL-5, therefor only 1
active X-session is supported with RHEL-5. If you try to start multiple
sessions by running multiple X-servers the agent will disable itself.
Since the RHEL-5 X-server does not support hotplugging of input devices,
spice-vdagentd must be started before the X-server, so that it can create
the uinput tablet device it uses for agent mouse mode.
This also means that you must use a customized xorg.conf to teach the
X-server about the uinput device. An example xorg.conf is included with
spice-vdagent. After installing spice-vdagent, first start spice-vdagentd,
and then copy this file to /etc/X11/xorg.conf and restart your X-server.
Note: the sample xorg.conf assumes that the vm has been configured to *not*
use a usb tablet device, since there is no need for one with the agent and
usb emulation takes a significant amount of CPU.
Building from source for RHEL-5
-------------------------------
If you're building spice-vdagent from source on RHEL-5, you must pass
--disable-console-kit --enable-static-uinput to ./configure!
This diff is collapsed.
#! /bin/sh
#!/bin/sh
# Wrapper for compilers which do not understand '-c -o'.
scriptversion=2012-10-14.11; # UTC
scriptversion=2016-01-11.22; # UTC
# Copyright (C) 1999-2014 Free Software Foundation, Inc.
# Copyright (C) 1999-2017 Free Software Foundation, Inc.
# Written by Tom Tromey <tromey@cygnus.com>.
#
# This program is free software; you can redistribute it and/or modify
......@@ -255,7 +255,8 @@ EOF
echo "compile $scriptversion"
exit $?
;;
cl | *[/\\]cl | cl.exe | *[/\\]cl.exe )
cl | *[/\\]cl | cl.exe | *[/\\]cl.exe | \
icl | *[/\\]icl | icl.exe | *[/\\]icl.exe )
func_cl_wrapper "$@" # Doesn't return...
;;
esac
......@@ -342,6 +343,6 @@ exit $ret
# eval: (add-hook 'write-file-hooks 'time-stamp)
# time-stamp-start: "scriptversion="
# time-stamp-format: "%:y-%02m-%02d.%02H"
# time-stamp-time-zone: "UTC"
# time-stamp-time-zone: "UTC0"
# time-stamp-end: "; # UTC"
# End:
This diff is collapsed.
AC_PREREQ(2.59)
AC_INIT([spice-vdagent], [0.17.0])
AC_INIT([spice-vdagent], [0.18.0])
AC_CONFIG_SRCDIR([configure.ac])
AM_CONFIG_HEADER([src/config.h])
......@@ -65,6 +65,29 @@ AC_MSG_RESULT($with_init_script)
if test "x$init_systemd" = "xyes"; then
SYSTEMDSYSTEMUNITDIR=`${PKG_CONFIG} systemd --variable=systemdsystemunitdir`
AC_SUBST(SYSTEMDSYSTEMUNITDIR)
# earlier versions of systemd require a separate libsystemd-daemon library
PKG_CHECK_MODULES([LIBSYSTEMD_DAEMON],
[libsystemd >= 209],
[have_libsystemd_daemon="yes"],
[have_libsystemd_daemon="no"])
if test "$have_libsystemd_daemon" = "yes"; then
AC_DEFINE([WITH_SYSTEMD_SOCKET_ACTIVATION], [1], [If defined, vdagentd will support socket activation with systemd] )
fi
fi
AC_ARG_WITH([gtk],
[AS_HELP_STRING(
[--with-gtk=@<:@auto/yes/no@:>@],
[Use GTK+ instead of Xlib @<:@default=auto@:>@])],
[],
[with_gtk="auto"])
if test "x$with_gtk" != "xno"; then
PKG_CHECK_MODULES([GTK], [gtk+-3.0 >= 3.10], [
AC_DEFINE([WITH_GTK], [1], [If defined, vdagent will favor GTK+ over Xlib])
with_gtk="yes"
], [
AS_IF([test "x$with_gtk" = "xyes"], [AC_MSG_ERROR([GTK+ requested but not found])])
with_gtk="no"])
fi
AC_ARG_ENABLE([pciaccess],
......@@ -73,13 +96,13 @@ AC_ARG_ENABLE([pciaccess],
[enable_pciaccess="yes"])
AC_ARG_ENABLE([static-uinput],
[AS_HELP_STRING([--enable-statis-uinput], [Enable use of a fixed, static uinput device for X-servers without hotplug support (default: no)])],
[AS_HELP_STRING([--enable-static-uinput], [Enable use of a fixed, static uinput device for X-servers without hotplug support (default: no)])],
[enable_static_uinput="$enableval"],
[enable_static_uinput="no"])
PKG_CHECK_MODULES([GLIB2], [glib-2.0 >= 2.28])
PKG_CHECK_MODULES([GLIB2], [glib-2.0 >= 2.34])
PKG_CHECK_MODULES(X, [xfixes xrandr >= 1.3 xinerama x11])
PKG_CHECK_MODULES(SPICE, [spice-protocol >= 0.12.8])
PKG_CHECK_MODULES(SPICE, [spice-protocol >= 0.12.13])
PKG_CHECK_MODULES(ALSA, [alsa >= 1.0.22])
PKG_CHECK_MODULES([DBUS], [dbus-1])
......@@ -107,6 +130,10 @@ else
fi
AM_CONDITIONAL(HAVE_LIBSYSTEMD_LOGIN, test x"$have_libsystemd_login" = "xyes")
#udevdir
udevdir=$($PKG_CONFIG --variable=udevdir udev)
AC_SUBST(udevdir)
if test "$with_session_info" = "auto" || test "$with_session_info" = "console-kit"; then
AC_DEFINE([HAVE_CONSOLE_KIT], [1], [If defined, vdagentd will be compiled with ConsoleKit support])
have_console_kit="yes"
......@@ -195,6 +222,9 @@ AC_MSG_NOTICE([
install RH initscript: ${init_redhat}
install systemd service: ${init_systemd}
udevdir: ${udevdir}
use GTK+: ${with_gtk}
Now type 'make' to build $PACKAGE
......
ACTION=="add", SUBSYSTEM=="virtio-ports", ENV{DEVLINKS}=="/dev/virtio-ports/com.redhat.spice.0", ENV{SYSTEMD_WANTS}="spice-vdagentd.target"
ACTION=="add", SUBSYSTEM=="virtio-ports", ENV{DEVLINKS}=="/dev/virtio-ports/com.redhat.spice.0", ENV{SYSTEMD_WANTS}="spice-vdagentd.socket"
......@@ -21,7 +21,7 @@ resolution, to the number of client windows and their resolution
Support of copy and paste (text and images) between the active X11 session
and the client, this supports both the primary selection and the clipboard
.P
Support for transfering files from the client to the agent
Support for transferring files from the client to the agent
.SH OPTIONS
.TP
\fB-h\fP
......
......@@ -6,3 +6,4 @@ Terminal=false
Type=Application
Categories=
X-GNOME-Autostart-Phase=Initialization
NoDisplay=true
......@@ -20,7 +20,7 @@ resolution, to the number of client windows and their resolution
Support of copy and paste (text and images) between the active X11 session
and the client, this supports both the primary selection and the clipboard
.P
Support for transfering files from the client to the agent
Support for transferring files from the client to the agent
.SH OPTIONS
.TP
\fB-h\fP
......
[Unit]
Description=Agent daemon for Spice guests
After=dbus.target
# TODO we should use:
#Requires=spice-vdagentd.socket
Requires=spice-vdagentd.socket
[Service]
Type=forking
EnvironmentFile=-/etc/sysconfig/spice-vdagentd
ExecStartPre=/bin/rm -f /var/run/spice-vdagentd/spice-vdagent-sock
ExecStart=/usr/sbin/spice-vdagentd $SPICE_VDAGENTD_EXTRA_ARGS
PIDFile=/var/run/spice-vdagentd/spice-vdagentd.pid
PrivateTmp=true
Restart=on-failure
[Install]
WantedBy=spice-vdagentd.target
Also=spice-vdagentd.socket
[Unit]
Description=Activation socket for spice guest agent daemon
# only start the socket if the virtio port device exists
Requisite=dev-virtio\x2dports-com.redhat.spice.0.device
[Socket]
ListenStream=/var/run/spice-vdagentd/spice-vdagent-sock
[Install]
WantedBy=sockets.target
[Unit]
Description=Agent daemon for Spice guests
#! /bin/sh
#!/bin/sh
# depcomp - compile a program generating dependencies as side-effects
scriptversion=2013-05-30.07; # UTC
scriptversion=2016-01-11.22; # UTC
# Copyright (C) 1999-2014 Free Software Foundation, Inc.
# Copyright (C) 1999-2017 Free Software Foundation, Inc.
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
......@@ -786,6 +786,6 @@ exit 0
# eval: (add-hook 'write-file-hooks 'time-stamp)
# time-stamp-start: "scriptversion="
# time-stamp-format: "%:y-%02m-%02d.%02H"
# time-stamp-time-zone: "UTC"
# time-stamp-time-zone: "UTC0"
# time-stamp-end: "; # UTC"
# End:
#!/bin/sh
# install - install a program, script, or datafile
scriptversion=2013-12-25.23; # UTC
scriptversion=2016-01-11.22; # UTC
# This originates from X11R5 (mit/util/scripts/install.sh), which was
# later released in X11R6 (xc/config/util/install.sh) with the
......@@ -496,6 +496,6 @@ done
# eval: (add-hook 'write-file-hooks 'time-stamp)
# time-stamp-start: "scriptversion="
# time-stamp-format: "%:y-%02m-%02d.%02H"
# time-stamp-time-zone: "UTC"
# time-stamp-time-zone: "UTC0"
# time-stamp-end: "; # UTC"
# End:
#! /bin/sh
#!/bin/sh
# Common wrapper for a few potentially missing GNU programs.
scriptversion=2013-10-28.13; # UTC
scriptversion=2016-01-11.22; # UTC
# Copyright (C) 1996-2014 Free Software Foundation, Inc.
# Copyright (C) 1996-2017 Free Software Foundation, Inc.
# Originally written by Fran,cois Pinard <pinard@iro.umontreal.ca>, 1996.
# This program is free software; you can redistribute it and/or modify
......@@ -210,6 +210,6 @@ exit $st
# eval: (add-hook 'write-file-hooks 'time-stamp)
# time-stamp-start: "scriptversion="
# time-stamp-format: "%:y-%02m-%02d.%02H"
# time-stamp-time-zone: "UTC"
# time-stamp-time-zone: "UTC0"
# time-stamp-end: "; # UTC"
# End:
......@@ -36,9 +36,15 @@
/* Version number of package */
#undef VERSION
/* If defined, vdagent will favor GTK+ over Xlib */
#undef WITH_GTK
/* If defined, vdagentd will use a static uinput device */
#undef WITH_STATIC_UINPUT
/* If defined, vdagentd will support socket activation with systemd */
#undef WITH_SYSTEMD_SOCKET_ACTIVATION
/* Enable large inode numbers on Mac OS X 10.5. */
#ifndef _DARWIN_USE_64_BIT_INODE
# define _DARWIN_USE_64_BIT_INODE 1
......
......@@ -31,6 +31,8 @@
#include <errno.h>
#include <sys/socket.h>
#include <sys/un.h>
#include <glib.h>
#include <glib-unix.h>
#include "udscs.h"
struct udscs_buf {
......@@ -66,8 +68,16 @@ struct udscs_connection {
struct udscs_connection *next;
struct udscs_connection *prev;
GIOChannel *io_channel;
guint write_watch_id;
guint read_watch_id;
};
static gboolean udscs_io_channel_cb(GIOChannel *source,
GIOCondition condition,
gpointer data);
struct udscs_connection *udscs_connect(const char *socketname,
udscs_read_callback read_callback,
udscs_disconnect_callback disconnect_callback,
......@@ -103,6 +113,17 @@ struct udscs_connection *udscs_connect(const char *socketname,
return NULL;
}
conn->io_channel = g_io_channel_unix_new(conn->fd);
if (!conn->io_channel) {
udscs_destroy_connection(&conn);
return NULL;
}
conn->read_watch_id =
g_io_add_watch(conn->io_channel,
G_IO_IN | G_IO_ERR | G_IO_NVAL,
udscs_io_channel_cb,
conn);
conn->read_callback = read_callback;
conn->disconnect_callback = disconnect_callback;
......@@ -132,6 +153,7 @@ void udscs_destroy_connection(struct udscs_connection **connp)
}
free(conn->data.buf);
conn->data.buf = NULL;
if (conn->next)
conn->next->prev = conn->prev;
......@@ -140,6 +162,12 @@ void udscs_destroy_connection(struct udscs_connection **connp)
close(conn->fd);
if (conn->write_watch_id != 0)
g_source_remove(conn->write_watch_id);
if (conn->read_watch_id != 0)
g_source_remove(conn->read_watch_id);
g_clear_pointer(&conn->io_channel, g_io_channel_unref);
if (conn->debug)
syslog(LOG_DEBUG, "%p disconnected", conn);
......@@ -197,6 +225,13 @@ int udscs_write(struct udscs_connection *conn, uint32_t type, uint32_t arg1,
conn, type, arg1, arg2, size);
}
if (conn->io_channel && conn->write_watch_id == 0)
conn->write_watch_id =
g_io_add_watch(conn->io_channel,
G_IO_OUT | G_IO_ERR | G_IO_NVAL,
udscs_io_channel_cb,
conn);
if (!conn->write_buf) {
conn->write_buf = new_wbuf;
return 0;
......@@ -236,11 +271,11 @@ static void udscs_read_complete(struct udscs_connection **connp)
return;
}
free(conn->data.buf);
memset(&conn->data, 0, sizeof(conn->data)); /* data.buf = NULL */
conn->header_read = 0;
memset(&conn->data, 0, sizeof(conn->data));
}
/* A helper for udscs_client_handle_fds() */
static void udscs_do_read(struct udscs_connection **connp)
{
ssize_t n;
......@@ -291,7 +326,6 @@ static void udscs_do_read(struct udscs_connection **connp)
}
}
/* A helper for udscs_client_handle_fds() */
static void udscs_do_write(struct udscs_connection **connp)
{
ssize_t n;
......@@ -325,30 +359,30 @@ static void udscs_do_write(struct udscs_connection **connp)
}
}
void udscs_client_handle_fds(struct udscs_connection **connp, fd_set *readfds,
fd_set *writefds)
{
if (!*connp)
return;
if (FD_ISSET((*connp)->fd, readfds))
udscs_do_read(connp);
if (*connp && FD_ISSET((*connp)->fd, writefds))
udscs_do_write(connp);
}
int udscs_client_fill_fds(struct udscs_connection *conn, fd_set *readfds,
fd_set *writefds)
static gboolean udscs_io_channel_cb(GIOChannel *source,
GIOCondition condition,
gpointer data)
{
if (!conn)
return -1;
struct udscs_connection *conn = data;
FD_SET(conn->fd, readfds);
if (conn->write_buf)
FD_SET(conn->fd, writefds);
if (condition & G_IO_IN) {
udscs_do_read(&conn);
if (conn == NULL)
return G_SOURCE_REMOVE;
return G_SOURCE_CONTINUE;
}
if (condition & G_IO_OUT) {
udscs_do_write(&conn);
if (conn == NULL)
return G_SOURCE_REMOVE;
if (conn->write_buf)
return G_SOURCE_CONTINUE;
conn->write_watch_id = 0;
return G_SOURCE_REMOVE;
}
return conn->fd + 1;
udscs_destroy_connection(&conn);
return G_SOURCE_REMOVE;
}
......@@ -367,16 +401,19 @@ struct udscs_server {
udscs_disconnect_callback disconnect_callback;
};
struct udscs_server *udscs_create_server(const char *socketname,
struct udscs_server *udscs_create_server_for_fd(int fd,
udscs_connect_callback connect_callback,
udscs_read_callback read_callback,
udscs_disconnect_callback disconnect_callback,
const char * const type_to_string[], int no_types, int debug)
{
int c;
struct sockaddr_un address;
struct udscs_server *server;
if (fd <= 0) {
syslog(LOG_ERR, "Invalid file descriptor: %i", fd);
return NULL;
}
server = calloc(1, sizeof(*server));
if (!server)
return NULL;
......@@ -384,33 +421,54 @@ struct udscs_server *udscs_create_server(const char *socketname,
server->type_to_string = type_to_string;
server->no_types = no_types;
server->debug = debug;
server->fd = fd;
server->connect_callback = connect_callback;
server->read_callback = read_callback;
server->disconnect_callback = disconnect_callback;
return server;
}
struct udscs_server *udscs_create_server(const char *socketname,
udscs_connect_callback connect_callback,
udscs_read_callback read_callback,
udscs_disconnect_callback disconnect_callback,
const char * const type_to_string[], int no_types, int debug)
{
int c;
int fd;
struct sockaddr_un address;
struct udscs_server *server;
server->fd = socket(PF_UNIX, SOCK_STREAM, 0);
if (server->fd == -1) {
fd = socket(PF_UNIX, SOCK_STREAM, 0);
if (fd == -1) {
syslog(LOG_ERR, "creating unix domain socket: %m");
free(server);
return NULL;
}
address.sun_family = AF_UNIX;
snprintf(address.sun_path, sizeof(address.sun_path), "%s", socketname);
c = bind(server->fd, (struct sockaddr *)&address, sizeof(address));
c = bind(fd, (struct sockaddr *)&address, sizeof(address));
if (c != 0) {
syslog(LOG_ERR, "bind %s: %m", socketname);
free(server);
close(fd);
return NULL;
}
c = listen(server->fd, 5);
c = listen(fd, 5);
if (c != 0) {
syslog(LOG_ERR, "listen: %m");
free(server);
close(fd);
return NULL;
}
server->connect_callback = connect_callback;
server->read_callback = read_callback;
server->disconnect_callback = disconnect_callback;
server = udscs_create_server_for_fd(fd, connect_callback, read_callback,
disconnect_callback, type_to_string,
no_types, debug);
if (!server) {
close(fd);
}
return server;
}
......@@ -493,18 +551,22 @@ int udscs_server_fill_fds(struct udscs_server *server, fd_set *readfds,
fd_set *writefds)
{
struct udscs_connection *conn;
int nfds = server->fd + 1;
int nfds;
if (!server)
return -1;
nfds = server->fd + 1;
FD_SET(server->fd, readfds);
conn = server->connections_head.next;
while (conn) {
int conn_nfds = udscs_client_fill_fds(conn, readfds, writefds);
if (conn_nfds > nfds)
nfds = conn_nfds;
FD_SET(conn->fd, readfds);
if (conn->write_buf)
FD_SET(conn->fd, writefds);
if (conn->fd >= nfds)
nfds = conn->fd + 1;
conn = conn->next;
}
......@@ -525,10 +587,15 @@ void udscs_server_handle_fds(struct udscs_server *server, fd_set *readfds,
conn = server->connections_head.next;
while (conn) {
/* conn maybe destroyed by udscs_client_handle_fds (when disconnected),
so get the next connection first. */
/* conn may be destroyed by udscs_do_read() or udscs_do_write()
* (when disconnected), so get the next connection first. */