summaryrefslogtreecommitdiff
path: root/pullreqd.c
diff options
context:
space:
mode:
authormrb0nk500 <b0nk@b0nk.xyz>2021-06-10 23:20:38 -0400
committermrb0nk500 <b0nk@b0nk.xyz>2021-06-10 23:20:38 -0400
commit3b9029a94641563b9dda4f75694e499be9366d0a (patch)
tree4fce56daead45f6534a9d10d0577835be63abc77 /pullreqd.c
parentffc2fbd948d8ebb64dd917aeb679e18ecae3219b (diff)
Finished `init_socket()`.
Diffstat (limited to 'pullreqd.c')
-rw-r--r--pullreqd.c73
1 files changed, 70 insertions, 3 deletions
diff --git a/pullreqd.c b/pullreqd.c
index b3029ae..a4501c6 100644
--- a/pullreqd.c
+++ b/pullreqd.c
@@ -15,6 +15,8 @@
#include <unistd.h>
#include "config.h"
+#define UNIX_PATH_MAX 108
+
pid_t fork_proc() {
/* Fork off the parent. */
pid_t pid = fork();
@@ -91,17 +93,82 @@ int init_socket(config *cfg) {
struct sockaddr_un sa_un;
struct sockaddr_in sa_in;
} sock_addr;
+ /* Size of the socket address we're using. */
+ size_t sockaddr_size = 0;
/* Set socket type to unix socket, if socket-type was set to unix, otherwise set it to network socket. */
const int sock_type = (!strcasecmp(cfg->sock_type, "unix")) ? AF_UNIX : AF_INET;
+
+ if (sock_type == AF_UNIX) {
+ size_t path_length = strlen(cfg->sock);
+ if (path_length >= UNIX_PATH_MAX) {
+ syslog(LOG_ERR, "The socket path is too long, and exceeded %i characters.", UNIX_PATH_MAX);
+ return -1;
+ }
+
+ sockaddr_size = sizeof(sock_addr.sa_un);
+ sock_addr.sa_un.sun_family = sock_type;
+ memcpy(sock_addr.sa_un.sun_path, cfg->sock, path_length+1);
+ } else {
+ if (cfg->port <= 0 || cfg->port > 65535) {
+ syslog(LOG_ERR, "Invalid port %d. (Valid port must be between 1, and 65535.)", cfg->port);
+ return -1;
+ }
+ struct addrinfo hints, *ainfo_root, *ainfo;
+ const size_t size = sprintf(NULL, "%d", cfg->port) + 1;
+ char *port_str = malloc(size);
+
+ sprintf(port_str, "%d", cfg->port);
+ memset(&hints, 0, sizeof(hints));
+
+ hints.ai_family = AF_UNSPEC;
+ hints.ai_socktype = SOCK_SEQPACKET;
+ /*hints.ai_protocol = IPPROTO_SCTP;*/
+ hints.ai_flags = AI_PASSIVE;
+
+ const int gai_ret = getaddrinfo(cfg->sock, port_str, &hints, &ainfo_root);
+ /* Did getaddrinfo fail? */
+ if (gai_ret) {
+ syslog(LOG_ERR, "getaddrinfo() failed for hostname %s. Reason: %s", cfg->sock, gai_strerror(gai_ret));
+ return -1;
+ }
+
+ /* TODO: Create sockets for all resolved addresses, instead of just the first. */
+ sockaddr_size = ainfo_root->ai_addrlen;
+ sock_addr.sa = *ainfo_root->ai_addr;
+
+ freeaddrinfo(ainfo_root);
+ }
+
/* Create a new listen socket. */
- int fd = socket(sock_type, SOCK_SEQPACKET, 0);
+ int fd = socket(sock_addr.sa.sa_family, SOCK_SEQPACKET, 0);
- /* TODO: Add rest of init code. */
+ /* Did we fail to create the listen socket? */
+ if (fd < 0) {
+ syslog(LOG_ERR, "Failed to create listen socket.");
+ return -1;
+ }
- if (sock_type == AF_UNIX) {
+ /* Did we fail to bind the listen socket? */
+ if (bind(fd, &sock_addr.sa, sockaddr_size) < 0) {
+ syslog(LOG_ERR, "Failed to bind listen socket.");
+ return -1;
+ }
+
+ int one = 1;
+
+ /* Did we fail to enable SO_REUSEADDR? */
+ if (setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &one, sizeof(one)) < 0) {
+ syslog(LOG_ERR, "Failed to enable SO_REUSEADDR.");
+ return -1;
+ }
+ /* Did we fail to listen to the socket? */
+ if (listen(fd, 20) < 0) {
+ syslog(LOG_ERR, "Failed to listen to socket.");
+ return -1;
}
+ syslog(LOG_INFO, "Successfully created socket descriptor %i for address %s.", fd, cfg->sock);
return fd;
}