|
Packit |
ac4610 |
#include "config.h"
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
#include <pthread.h>
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
#include <stdarg.h>
|
|
Packit |
ac4610 |
#include <stddef.h>
|
|
Packit |
ac4610 |
#include <setjmp.h>
|
|
Packit |
ac4610 |
#include <cmocka.h>
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
#include <errno.h>
|
|
Packit |
ac4610 |
#include <stdio.h>
|
|
Packit |
ac4610 |
#include <string.h>
|
|
Packit |
ac4610 |
#include <stdlib.h>
|
|
Packit |
ac4610 |
#include <unistd.h>
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
#include <sys/socket.h>
|
|
Packit |
ac4610 |
#include <netinet/in.h>
|
|
Packit |
ac4610 |
#include <arpa/inet.h>
|
|
Packit |
ac4610 |
#include <netdb.h>
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
#define NSS_WRAPPER_HOSTNAME_ENV "NSS_WRAPPER_HOSTNAME"
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
static void test_nwrap_gethostname(void **state)
|
|
Packit |
ac4610 |
{
|
|
Packit |
ac4610 |
const char *hostname = "milliways";
|
|
Packit |
ac4610 |
char sys_host[256] = {0};
|
|
Packit |
ac4610 |
char host[16] = {0};
|
|
Packit |
ac4610 |
int rc;
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
(void) state; /* unused */
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
rc = setenv(NSS_WRAPPER_HOSTNAME_ENV, hostname, 1);
|
|
Packit |
ac4610 |
assert_int_equal(rc, 0);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
rc = gethostname(host, sizeof(host));
|
|
Packit |
ac4610 |
assert_int_equal(rc, 0);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
assert_string_equal(host, hostname);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
rc = setenv(NSS_WRAPPER_HOSTNAME_ENV, "this_hostname_is_too_long", 1);
|
|
Packit |
ac4610 |
assert_int_equal(rc, 0);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
rc = gethostname(host, sizeof(host));
|
|
Packit |
ac4610 |
assert_int_equal(rc, -1);
|
|
Packit |
ac4610 |
assert_int_equal(errno, ENAMETOOLONG);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
unsetenv(NSS_WRAPPER_HOSTNAME_ENV);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
rc = gethostname(sys_host, sizeof(sys_host));
|
|
Packit |
ac4610 |
assert_int_equal(rc, 0);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
}
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
static void *thread_test_gethostbyname(void *u)
|
|
Packit |
ac4610 |
{
|
|
Packit |
ac4610 |
struct hostent *he;
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
(void) u; /* unused */
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
he = gethostbyname("magrathea");
|
|
Packit |
ac4610 |
assert_non_null(he);
|
|
Packit |
ac4610 |
assert_non_null(he->h_name);
|
|
Packit |
ac4610 |
assert_string_equal(he->h_name, "magrathea.galaxy.site");
|
|
Packit |
ac4610 |
pthread_exit(NULL);
|
|
Packit |
ac4610 |
}
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
static void test_nwrap_gethostbyname_thread(void **state)
|
|
Packit |
ac4610 |
{
|
|
Packit |
ac4610 |
struct hostent *he;
|
|
Packit |
ac4610 |
pthread_t th;
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
(void) state; /* unused */
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
he = gethostbyname("maximegalon.galaxy.site");
|
|
Packit |
ac4610 |
assert_non_null(he);
|
|
Packit |
ac4610 |
assert_non_null(he->h_name);
|
|
Packit |
ac4610 |
assert_string_equal(he->h_name, "maximegalon.galaxy.site");
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
pthread_create(&th, NULL, &thread_test_gethostbyname, NULL);
|
|
Packit |
ac4610 |
pthread_join(th, NULL);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
assert_non_null(he);
|
|
Packit |
ac4610 |
assert_non_null(he->h_name);
|
|
Packit |
ac4610 |
#ifdef BSD
|
|
Packit |
ac4610 |
/*
|
|
Packit |
ac4610 |
* On *BSD (and Mac OS X) systems,
|
|
Packit |
ac4610 |
* data is stored in thread local storage.
|
|
Packit |
ac4610 |
*/
|
|
Packit |
ac4610 |
assert_string_equal(he->h_name, "maximegalon.galaxy.site");
|
|
Packit |
ac4610 |
#else
|
|
Packit |
ac4610 |
/*
|
|
Packit |
ac4610 |
* Glibc doesn't store data in thread local storage, so calling
|
|
Packit |
ac4610 |
* gethostbyname from a thread overwrites the parent thread's data.
|
|
Packit |
ac4610 |
*/
|
|
Packit |
ac4610 |
assert_string_equal(he->h_name, "magrathea.galaxy.site");
|
|
Packit |
ac4610 |
#endif
|
|
Packit |
ac4610 |
}
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
static void test_nwrap_gethostbyname(void **state)
|
|
Packit |
ac4610 |
{
|
|
Packit |
ac4610 |
char ip[INET_ADDRSTRLEN];
|
|
Packit |
ac4610 |
struct hostent *he;
|
|
Packit |
ac4610 |
const char *a;
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
(void) state; /* unused */
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
he = gethostbyname("magrathea.galaxy.site");
|
|
Packit |
ac4610 |
assert_non_null(he);
|
|
Packit |
ac4610 |
assert_non_null(he->h_name);
|
|
Packit |
ac4610 |
assert_non_null(he->h_addr_list);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
assert_string_equal(he->h_name, "magrathea.galaxy.site");
|
|
Packit |
ac4610 |
assert_int_equal(he->h_addrtype, AF_INET);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
a = inet_ntop(AF_INET, he->h_addr_list[0], ip, sizeof(ip));
|
|
Packit |
ac4610 |
assert_non_null(a);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
assert_string_equal(ip, "127.0.0.11");
|
|
Packit |
ac4610 |
}
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
static void test_nwrap_gethostbyname_multiple(void **state)
|
|
Packit |
ac4610 |
{
|
|
Packit |
ac4610 |
struct hostent *he;
|
|
Packit |
ac4610 |
char **list;
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
/* For inet_ntop call */
|
|
Packit |
ac4610 |
char buf[4096];
|
|
Packit |
ac4610 |
const char *result;
|
|
Packit |
ac4610 |
char *p = buf;
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
/* List of ips in hosts file - order matters */
|
|
Packit |
ac4610 |
const char *const result_ips[] = { "127.0.0.11", "127.0.0.12", NULL };
|
|
Packit |
ac4610 |
const char *actual_ip = result_ips[0];
|
|
Packit |
ac4610 |
unsigned int ac;
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
(void) state; /* unused */
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
he = gethostbyname("magrathea.galaxy.site");
|
|
Packit |
ac4610 |
assert_non_null(he);
|
|
Packit |
ac4610 |
assert_non_null(he->h_name);
|
|
Packit |
ac4610 |
assert_non_null(he->h_addr_list);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
list = he->h_addr_list;
|
|
Packit |
ac4610 |
for (ac = 0; *list != NULL; ++ac, ++list) {
|
|
Packit |
ac4610 |
actual_ip = result_ips[ac];
|
|
Packit |
ac4610 |
/* When test fails here more records are returned */
|
|
Packit |
ac4610 |
assert_non_null(actual_ip);
|
|
Packit |
ac4610 |
result = inet_ntop(AF_INET, *list, p, 4096);
|
|
Packit |
ac4610 |
assert_non_null(p);
|
|
Packit |
ac4610 |
assert_string_equal(actual_ip, result);
|
|
Packit |
ac4610 |
}
|
|
Packit |
ac4610 |
}
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
#ifdef HAVE_GETHOSTBYNAME2
|
|
Packit |
ac4610 |
static void test_nwrap_gethostbyname2(void **state)
|
|
Packit |
ac4610 |
{
|
|
Packit |
ac4610 |
char ip[INET6_ADDRSTRLEN];
|
|
Packit |
ac4610 |
struct hostent *he;
|
|
Packit |
ac4610 |
const char *a;
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
(void) state; /* unused */
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
he = gethostbyname2("magrathea.galaxy.site", AF_INET6);
|
|
Packit |
ac4610 |
assert_non_null(he);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
he = gethostbyname2("magrathea.galaxy.site", AF_INET);
|
|
Packit |
ac4610 |
assert_non_null(he);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
/* Check ipv6 he */
|
|
Packit |
ac4610 |
he = gethostbyname2("krikkit.galaxy.site", AF_INET6);
|
|
Packit |
ac4610 |
assert_non_null(he);
|
|
Packit |
ac4610 |
assert_non_null(he->h_name);
|
|
Packit |
ac4610 |
assert_non_null(he->h_addr_list);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
assert_string_equal(he->h_name, "krikkit.galaxy.site");
|
|
Packit |
ac4610 |
assert_int_equal(he->h_addrtype, AF_INET6);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
a = inet_ntop(AF_INET6, he->h_addr_list[0], ip, sizeof(ip));
|
|
Packit |
ac4610 |
assert_non_null(a);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
assert_string_equal(ip, "::14");
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
/* Check ipv4 he */
|
|
Packit |
ac4610 |
he = gethostbyname2("krikkit.galaxy.site", AF_INET);
|
|
Packit |
ac4610 |
assert_non_null(he);
|
|
Packit |
ac4610 |
assert_non_null(he->h_name);
|
|
Packit |
ac4610 |
assert_non_null(he->h_addr_list);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
assert_string_equal(he->h_name, "krikkit.galaxy.site");
|
|
Packit |
ac4610 |
assert_int_equal(he->h_addrtype, AF_INET);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
a = inet_ntop(AF_INET, he->h_addr_list[0], ip, sizeof(ip));
|
|
Packit |
ac4610 |
assert_non_null(a);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
assert_string_equal(ip, "127.0.0.14");
|
|
Packit |
ac4610 |
}
|
|
Packit |
ac4610 |
#endif /* HAVE_GETHOSTBYNAME2 */
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
static void test_nwrap_gethostbyaddr(void **state)
|
|
Packit |
ac4610 |
{
|
|
Packit |
ac4610 |
struct hostent *he;
|
|
Packit |
ac4610 |
struct in_addr in;
|
|
Packit |
ac4610 |
int rc;
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
(void) state; /* unused */
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
rc = inet_aton("127.0.0.11", &in);
|
|
Packit |
ac4610 |
assert_int_equal(rc, 1);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
he = gethostbyaddr(&in, sizeof(struct in_addr), AF_INET);
|
|
Packit |
ac4610 |
assert_non_null(he);
|
|
Packit |
ac4610 |
assert_non_null(he->h_name);
|
|
Packit |
ac4610 |
assert_non_null(he->h_addr_list);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
assert_string_equal(he->h_name, "magrathea.galaxy.site");
|
|
Packit |
ac4610 |
assert_int_equal(he->h_addrtype, AF_INET);
|
|
Packit |
ac4610 |
assert_memory_equal(&in, he->h_addr_list[0], he->h_length);
|
|
Packit |
ac4610 |
}
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
#ifdef HAVE_GETHOSTBYNAME_R
|
|
Packit |
ac4610 |
static void test_nwrap_gethostbyname_r(void **state)
|
|
Packit |
ac4610 |
{
|
|
Packit |
ac4610 |
char buf[1024] = {0};
|
|
Packit |
ac4610 |
char ip[INET_ADDRSTRLEN];
|
|
Packit |
ac4610 |
struct hostent hb, *he;
|
|
Packit |
ac4610 |
const char *a;
|
|
Packit |
ac4610 |
int herr = 0;
|
|
Packit |
ac4610 |
int rc;
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
(void) state; /* unused */
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
rc = gethostbyname_r("magrathea.galaxy.site",
|
|
Packit |
ac4610 |
&hb,
|
|
Packit |
ac4610 |
buf, sizeof(buf),
|
|
Packit |
ac4610 |
&he,
|
|
Packit |
ac4610 |
&herr;;
|
|
Packit |
ac4610 |
assert_int_equal(rc, 0);
|
|
Packit |
ac4610 |
assert_non_null(he);
|
|
Packit |
ac4610 |
assert_non_null(he->h_name);
|
|
Packit |
ac4610 |
assert_non_null(he->h_addr_list);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
assert_string_equal(he->h_name, "magrathea.galaxy.site");
|
|
Packit |
ac4610 |
assert_int_equal(he->h_addrtype, AF_INET);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
a = inet_ntop(AF_INET, he->h_addr_list[0], ip, sizeof(ip));
|
|
Packit |
ac4610 |
assert_non_null(a);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
assert_string_equal(ip, "127.0.0.11");
|
|
Packit |
ac4610 |
}
|
|
Packit |
ac4610 |
#endif
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
#ifdef HAVE_GETHOSTBYADDR_R
|
|
Packit |
ac4610 |
static void test_nwrap_gethostbyaddr_r(void **state)
|
|
Packit |
ac4610 |
{
|
|
Packit |
ac4610 |
char buf[1024] = {0};
|
|
Packit |
ac4610 |
struct hostent hb, *he;
|
|
Packit |
ac4610 |
struct in_addr in;
|
|
Packit |
ac4610 |
int herr = 0;
|
|
Packit |
ac4610 |
int rc;
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
(void) state; /* unused */
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
rc = inet_aton("127.0.0.11", &in);
|
|
Packit |
ac4610 |
assert_int_equal(rc, 1);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
rc = gethostbyaddr_r(&in, sizeof(struct in_addr),
|
|
Packit |
ac4610 |
AF_INET,
|
|
Packit |
ac4610 |
&hb,
|
|
Packit |
ac4610 |
buf, sizeof(buf),
|
|
Packit |
ac4610 |
&he,
|
|
Packit |
ac4610 |
&herr;;
|
|
Packit |
ac4610 |
assert_int_equal(rc, 0);
|
|
Packit |
ac4610 |
assert_non_null(he);
|
|
Packit |
ac4610 |
assert_non_null(he->h_name);
|
|
Packit |
ac4610 |
assert_non_null(he->h_addr_list);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
assert_string_equal(he->h_name, "magrathea.galaxy.site");
|
|
Packit |
ac4610 |
assert_int_equal(he->h_addrtype, AF_INET);
|
|
Packit |
ac4610 |
assert_memory_equal(&in, he->h_addr_list[0], he->h_length);
|
|
Packit |
ac4610 |
}
|
|
Packit |
ac4610 |
#endif
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
int main(void) {
|
|
Packit |
ac4610 |
int rc;
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
const struct CMUnitTest tests[] = {
|
|
Packit |
ac4610 |
cmocka_unit_test(test_nwrap_gethostname),
|
|
Packit |
ac4610 |
cmocka_unit_test(test_nwrap_gethostbyname),
|
|
Packit |
ac4610 |
cmocka_unit_test(test_nwrap_gethostbyname_thread),
|
|
Packit |
ac4610 |
#ifdef HAVE_GETHOSTBYNAME2
|
|
Packit |
ac4610 |
cmocka_unit_test(test_nwrap_gethostbyname2),
|
|
Packit |
ac4610 |
#endif
|
|
Packit |
ac4610 |
cmocka_unit_test(test_nwrap_gethostbyaddr),
|
|
Packit |
ac4610 |
#ifdef HAVE_GETHOSTBYNAME_R
|
|
Packit |
ac4610 |
cmocka_unit_test(test_nwrap_gethostbyname_r),
|
|
Packit |
ac4610 |
#endif
|
|
Packit |
ac4610 |
#ifdef HAVE_GETHOSTBYADDR_R
|
|
Packit |
ac4610 |
cmocka_unit_test(test_nwrap_gethostbyaddr_r),
|
|
Packit |
ac4610 |
#endif
|
|
Packit |
ac4610 |
cmocka_unit_test(test_nwrap_gethostbyname_multiple),
|
|
Packit |
ac4610 |
};
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
rc = cmocka_run_group_tests(tests, NULL, NULL);
|
|
Packit |
ac4610 |
|
|
Packit |
ac4610 |
return rc;
|
|
Packit |
ac4610 |
}
|
|
Packit |
ac4610 |
|