diff options
author | Ren Kararou <[email protected]> | 2025-01-06 17:06:05 -0600 |
---|---|---|
committer | Ren Kararou <[email protected]> | 2025-01-06 17:06:05 -0600 |
commit | b9635ce3b4ca30b14128c131bb9fe9be08740d6d (patch) | |
tree | 14e3a0d128635b70fd71bedbb6caee074ac7eda4 | |
parent | 5605a5ddf3c77232b04c002a82b91e227c0f27da (diff) | |
download | nbtpd-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.h | 33 | ||||
-rw-r--r-- | src/handlers.c | 71 | ||||
-rw-r--r-- | src/main.c | 18 |
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; } + |