• Main Page
  • Related Pages
  • Modules
  • Data Structures
  • Files
  • File List
  • Globals

src/lib/xmmsipc/socket_unix.c

Go to the documentation of this file.
00001 /*  XMMS2 - X Music Multiplexer System
00002  *  Copyright (C) 2003-2009 XMMS2 Team
00003  *
00004  *  PLUGINS ARE NOT CONSIDERED TO BE DERIVED WORK !!!
00005  *
00006  *  This library is free software; you can redistribute it and/or
00007  *  modify it under the terms of the GNU Lesser General Public
00008  *  License as published by the Free Software Foundation; either
00009  *  version 2.1 of the License, or (at your option) any later version.
00010  *
00011  *  This library is distributed in the hope that it will be useful,
00012  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
00013  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00014  *  Lesser General Public License for more details.
00015  */
00016 
00017 
00018 #include <stdio.h>
00019 #include <sys/types.h>
00020 #include <sys/socket.h>
00021 #include <unistd.h>
00022 #include <sys/un.h>
00023 #include <errno.h>
00024 #include <string.h>
00025 #include <fcntl.h>
00026 #include <unistd.h>
00027 #include <stdlib.h>
00028 #include <signal.h>
00029 #include <syslog.h>
00030 
00031 #include "xmmsc/xmmsc_ipc_transport.h"
00032 #include "xmmsc/xmmsc_util.h"
00033 #include "url.h"
00034 
00035 static void
00036 xmms_ipc_usocket_destroy (xmms_ipc_transport_t *ipct)
00037 {
00038     free (ipct->path);
00039     close (ipct->fd);
00040 }
00041 
00042 static int
00043 xmms_ipc_usocket_read (xmms_ipc_transport_t *ipct, char *buffer, int len)
00044 {
00045     int fd;
00046     int ret;
00047     x_return_val_if_fail (ipct, -1);
00048     x_return_val_if_fail (buffer, -1);
00049 
00050     fd = ipct->fd;
00051 
00052     ret =  recv (fd, buffer, len, 0);
00053 
00054     return ret;
00055 }
00056 
00057 static int
00058 xmms_ipc_usocket_write (xmms_ipc_transport_t *ipct, char *buffer, int len)
00059 {
00060     int fd;
00061     x_return_val_if_fail (ipct, -1);
00062     x_return_val_if_fail (buffer, -1);
00063 
00064     fd = ipct->fd;
00065 
00066     return send (fd, buffer, len, 0);
00067 
00068 }
00069 
00070 xmms_ipc_transport_t *
00071 xmms_ipc_usocket_client_init (const xmms_url_t *url)
00072 {
00073     int fd;
00074     int flags;
00075     xmms_ipc_transport_t *ipct;
00076     struct sockaddr_un saddr;
00077 
00078 
00079     fd = socket (AF_UNIX, SOCK_STREAM, 0);
00080     if (fd == -1) {
00081         return NULL;
00082     }
00083 
00084     saddr.sun_family = AF_UNIX;
00085     snprintf (saddr.sun_path, 108, "/%s", url->path);
00086 
00087     if (connect (fd, (struct sockaddr *) &saddr, sizeof (saddr)) == -1) {
00088         close (fd);
00089         return NULL;
00090     }
00091 
00092     flags = fcntl (fd, F_GETFL, 0);
00093 
00094     if (flags == -1) {
00095         close (fd);
00096         return NULL;
00097     }
00098 
00099     flags |= O_NONBLOCK;
00100 
00101     flags = fcntl (fd, F_SETFL, flags);
00102     if (flags == -1) {
00103         close (fd);
00104         return NULL;
00105     }
00106 
00107     ipct = x_new0 (xmms_ipc_transport_t, 1);
00108     ipct->fd = fd;
00109     ipct->path = strdup (url->path);
00110     ipct->read_func = xmms_ipc_usocket_read;
00111     ipct->write_func = xmms_ipc_usocket_write;
00112     ipct->destroy_func = xmms_ipc_usocket_destroy;
00113 
00114     return ipct;
00115 }
00116 
00117 static xmms_ipc_transport_t *
00118 xmms_ipc_usocket_accept (xmms_ipc_transport_t *transport)
00119 {
00120     int fd;
00121     struct sockaddr_un sin;
00122     socklen_t sin_len;
00123 
00124     x_return_val_if_fail (transport, NULL);
00125 
00126     sin_len = sizeof (sin);
00127 
00128     fd = accept (transport->fd, (struct sockaddr *)&sin, &sin_len);
00129     if (fd >= 0) {
00130         int flags;
00131         xmms_ipc_transport_t *ret;
00132 
00133         flags = fcntl (fd, F_GETFL, 0);
00134 
00135         if (flags == -1) {
00136             close (fd);
00137             return NULL;
00138         }
00139 
00140         flags |= O_NONBLOCK;
00141 
00142         flags = fcntl (fd, F_SETFL, flags);
00143         if (flags == -1) {
00144             close (fd);
00145             return NULL;
00146         }
00147 
00148 
00149         ret = x_new0 (xmms_ipc_transport_t, 1);
00150         ret->fd = fd;
00151         ret->read_func = xmms_ipc_usocket_read;
00152         ret->write_func = xmms_ipc_usocket_write;
00153         ret->destroy_func = xmms_ipc_usocket_destroy;
00154 
00155         return ret;
00156     }
00157 
00158     return NULL;
00159 }
00160 
00161 xmms_ipc_transport_t *
00162 xmms_ipc_usocket_server_init (const xmms_url_t *url)
00163 {
00164     int fd;
00165     int flags;
00166     xmms_ipc_transport_t *ipct;
00167     struct sockaddr_un saddr;
00168 
00169 
00170     fd = socket (AF_UNIX, SOCK_STREAM, 0);
00171     if (fd == -1) {
00172         return NULL;
00173     }
00174 
00175     saddr.sun_family = AF_UNIX;
00176     snprintf (saddr.sun_path, 108, "/%s", url->path);
00177 
00178     if (access (saddr.sun_path, F_OK) == 0) {
00179         if (connect (fd, (struct sockaddr *) &saddr, sizeof (saddr)) != -1) {
00180             /* active socket already exists! */
00181             close (fd);
00182             return NULL;
00183         }
00184         /* remove stale socket */
00185         unlink (saddr.sun_path);
00186     }
00187 
00188     if (bind (fd, (struct sockaddr *) &saddr, sizeof (saddr)) == -1) {
00189         close (fd);
00190         return NULL;
00191     }
00192 
00193     listen (fd, 5);
00194 
00195     flags = fcntl (fd, F_GETFL, 0);
00196 
00197     if (flags == -1) {
00198         close (fd);
00199         return NULL;
00200     }
00201 
00202     flags |= O_NONBLOCK;
00203 
00204     flags = fcntl (fd, F_SETFL, flags);
00205     if (flags == -1) {
00206         close (fd);
00207         return NULL;
00208     }
00209 
00210     ipct = x_new0 (xmms_ipc_transport_t, 1);
00211     ipct->fd = fd;
00212     ipct->path = strdup (url->path);
00213     ipct->read_func = xmms_ipc_usocket_read;
00214     ipct->write_func = xmms_ipc_usocket_write;
00215     ipct->accept_func = xmms_ipc_usocket_accept;
00216     ipct->destroy_func = xmms_ipc_usocket_destroy;
00217 
00218     return ipct;
00219 }
00220 

Generated on Wed Feb 9 2011 for XMMS2 by  doxygen 1.7.1