Added test cases for sid allocation.
This revealed a few bugs: * when sid allocator is full, then uhub will loop indefinitely when allocating one more (unlikely to occur). * looking up a user object based on a sid that is out of range (off by one) returns invalid memory.
This commit is contained in:
parent
963416ad73
commit
59ed268f4d
13
GNUmakefile
13
GNUmakefile
|
@ -167,16 +167,17 @@ adcrush_SOURCES := src/tools/adcrush.c
|
||||||
admin_SOURCES := src/tools/admin.c
|
admin_SOURCES := src/tools/admin.c
|
||||||
|
|
||||||
autotest_SOURCES := \
|
autotest_SOURCES := \
|
||||||
autotest/test_message.tcc \
|
autotest/test_eventqueue.tcc \
|
||||||
|
autotest/test_hub.tcc \
|
||||||
|
autotest/test_inf.tcc \
|
||||||
|
autotest/test_ipfilter.tcc \
|
||||||
autotest/test_list.tcc \
|
autotest/test_list.tcc \
|
||||||
autotest/test_memory.tcc \
|
autotest/test_memory.tcc \
|
||||||
autotest/test_ipfilter.tcc \
|
autotest/test_message.tcc \
|
||||||
autotest/test_inf.tcc \
|
|
||||||
autotest/test_hub.tcc \
|
|
||||||
autotest/test_misc.tcc \
|
autotest/test_misc.tcc \
|
||||||
|
autotest/test_sid.tcc \
|
||||||
autotest/test_tiger.tcc \
|
autotest/test_tiger.tcc \
|
||||||
autotest/test_usermanager.tcc \
|
autotest/test_usermanager.tcc
|
||||||
autotest/test_eventqueue.tcc
|
|
||||||
|
|
||||||
autotest_OBJECTS = autotest.o
|
autotest_OBJECTS = autotest.o
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,138 @@
|
||||||
|
#include <uhub.h>
|
||||||
|
|
||||||
|
static struct sid_pool* sid_pool = 0;
|
||||||
|
|
||||||
|
struct dummy_user
|
||||||
|
{
|
||||||
|
sid_t sid;
|
||||||
|
};
|
||||||
|
|
||||||
|
static struct dummy_user* last = 0;
|
||||||
|
sid_t last_sid = 0;
|
||||||
|
|
||||||
|
EXO_TEST(sid_create_pool, {
|
||||||
|
sid_pool = sid_pool_create(4);
|
||||||
|
return sid_pool != 0;
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_check_0a, {
|
||||||
|
struct dummy_user* user = (struct dummy_user*) sid_lookup(sid_pool, 0);
|
||||||
|
return user == 0;
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_check_0b, {
|
||||||
|
struct dummy_user* user = (struct dummy_user*) sid_lookup(sid_pool, 5);
|
||||||
|
return user == 0;
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_alloc_1, {
|
||||||
|
struct dummy_user* user = hub_malloc_zero(sizeof(struct dummy_user));
|
||||||
|
user->sid = sid_alloc(sid_pool, (struct hub_user*) user);
|
||||||
|
last = user;
|
||||||
|
last_sid = user->sid;
|
||||||
|
return (user->sid > 0 && user->sid < 1048576);
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_check_1a, {
|
||||||
|
struct dummy_user* user = (struct dummy_user*) sid_lookup(sid_pool, last_sid);
|
||||||
|
return last == user;
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_check_1b, {
|
||||||
|
struct dummy_user* user = (struct dummy_user*) sid_lookup(sid_pool, last_sid+1);
|
||||||
|
return user == 0;
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_alloc_2, {
|
||||||
|
struct dummy_user* user = hub_malloc_zero(sizeof(struct dummy_user));
|
||||||
|
user->sid = sid_alloc(sid_pool, (struct hub_user*) user);
|
||||||
|
last_sid = user->sid;
|
||||||
|
return (user->sid > 0 && user->sid < 1048576);
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_check_2, {
|
||||||
|
struct dummy_user* user = (struct dummy_user*) sid_lookup(sid_pool, last_sid);
|
||||||
|
return last != user;
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_alloc_3, {
|
||||||
|
struct dummy_user* user = hub_malloc_zero(sizeof(struct dummy_user));
|
||||||
|
user->sid = sid_alloc(sid_pool, (struct hub_user*) user);
|
||||||
|
last_sid = user->sid;
|
||||||
|
return (user->sid > 0 && user->sid < 1048576);
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_check_3, {
|
||||||
|
struct dummy_user* user = (struct dummy_user*) sid_lookup(sid_pool, last_sid);
|
||||||
|
return last != user;
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_alloc_4, {
|
||||||
|
struct dummy_user* user = hub_malloc_zero(sizeof(struct dummy_user));
|
||||||
|
user->sid = sid_alloc(sid_pool, (struct hub_user*) user);
|
||||||
|
last_sid = user->sid;
|
||||||
|
return (user->sid > 0 && user->sid < 1048576);
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_check_4, {
|
||||||
|
struct dummy_user* user = (struct dummy_user*) sid_lookup(sid_pool, last_sid);
|
||||||
|
return last != user;
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_alloc_5, {
|
||||||
|
struct dummy_user user;
|
||||||
|
sid_t sid;
|
||||||
|
sid = sid_alloc(sid_pool, (struct hub_user*) &user);
|
||||||
|
return sid == 0;
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_check_6, {
|
||||||
|
struct dummy_user* user = (struct dummy_user*) sid_lookup(sid_pool, 0);
|
||||||
|
return user == 0;
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
|
EXO_TEST(sid_list_all_1, {
|
||||||
|
sid_t s;
|
||||||
|
size_t n = 0;
|
||||||
|
int ok = 1;
|
||||||
|
for (s = last->sid; s <= last_sid; s++)
|
||||||
|
{
|
||||||
|
struct dummy_user* user = (struct dummy_user*) sid_lookup(sid_pool, s);
|
||||||
|
if (s != (user ? user->sid : -1))
|
||||||
|
{
|
||||||
|
ok = 0;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
n++;
|
||||||
|
}
|
||||||
|
return ok && n == 4;
|
||||||
|
});
|
||||||
|
|
||||||
|
#define FREE_SID(N) \
|
||||||
|
struct dummy_user* user = (struct dummy_user*) sid_lookup(sid_pool, N); \
|
||||||
|
sid_free(sid_pool, N); \
|
||||||
|
hub_free(user); \
|
||||||
|
return sid_lookup(sid_pool, N) == NULL;
|
||||||
|
|
||||||
|
EXO_TEST(sid_remove_1, {
|
||||||
|
FREE_SID(2);
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_remove_2, {
|
||||||
|
FREE_SID(1);
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_remove_3, {
|
||||||
|
FREE_SID(4);
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_remove_4, {
|
||||||
|
FREE_SID(3);
|
||||||
|
});
|
||||||
|
|
||||||
|
EXO_TEST(sid_destroy_pool, {
|
||||||
|
sid_pool_destroy(sid_pool);
|
||||||
|
sid_pool = 0;
|
||||||
|
return sid_pool == 0;
|
||||||
|
});
|
|
@ -119,6 +119,14 @@ void sid_pool_destroy(struct sid_pool* pool)
|
||||||
|
|
||||||
sid_t sid_alloc(struct sid_pool* pool, struct hub_user* user)
|
sid_t sid_alloc(struct sid_pool* pool, struct hub_user* user)
|
||||||
{
|
{
|
||||||
|
if (pool->count >= (pool->max - pool->min))
|
||||||
|
{
|
||||||
|
#ifdef DEBUG_SID
|
||||||
|
LOG_DUMP("SID_POOL: alloc, sid pool is full.");
|
||||||
|
#endif
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
sid_t n = (++pool->count);
|
sid_t n = (++pool->count);
|
||||||
for (; (pool->map[n % pool->max]); n++) ;
|
for (; (pool->map[n % pool->max]); n++) ;
|
||||||
|
|
||||||
|
@ -140,7 +148,7 @@ void sid_free(struct sid_pool* pool, sid_t sid)
|
||||||
|
|
||||||
struct hub_user* sid_lookup(struct sid_pool* pool, sid_t sid)
|
struct hub_user* sid_lookup(struct sid_pool* pool, sid_t sid)
|
||||||
{
|
{
|
||||||
if (!sid || (sid > pool->max))
|
if (!sid || (sid >= pool->max))
|
||||||
return 0;
|
return 0;
|
||||||
return pool->map[sid];
|
return pool->map[sid];
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue