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
|
||||
|
||||
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_memory.tcc \
|
||||
autotest/test_ipfilter.tcc \
|
||||
autotest/test_inf.tcc \
|
||||
autotest/test_hub.tcc \
|
||||
autotest/test_message.tcc \
|
||||
autotest/test_misc.tcc \
|
||||
autotest/test_sid.tcc \
|
||||
autotest/test_tiger.tcc \
|
||||
autotest/test_usermanager.tcc \
|
||||
autotest/test_eventqueue.tcc
|
||||
autotest/test_usermanager.tcc
|
||||
|
||||
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)
|
||||
{
|
||||
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);
|
||||
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)
|
||||
{
|
||||
if (!sid || (sid > pool->max))
|
||||
if (!sid || (sid >= pool->max))
|
||||
return 0;
|
||||
return pool->map[sid];
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue