about summary refs log tree commit diff stats
diff options
context:
space:
mode:
authorRen Kararou <[email protected]>2025-01-06 17:06:05 -0600
committerRen Kararou <[email protected]>2025-01-06 17:06:05 -0600
commitb9635ce3b4ca30b14128c131bb9fe9be08740d6d (patch)
tree14e3a0d128635b70fd71bedbb6caee074ac7eda4
parent5605a5ddf3c77232b04c002a82b91e227c0f27da (diff)
downloadnbtpd-b9635ce3b4ca30b14128c131bb9fe9be08740d6d.tar.gz
nbtpd-b9635ce3b4ca30b14128c131bb9fe9be08740d6d.tar.bz2
nbtpd-b9635ce3b4ca30b14128c131bb9fe9be08740d6d.zip
start documentation efforts; cleanup handlers
socket connect in handlers, etc.
-rw-r--r--inc/handlers.h33
-rw-r--r--src/handlers.c71
-rw-r--r--src/main.c18
3 files changed, 76 insertions, 46 deletions
diff --git a/inc/handlers.h b/inc/handlers.h
index 6be05da..aecd964 100644
--- a/inc/handlers.h
+++ b/inc/handlers.h
@@ -7,6 +7,14 @@
 #define NBD_NBTPD_ARGS_PATH_MAX 768
 #define NBD_NBTPD_ARGS_MODE_MAX 32
 
+typedef enum opmode {
+	NOT_FOUND,
+	NETASCII,
+	OCTAL,
+	MAIL
+// any additional modes
+} nbd_opmode;
+
 typedef struct {
 	char path[NBD_NBTPD_ARGS_PATH_MAX];
 	char mode[NBD_NBTPD_ARGS_MODE_MAX];
@@ -14,9 +22,30 @@ typedef struct {
 	struct sockaddr_in client;
 } nbd_nbtpd_args;
 
-/// WARNING: use this only if you know what you are doing
+nbd_opmode get_mode(char *mode);
+
+
+/*!
+ *  WARNING: use this only if you know what you are doing
+ *  The actual function signature is `void read_req_resp(nbd_nbtpd_args *args)`
+ *  Invoke this function as a response to getting a new read request.
+ *  It opens a new UDP socket and reads file to transmit.
+ *  ```c
+ *  nbd_nbtpd_args *args = malloc(sizeof(nbd_nbtpd_args));
+ *  pthread_create(thread, attrs, read_req_resp, (void *)args);
+ *  ```
+ */
 void *read_req_resp(void *args);
-/// WARNING: use this only if you know what you are doing
+/*!
+ *  WARNING: use this only if you know what you are doing
+ *  The actual function signature is `void write_req_resp(nbd_nbtpd_args *args)`
+ *  Invoke this function as a response to getting a new write request.
+ *  It opens a new UDP socket, receives file to write to disk.
+ *  ```c
+ *  nbd_nbtpd_args *args = malloc(sizeof(nbd_nbtpd_args));
+ *  pthread_create(thread, attrs, write_req_resp, (void *)args);
+ *  ```
+ */
 void *write_req_resp(void *args);
 /// WARNING: use this only if you know what you are doing
 void *nbd_nbtpd_resp_error(void *args);
diff --git a/src/handlers.c b/src/handlers.c
index 10599a3..fdd16f8 100644
--- a/src/handlers.c
+++ b/src/handlers.c
@@ -6,6 +6,7 @@
 #include <stdlib.h>
 #include <stdio.h>
 #include <sys/socket.h>
+#include <arpa/inet.h>
 #include <string.h>
 #include <syslog.h>
 #include <limits.h>
@@ -19,21 +20,13 @@
 #include "packet.h"
 #include "netascii.h"
 
-typedef enum opmode {
-	NOT_FOUND,
-	NETASCII,
-	OCTAL,
-	MAIL
-// any additional modes
-} nbd_opmode;
-
 nbd_opmode get_mode(char *mode) {
 	nbd_opmode opmode;
-	if (strncmp((const char *)mode, (const char *)&"netascii", NBD_NBTPD_ARGS_MODE_MAX) == 0) {
+	if (strncmp(mode, (char *)&"netascii", NBD_NBTPD_ARGS_MODE_MAX) == 0) {
 		opmode = NETASCII;
-	} else if (strncmp((const char *)mode, (const char *)&"octal", NBD_NBTPD_ARGS_MODE_MAX) == 0) {
+	} else if (strncmp(mode, (char *)&"octal", NBD_NBTPD_ARGS_MODE_MAX) == 0) {
 		opmode = OCTAL;
-	} else if (strncmp((const char *)mode, (const char *)&"mail", NBD_NBTPD_ARGS_MODE_MAX) == 0) {
+	} else if (strncmp(mode, (char *)&"mail", NBD_NBTPD_ARGS_MODE_MAX) == 0) {
 		opmode = MAIL;
 	} else {
 		opmode = NOT_FOUND;
@@ -47,57 +40,51 @@ void *read_req_resp(void *args) {
 	nbd_nbtpd_args *argptr = (nbd_nbtpd_args *)args;
 	if (!is_netascii_str((char *)&argptr->path)) {
 		argptr->err = 1;
-		goto nbd_nbtpd_thread_read_cleanup_ps;
+		goto pre_socket;
 	}
 	fname = realpath((char *)&argptr->path, NULL);
 	if (fname == NULL) {
 		syslog(LOG_ERR, "unable to get real path: %s", strerror(errno));
 		argptr->err = 1;
-		goto nbd_nbtpd_thread_read_cleanup_ps;
+		goto pre_socket;
 	}
-	/*
-	 * POSIX does not define what happens when getcwd() is given NULL.
-	 * This means that illumos libc and GNU libc both return a newly
-	 * malloc()'d string, while FreeBSD libc does not.  Also, FreeBSD uses
-	 * constant MAXPATHLEN defined in <sys/param.h> rather than PATH_MAX.
-	 */
+/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+ * POSIX does not define what happens when getcwd() is given NULL.     *
+ * This means that illumos libc and GNU libc both return a newly       *
+ * malloc()'d string, while FreeBSD libc does not.  Also, FreeBSD uses *
+ * constant MAXPATHLEN defined in <sys/param.h> rather than PATH_MAX.  *
+ * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
 #ifdef __FreeBSD__
 	wd = malloc(MAXPATHLEN);
 	if (wd == NULL) {
 		syslog(LOG_ERR, "unable to allocate PATH_MAX memory: %s", strerror(errno));
 		argptr->err = 0;
-		goto nbd_nbtpd_thread_read_cleanup_ps;
+		goto pre_socket;
 	}
 	if (getcwd(wd, MAXPATHLEN) == NULL) {
 		argptr->err = 0;
-		goto nbd_nbtpd_thread_read_cleanup_ps;
+		goto pre_socket;
 	}
 #else
 	if ((wd = getcwd(NULL, PATH_MAX)) == NULL) {
 		argptr->err = 0;
-		goto nbd_nbtpd_thread_read_cleanup_ps;
+		goto pre_socket;
 	}
 #endif
 	if (!strncmp(wd, fname, sizeof(wd) - 1)) {
 		argptr->err = 2;
-		goto nbd_nbtpd_thread_read_cleanup_ps;
+		goto pre_socket;
 	}
 	if (!is_netascii_str((char *)&argptr->mode)) {
 		argptr->err = 4;
-		goto nbd_nbtpd_thread_read_cleanup_ps;
+		goto pre_socket;
 	}
 	nbd_opmode opmode = get_mode((char *)&argptr->mode);
-	switch (opmode) {
-		case NETASCII:
-			break;
-		case OCTAL:
-			break;
-		default:
-			argptr->err = 4;
-			goto nbd_nbtpd_thread_read_cleanup_ps;
+	if ((opmode != NETASCII) && (opmode != OCTAL)) {
+		argptr->err = 4;
+		goto pre_socket;
 	}
 	fp = fopen(fname, "r");
-
 	buf = malloc(512);
 	if (buf == NULL) {
 		syslog(
@@ -106,24 +93,34 @@ void *read_req_resp(void *args) {
 			strerror(errno)
 		);
 		argptr->err = 0;
-		goto nbd_nbtpd_thread_read_cleanup_ps;
+		goto pre_socket;
 	}
 	memset(buf, '\0', 512);
 	int s = socket(AF_INET, SOCK_DGRAM, 0);
 	if (s <= 0) {
 		syslog(LOG_ERR, "unable to define socket: %s", strerror(errno));
-		goto nbd_nbtpd_thread_read_cleanup;
+		goto cleanup;
+	}
+	if (connect(s, (struct sockaddr *)&argptr->client, sizeof(struct sockaddr)) < 0) {
+		syslog(
+			LOG_ERR,
+			"unable to connect to client %s: %s",
+			inet_ntoa(argptr->client.sin_addr),
+			strerror(errno)
+		);
+		goto socket_clean;
 	}
 
+socket_clean:
 	close(s);
-nbd_nbtpd_thread_read_cleanup:
+cleanup:
 	fclose(fp);
 	free(buf);
 	free(fname);
 	free(wd);
 	free(args);
 	return (void *)NULL;
-nbd_nbtpd_thread_read_cleanup_ps:
+pre_socket:
 	if (fp != NULL) {
 		fclose(fp);
 	}
diff --git a/src/main.c b/src/main.c
index 31d8aec..c36bc9a 100644
--- a/src/main.c
+++ b/src/main.c
@@ -176,7 +176,7 @@ int main(int argc, char **argv) {
 		if (daemon(1, 0)) {
 			syslog(LOG_ERR, "failed to daemonize: %s", strerror(errno));
 			retme = -1;
-			goto nbd_nbtpd_cleanup_main;
+			goto cleanup;
 		} else {
 			syslog(LOG_INFO, "daemonized");
 		}
@@ -185,7 +185,7 @@ int main(int argc, char **argv) {
 	if (setsockopt(s, SOL_SOCKET, SO_RCVTIMEO, &timeout, sizeof(timeout)) < 0) {
 		syslog(LOG_ERR, "unable to set socket timeout: %s", strerror(errno));
 		retme = -1;
-		goto nbd_nbtpd_cleanup_main;
+		goto cleanup;
 	}
 	struct sockaddr_in saddr;
 	saddr.sin_family = AF_INET;
@@ -194,7 +194,7 @@ int main(int argc, char **argv) {
 	if (bind(s, (struct sockaddr*)&saddr, sizeof(saddr)) < 0) {
 		syslog(LOG_ERR, "socket bind failed: %s", strerror(errno));
 		retme = -1;
-		goto nbd_nbtpd_cleanup_main;
+		goto cleanup;
 	}
 	syslog(LOG_INFO, "socket bind success");
 	if (daemonize) {
@@ -207,7 +207,7 @@ int main(int argc, char **argv) {
 				strerror(errno)
 			);
 			retme = -1;
-			goto nbd_nbtpd_cleanup_main;
+			goto cleanup;
 		}
 		struct passwd *u = getpwnam((const char *)&user);
 		if (setuid((*u).pw_uid) == -1) {
@@ -217,14 +217,17 @@ int main(int argc, char **argv) {
 				strerror(errno)
 			);
 			retme = -1;
-			goto nbd_nbtpd_cleanup_main;
+			goto cleanup;
 		}
 	}
+#ifdef __illumos__
+	//TODO: illumos priv.h privdrop
+#endif
 	buf = malloc(1024);
 	if (buf == NULL) {
 		syslog(LOG_CRIT, "unable to allocate memory: %s", strerror(errno));
 		retme = -1;
-		goto nbd_nbtpd_cleanup_main;
+		goto cleanup;
 	}
 	while (!nbtpd_stop) {
 		struct sockaddr_in caddr;
@@ -300,9 +303,10 @@ int main(int argc, char **argv) {
 			free(args);
 		}
 	}
-nbd_nbtpd_cleanup_main:
+cleanup:
 	free(buf);
 	close(s);
 	pthread_exit(NULL);
 	return retme;
 }
+