[tarantool-patches] [PATCH 3/5] sio: return 'no host' flag from sio_uri_to_addr()
Vladislav Shpilevoy
v.shpilevoy at tarantool.org
Wed May 1 01:31:25 MSK 2019
Results of sio_uri_to_addr("0.0.0.0:port") and
sio_uri_to_addr("port") are indistinguishable - both fill
sockaddr_in.sin_addr as INADDR_ANY. But SWIM wants to forbid the
former, and allow the latter. In case if only port is specified,
host will be 'localhost'.
This commit returns a flag from sio_uri_to_addr() signaling if a
host was specified.
---
src/lib/core/sio.c | 3 ++-
src/lib/core/sio.h | 2 +-
src/lib/swim/swim.c | 4 +++-
test/unit/sio.c | 29 ++++++++++++++++++++---------
test/unit/sio.result | 32 ++++++++++++++++++--------------
5 files changed, 44 insertions(+), 26 deletions(-)
diff --git a/src/lib/core/sio.c b/src/lib/core/sio.c
index 28aef1d6c..97a512eee 100644
--- a/src/lib/core/sio.c
+++ b/src/lib/core/sio.c
@@ -344,11 +344,12 @@ sio_strfaddr(const struct sockaddr *addr, socklen_t addrlen)
}
int
-sio_uri_to_addr(const char *uri, struct sockaddr *addr)
+sio_uri_to_addr(const char *uri, struct sockaddr *addr, bool *is_host_empty)
{
struct uri u;
if (uri_parse(&u, uri) != 0 || u.service == NULL)
goto invalid_uri;
+ *is_host_empty = u.host_len == 0;
if (u.host_len == strlen(URI_HOST_UNIX) &&
memcmp(u.host, URI_HOST_UNIX, u.host_len) == 0) {
struct sockaddr_un *un = (struct sockaddr_un *) addr;
diff --git a/src/lib/core/sio.h b/src/lib/core/sio.h
index 093b5f5ba..db2e3281f 100644
--- a/src/lib/core/sio.h
+++ b/src/lib/core/sio.h
@@ -223,7 +223,7 @@ ssize_t sio_recvfrom(int fd, void *buf, size_t len, int flags,
* sockaddr_in/un structure.
*/
int
-sio_uri_to_addr(const char *uri, struct sockaddr *addr);
+sio_uri_to_addr(const char *uri, struct sockaddr *addr, bool *is_host_empty);
#if defined(__cplusplus)
} /* extern "C" */
diff --git a/src/lib/swim/swim.c b/src/lib/swim/swim.c
index 941214289..22dfc3d2a 100644
--- a/src/lib/swim/swim.c
+++ b/src/lib/swim/swim.c
@@ -1686,7 +1686,9 @@ swim_uri_to_addr(const char *uri, struct sockaddr_in *addr,
const char *prefix)
{
struct sockaddr_storage storage;
- if (sio_uri_to_addr(uri, (struct sockaddr *) &storage) != 0)
+ bool is_host_empty;
+ if (sio_uri_to_addr(uri, (struct sockaddr *) &storage,
+ &is_host_empty) != 0)
return -1;
if (storage.ss_family != AF_INET) {
diag_set(IllegalParams, "%s only IP sockets are supported",
diff --git a/test/unit/sio.c b/test/unit/sio.c
index dffdd5592..4ded96f4a 100644
--- a/test/unit/sio.c
+++ b/test/unit/sio.c
@@ -39,40 +39,49 @@ static void
check_uri_to_addr(void)
{
header();
- plan(18);
+ plan(22);
+ bool is_host_empty;
struct sockaddr_storage storage;
struct sockaddr *addr = (struct sockaddr *) &storage;
struct sockaddr_un *un = (struct sockaddr_un *) addr;
struct sockaddr_in *in = (struct sockaddr_in *) addr;
- isnt(0, sio_uri_to_addr("invalid uri", addr),
+ isnt(0, sio_uri_to_addr("invalid uri", addr, &is_host_empty),
"invalid uri is detected");
char long_path[1000];
char *pos = long_path + sprintf(long_path, "unix/:/");
memset(pos, 'a', 900);
pos[900] = 0;
- isnt(0, sio_uri_to_addr(long_path, addr), "too long UNIX path");
+ isnt(0, sio_uri_to_addr(long_path, addr, &is_host_empty),
+ "too long UNIX path");
- is(0, sio_uri_to_addr("unix/:/normal_path", addr), "UNIX");
+ is(0, sio_uri_to_addr("unix/:/normal_path", addr, &is_host_empty),
+ "UNIX");
is(0, strcmp(un->sun_path, "/normal_path"), "UNIX path");
is(AF_UNIX, un->sun_family, "UNIX family");
+ ok(! is_host_empty, "unix host is not empty");
- is(0, sio_uri_to_addr("localhost:1234", addr), "localhost");
+ is(0, sio_uri_to_addr("localhost:1234", addr, &is_host_empty),
+ "localhost");
is(AF_INET, in->sin_family, "localhost family");
is(htonl(INADDR_LOOPBACK), in->sin_addr.s_addr, "localhost address");
is(htons(1234), in->sin_port, "localhost port");
+ ok(! is_host_empty, "'localhost' host is not empty");
- is(0, sio_uri_to_addr("5678", addr), "'any'");
+ is(0, sio_uri_to_addr("5678", addr, &is_host_empty), "'any'");
is(AF_INET, in->sin_family, "'any' family");
is(htonl(INADDR_ANY), in->sin_addr.s_addr, "'any' address");
is(htons(5678), in->sin_port, "'any' port");
+ ok(is_host_empty, "only port specified - host is empty");
- is(0, sio_uri_to_addr("192.168.0.1:9101", addr), "IP");
+ is(0, sio_uri_to_addr("192.168.0.1:9101", addr, &is_host_empty), "IP");
is(AF_INET, in->sin_family, "IP family");
is(inet_addr("192.168.0.1"), in->sin_addr.s_addr, "IP address");
is(htons(9101), in->sin_port, "IP port");
+ ok(! is_host_empty, "IPv4 host is not empty");
- isnt(0, sio_uri_to_addr("192.168.0.300:1112", addr), "invalid IP");
+ isnt(0, sio_uri_to_addr("192.168.0.300:1112", addr, &is_host_empty),
+ "invalid IP");
check_plan();
footer();
@@ -84,9 +93,11 @@ check_auto_bind(void)
header();
plan(3);
+ bool is_host_empty;
struct sockaddr_in addr;
socklen_t addrlen = sizeof(addr);
- sio_uri_to_addr("127.0.0.1:0", (struct sockaddr *) &addr);
+ sio_uri_to_addr("127.0.0.1:0", (struct sockaddr *) &addr,
+ &is_host_empty);
int fd = sio_socket(AF_INET, SOCK_STREAM, 0);
is(sio_bind(fd, (struct sockaddr *) &addr, sizeof(addr)), 0,
"bind to 0 works");
diff --git a/test/unit/sio.result b/test/unit/sio.result
index e5712ad3c..896736bf9 100644
--- a/test/unit/sio.result
+++ b/test/unit/sio.result
@@ -1,25 +1,29 @@
*** main ***
1..2
*** check_uri_to_addr ***
- 1..18
+ 1..22
ok 1 - invalid uri is detected
ok 2 - too long UNIX path
ok 3 - UNIX
ok 4 - UNIX path
ok 5 - UNIX family
- ok 6 - localhost
- ok 7 - localhost family
- ok 8 - localhost address
- ok 9 - localhost port
- ok 10 - 'any'
- ok 11 - 'any' family
- ok 12 - 'any' address
- ok 13 - 'any' port
- ok 14 - IP
- ok 15 - IP family
- ok 16 - IP address
- ok 17 - IP port
- ok 18 - invalid IP
+ ok 6 - unix host is not empty
+ ok 7 - localhost
+ ok 8 - localhost family
+ ok 9 - localhost address
+ ok 10 - localhost port
+ ok 11 - 'localhost' host is not empty
+ ok 12 - 'any'
+ ok 13 - 'any' family
+ ok 14 - 'any' address
+ ok 15 - 'any' port
+ ok 16 - only port specified - host is empty
+ ok 17 - IP
+ ok 18 - IP family
+ ok 19 - IP address
+ ok 20 - IP port
+ ok 21 - IPv4 host is not empty
+ ok 22 - invalid IP
ok 1 - subtests
*** check_uri_to_addr: done ***
*** check_auto_bind ***
--
2.20.1 (Apple Git-117)
More information about the Tarantool-patches
mailing list