main xs_unix_socket.h
 1/* copyright (c) 2022 - 2026 grunfink et al. / MIT license */
 2
 3#ifndef _XS_UNIX_SOCKET_H
 4
 5#define _XS_UNIX_SOCKET_H
 6
 7#include "xs.h"
 8#include <unistd.h>
 9#include <sys/socket.h>
10#include <sys/types.h>
11
12 int xs_unix_socket_server(const char *path, const char *grp);
13 int xs_unix_socket_connect(const char *path);
14
15
16#ifdef XS_IMPLEMENTATION
17
18#include <sys/stat.h>
19#include <sys/un.h>
20#include <grp.h>
21
22int xs_unix_socket_server(const char *path, const char *grp)
23/* opens a unix-type server socket */
24{
25    int rs = -1;
26
27    if ((rs = socket(AF_UNIX, SOCK_STREAM, 0)) != -1) {
28        struct sockaddr_un su = {0};
29        mode_t mode = 0666;
30
31        su.sun_family = AF_UNIX;
32        strncpy(su.sun_path, path, sizeof(su.sun_path));
33
34        unlink(path);
35
36        if (bind(rs, (struct sockaddr *)&su, sizeof(su)) == -1) {
37            close(rs);
38            return -1;
39        }
40
41        listen(rs, SOMAXCONN);
42
43        if (grp != NULL) {
44            struct group *g = NULL;
45
46            /* if there is a group name, get its gid_t */
47            g = getgrnam(grp);
48
49            if (g != NULL && chown(path, -1, g->gr_gid) != -1)
50                mode = 0660;
51        }
52
53        chmod(path, mode);
54    }
55
56    return rs;
57}
58
59
60int xs_unix_socket_connect(const char *path)
61/* connects to a unix-type socket */
62{
63    int d = -1;
64
65    if ((d = socket(AF_UNIX, SOCK_STREAM, 0)) != -1) {
66        struct sockaddr_un su = {0};
67
68        su.sun_family = AF_UNIX;
69        strncpy(su.sun_path, path, sizeof(su.sun_path));
70
71        if (connect(d, (struct sockaddr *)&su, sizeof(su)) == -1) {
72            close(d);
73            d = -1;
74        }
75    }
76
77    return d;
78}
79
80
81#endif /* XS_IMPLEMENTATION */
82
83#endif /* _XS_UNIX_SOCKET_H */