/* See LICENSE file for copyright and license details. */
#define TEST_C
#include "common.h"
#include <assert.h> /* TODO improve output */
#include <stdarg.h>
#include <stdio.h>
#include <string.h>
static uint64_t classes_1 = (1 << 1);
static uint64_t classes_1_2 = (1 << 1) | (1 << 2);
static uint64_t classes_1_2_3 = (1 << 1) | (1 << 2) | (1 << 3);
static uint64_t classes_2 = (1 << 2);
static struct libenv_variable list[] = {
{"a", &classes_1},
{"aa", &classes_1_2},
{"BB", &classes_1_2_3},
{"bb", &classes_2},
{"b", &classes_1},
{NULL, NULL}
};
#include "libenv_get_complete_list.c"
union list_process_function {
size_t (*dyn)(char **, ...);
size_t (*cnst)(const char **, ...);
};
static void
dealloc(char **strings)
{
size_t i;
for (i = 0; strings[i]; i++)
free(strings[i]);
}
static void
check(size_t count, char **strings, ...)
{
size_t i, len;
const char *expect;
va_list args;
va_start(args, strings);
for (i = 0; (expect = va_arg(args, const char *)); i++) {
len = strlen(expect);
assert(strings[i]);
assert(!strncmp(strings[i], expect, len));
assert(!strings[i][len] || strings[i][len] == '=');
}
va_end(args);
assert(!strings[i]);
assert(count == i);
}
#define CHECK(CALL, ...)\
do {\
char *strings[8];\
char *allocations[8];\
size_t i;\
char *p;\
assert(strings[0] = allocations[0] = strdup("a="));\
assert(strings[1] = allocations[1] = strdup("aa=1"));\
assert(strings[2] = allocations[2] = strdup("b=12"));\
assert(strings[3] = allocations[3] = strdup("bb=34"));\
assert(strings[4] = allocations[4] = strdup("BB"));\
assert(strings[5] = allocations[5] = strdup("x=5"));\
assert(strings[6] = allocations[6] = strdup("xx"));\
strings[7] = allocations[7] = NULL;\
if (!variable_version) {\
for (i = 0; strings[i]; i++) {\
for (p = strings[i]; *p && *p != '='; p++);\
*p = '\0';\
}\
}\
check(CALL, strings, __VA_ARGS__);\
dealloc(dealloc_version ? strings : allocations);\
} while (0)
static void
test_filter(int dealloc_version, int variable_version, const union list_process_function *function)
{
CHECK((*function->dyn)(strings, LIBENV_END), NULL); /* each contain all of nothing, so remove all */
if (!variable_version) {
CHECK((*function->dyn)(strings, 3, LIBENV_END), "a", "aa", "b", "bb", "x", "xx", NULL);
CHECK((*function->dyn)(strings, 2, LIBENV_END), "a", "b", "x", "xx", NULL);
CHECK((*function->dyn)(strings, 1, 2, 3, LIBENV_END), "a", "aa", "b", "bb", "x", "xx", NULL);
CHECK((*function->dyn)(strings, 1, 2, LIBENV_END), "a", "b", "bb", "x", "xx", NULL);
} else {
CHECK((*function->dyn)(strings, 3, LIBENV_END), "a", "aa", "b", "bb", "BB", "x", "xx", NULL);
CHECK((*function->dyn)(strings, 2, LIBENV_END), "a", "b", "BB", "x", "xx", NULL);
CHECK((*function->dyn)(strings, 1, 2, 3, LIBENV_END), "a", "aa", "b", "bb", "BB", "x", "xx", NULL);
CHECK((*function->dyn)(strings, 1, 2, LIBENV_END), "a", "b", "bb", "BB", "x", "xx", NULL);
}
CHECK((*function->dyn)(strings, 10, LIBENV_END), "a", "aa", "b", "bb", "BB", "x", "xx", NULL);
CHECK((*function->dyn)(strings, 64, LIBENV_END), "a", "aa", "b", "bb", "BB", "x", "xx", NULL);
CHECK((*function->dyn)(strings, 100000, LIBENV_END), "a", "aa", "b", "bb", "BB", "x", "xx", NULL);
}
static void
test_select(int dealloc_version, int variable_version, const union list_process_function *function)
{
const char *BB = variable_version ? NULL : "BB";
CHECK((*function->dyn)(strings, LIBENV_END), NULL); /* none contain any of nothing, so select all */
CHECK((*function->dyn)(strings, 3, LIBENV_END), BB, NULL);
CHECK((*function->dyn)(strings, 2, LIBENV_END), "aa", "bb", BB, NULL);
CHECK((*function->dyn)(strings, 1, 2, 3, LIBENV_END), "a", "aa", "b", "bb", BB, NULL);
CHECK((*function->dyn)(strings, 1, 2, LIBENV_END), "a", "aa", "b", "bb", BB, NULL);
CHECK((*function->dyn)(strings, 1, 3, LIBENV_END), "a", "aa", "b", BB, NULL);
CHECK((*function->dyn)(strings, 10, LIBENV_END), NULL);
CHECK((*function->dyn)(strings, 64, LIBENV_END), NULL);
CHECK((*function->dyn)(strings, 100000, LIBENV_END), NULL);
}
#undef CHECK
static void
test_get_chosen_list(void) /* TODO check memory failure behaviour */
{
const char **r;
assert(r = libenv_get_chosen_list(LIBENV_END));
assert(!r[0]);
free(r);
assert(r = libenv_get_chosen_list(1, LIBENV_END));
assert(r[0] && !strcmp(r[0], "a"));
assert(r[1] && !strcmp(r[1], "aa"));
assert(r[2] && !strcmp(r[2], "BB"));
assert(r[3] && !strcmp(r[3], "b"));
assert(!r[4]);
free(r);
assert(r = libenv_get_chosen_list(2, LIBENV_END));
assert(r[0] && !strcmp(r[0], "aa"));
assert(r[1] && !strcmp(r[1], "BB"));
assert(r[2] && !strcmp(r[2], "bb"));
assert(!r[3]);
free(r);
assert(r = libenv_get_chosen_list(3, LIBENV_END));
assert(r[0] && !strcmp(r[0], "BB"));
assert(!r[1]);
free(r);
assert(r = libenv_get_chosen_list(1, 2, LIBENV_END));
assert(r[0] && !strcmp(r[0], "a"));
assert(r[1] && !strcmp(r[1], "aa"));
assert(r[2] && !strcmp(r[2], "BB"));
assert(r[3] && !strcmp(r[3], "bb"));
assert(r[4] && !strcmp(r[4], "b"));
assert(!r[5]);
free(r);
assert(r = libenv_get_chosen_list(2, 3, LIBENV_END));
assert(r[0] && !strcmp(r[0], "aa"));
assert(r[1] && !strcmp(r[1], "BB"));
assert(r[2] && !strcmp(r[2], "bb"));
assert(!r[3]);
free(r);
assert(r = libenv_get_chosen_list(3, 1, LIBENV_END));
assert(r[0] && !strcmp(r[0], "a"));
assert(r[1] && !strcmp(r[1], "aa"));
assert(r[2] && !strcmp(r[2], "BB"));
assert(r[3] && !strcmp(r[3], "b"));
assert(!r[4]);
free(r);
assert(r = libenv_get_chosen_list(1, 2, 3, LIBENV_END));
assert(r[0] && !strcmp(r[0], "a"));
assert(r[1] && !strcmp(r[1], "aa"));
assert(r[2] && !strcmp(r[2], "BB"));
assert(r[3] && !strcmp(r[3], "bb"));
assert(r[4] && !strcmp(r[4], "b"));
assert(!r[5]);
free(r);
assert(r = libenv_get_chosen_list(10, LIBENV_END));
assert(!r[0]);
free(r);
assert(r = libenv_get_chosen_list(64, LIBENV_END));
assert(!r[0]);
free(r);
assert(r = libenv_get_chosen_list(1000, LIBENV_END));
assert(!r[0]);
free(r);
}
int
main(void)
{
union list_process_function f;
f.cnst = &libenv_filter_name_list;
test_filter(0, 0, &f);
f.dyn = &libenv_filter_name_list_with_dealloc;
test_filter(1, 0, &f);
f.cnst = &libenv_filter_variable_list;
test_filter(0, 1, &f);
f.dyn = &libenv_filter_variable_list_with_dealloc;
test_filter(1, 1, &f);
f.cnst = &libenv_select_name_list;
test_select(0, 0, &f);
f.dyn = &libenv_select_name_list_with_dealloc;
test_select(1, 0, &f);
f.cnst = &libenv_select_variable_list;
test_select(0, 1, &f);
f.dyn = &libenv_select_variable_list_with_dealloc;
test_select(1, 1, &f);
test_get_chosen_list();
/* TODO check for memory leaks */
return 0;
}