From 2345d1123fa48420bcbb68fa17b975adcc68b450 Mon Sep 17 00:00:00 2001 From: Don McCaughey Date: Thu, 8 Feb 2024 11:10:50 -0800 Subject: [PATCH] Extract common `from_ip_and_port_str()` function. Remove duplication between `sa_from_ipv4_and_port_str()` and `sa_from_ipv6_and_port_str()`. Add `copy_str()` function to encapsulate string copying details. --- TODO.md | 5 +++++ sa.c | 67 ++++++++++++++++++++++++++++++++------------------------- 2 files changed, 43 insertions(+), 29 deletions(-) create mode 100644 TODO.md diff --git a/TODO.md b/TODO.md new file mode 100644 index 0000000..9bf05d2 --- /dev/null +++ b/TODO.md @@ -0,0 +1,5 @@ +# To Do + +- consistently use str "len" (nul not included) and "size" (nul included) +- add aliases for INET_ADDRSTRLEN and INET6_ADDRSTRLEN which include nul +- consistent convention for string containing a port vs string without a port diff --git a/sa.c b/sa.c index 34ea8a6..653d8fc 100644 --- a/sa.c +++ b/sa.c @@ -10,29 +10,38 @@ static bool -split_ip_and_port_str( +copy_str(char *destination, size_t destination_size, char const *source_begin, char const *source_end) +{ + size_t source_len = source_end - source_begin; + if (source_len >= destination_size) return false; + + strncpy(destination, source_begin, source_len); + destination[source_len] = '\0'; + return true; +} + + +typedef bool from_ip_str_and_port_fn(union sa *, char const *, in_port_t); + + +static bool +from_ip_and_port_str( + union sa *address, char const *ip_and_port_str, - char *ip_str, - size_t ip_str_size, - in_port_t *port + size_t ip_str_max_len, + from_ip_str_and_port_fn from_ip_str_and_port ) { - if (!ip_and_port_str) return false; - if (ip_str_size != INET_ADDRSTRLEN && ip_str_size != INET6_ADDRSTRLEN) { - return false; - } - if (!ip_str) return false; - if (!port) return false; + // TODO: check arguments - char const *colon; - if (!sa_find_port_in_str(ip_and_port_str, port, &colon)) return false; + char const *ip_str_end; + in_port_t port; + if (!sa_find_port_in_str(ip_and_port_str, &port, &ip_str_end)) return false; - size_t ip_len = colon - ip_and_port_str; - if (ip_len >= ip_str_size) return false; + char ip_str[ip_str_max_len]; + if (!copy_str(ip_str, sizeof ip_str, ip_and_port_str, ip_str_end)) return false; - strncpy(ip_str, ip_and_port_str, ip_len); - ip_str[ip_len] = '\0'; + return from_ip_str_and_port(address, ip_str, port); - return true; } @@ -142,24 +151,24 @@ sa_from_path(union sa *address, char const *path) bool sa_from_ipv4_and_port_str(union sa *address, char const *ipv4_and_port_str) { - char ip[INET_ADDRSTRLEN]; - in_port_t port; - if (!split_ip_and_port_str(ipv4_and_port_str, ip, INET_ADDRSTRLEN, &port)) { - return false; - } - return sa_from_ipv4_str_and_port(address, ip, port); + return from_ip_and_port_str( + address, + ipv4_and_port_str, + INET_ADDRSTRLEN, + sa_from_ipv4_str_and_port + ); } bool sa_from_ipv6_and_port_str(union sa *address, char const *ipv6_and_port_str) { - char ip[INET6_ADDRSTRLEN]; - in_port_t port; - if (!split_ip_and_port_str(ipv6_and_port_str, ip, INET6_ADDRSTRLEN, &port)) { - return false; - } - return sa_from_ipv6_str_and_port(address, ip, port); + return from_ip_and_port_str( + address, + ipv6_and_port_str, + INET6_ADDRSTRLEN, + sa_from_ipv6_str_and_port + ); } -- 2.45.2