From a693a53e2302fe9cc60c1b5d2bf59c42032b20a3 Mon Sep 17 00:00:00 2001 From: Garrett D'Amore Date: Tue, 31 Dec 2019 15:09:20 -0800 Subject: fixes #1081 Use after free possible in stats fixes #1080 Desire better way to access statistics for NNG objects We've also added a test that uses some of this, in order to verify that the req protocol rejects invalid peers. --- tests/testutil.c | 57 ++++++++++++++++++++++++++++++++++++++++++++++++++++---- tests/testutil.h | 5 +++++ 2 files changed, 58 insertions(+), 4 deletions(-) (limited to 'tests') diff --git a/tests/testutil.c b/tests/testutil.c index 1c65c996..36999448 100644 --- a/tests/testutil.c +++ b/tests/testutil.c @@ -127,14 +127,63 @@ uint32_t testutil_htonl(uint32_t in) { #ifdef NNG_LITTLE_ENDIAN - in = ((in >> 24u) & 0xffu) | - ((in >> 8u) & 0xff00u) | - ((in << 8u) & 0xff0000u) | - ((in << 24u) & 0xff000000u); + in = ((in >> 24u) & 0xffu) | ((in >> 8u) & 0xff00u) | + ((in << 8u) & 0xff0000u) | ((in << 24u) & 0xff000000u); #endif return (in); } +void +testutil_scratch_addr(const char *scheme, size_t sz, char *addr) +{ + if (strcmp(scheme, "inproc") == 0) { + (void) snprintf(addr, sz, "%s://testutil%04x%04x%04x%04x", + scheme, nng_random(), nng_random(), nng_random(), + nng_random()); + return; + } + + if ((strncmp(scheme, "tcp", 3) == 0) || + (strncmp(scheme, "tls", 3) == 0)) { + (void) snprintf(addr, sz, "%s://127.0.0.1:%u", scheme, + testutil_next_port()); + return; + } + + if (strncmp(scheme, "ws", 2) == 0) { + (void) snprintf(addr, sz, + "%s://127.0.0.1:%u/testutil%04x%04x%04x%04x", scheme, + testutil_next_port(), nng_random(), nng_random(), + nng_random(), nng_random()); + return; + } + + if (strncmp(scheme, "ipc", 3) == 0) { +#ifdef _WIN32 + // Windows doesn't place IPC names in the filesystem. + (void) snprintf(addr, sz, "%s://testutil%04x%04x%04x%04x", + scheme, nng_random(), nng_random(), nng_random(), + nng_random()); +#else + char *tmpdir; + + if (((tmpdir = getenv("TMPDIR")) == NULL) && + ((tmpdir = getenv("TEMP")) == NULL) && + ((tmpdir = getenv("TMP")) == NULL)) { + tmpdir = "/tmp"; + } + + (void) snprintf(addr, sz, "%s://%s/testutil%04x%04x%04x%04x", + scheme, tmpdir, nng_random(), nng_random(), nng_random(), + nng_random()); + return; +#endif + } + + // We should not be here. + abort(); +} + // testutil_next_port returns a "next" allocation port. // Ports are chosen by starting from a random point within a // range (normally 38000-40000, but other good places to choose diff --git a/tests/testutil.h b/tests/testutil.h index b9acfedf..14cc1712 100644 --- a/tests/testutil.h +++ b/tests/testutil.h @@ -40,6 +40,11 @@ extern void testutil_sleep(int); // testutil_next_port returns a new port number (presumably unique) extern uint16_t testutil_next_port(void); +// testutil_scratch_addr makes a scratch address for the given scheme. +// The address buffer must be supplied, and the size should be at least +// 64 bytes to ensure no truncation occurs. +extern void testutil_scratch_addr(const char *, size_t, char *); + // testutil_marry connects two sockets using inproc. It uses socket // pipe hooks to ensure that it does not return before both sockets // are fully connected. -- cgit v1.2.3-70-g09d2