1
0
mirror of https://github.com/alliedmodders/metamod-source.git synced 2025-03-22 13:19:40 +01:00

Added test4.cpp for plugin managment system testing, added -v parameter for verbose output on test fail

--HG--
extra : convert_revision : svn%3Ac2935e3e-5518-0410-8daf-afa5dab7d4e3/trunk%4061
This commit is contained in:
Pavol Marko 2005-05-05 14:00:08 +00:00
parent a5b89f545c
commit 3c82560621
4 changed files with 455 additions and 4 deletions

View File

@ -1,8 +1,8 @@
CC=gcc
CCFLAGS=-c -g -I.. -DSH_DEBUG
test.bin: bin bin/main.o bin/test1.o bin/test2.o bin/test3.o bin/sourcehook.o
$(CC) bin/main.o bin/test1.o bin/test2.o bin/test3.o bin/sourcehook.o -lstdc++ -o test.bin
test.bin: bin bin/main.o bin/test1.o bin/test2.o bin/test3.o bin/test4.o bin/sourcehook.o
$(CC) bin/main.o bin/test1.o bin/test2.o bin/test3.o bin/test4.o bin/sourcehook.o -lstdc++ -o test.bin
bin:
mkdir bin
@ -19,6 +19,9 @@ bin/test2.o: test2.cpp ../sourcehook.h
bin/test3.o: test3.cpp ../sourcehook.h
$(CC) $(CCFLAGS) -o bin/test3.o test3.cpp
bin/test4.o: test4.cpp ../sourcehook.h
$(CC) $(CCFLAGS) -o bin/test4.o test4.cpp
bin/sourcehook.o: ../sourcehook.cpp ../sourcehook.h
$(CC) $(CCFLAGS) -o bin/sourcehook.o ../sourcehook.cpp

View File

@ -62,13 +62,14 @@ std::list<Test *> Test::ms_Tests;
DO_TEST(Basic);
DO_TEST(VafmtAndOverload);
DO_TEST(ThisPtrOffs);
DO_TEST(PlugSys);
int main(int argc, char *argv[])
{
std::string error;
int passed=0, failed=0;
g_Verbose = false;
g_Verbose = argc > 1 && strcmp(argv[1], "-v") == 0;
Test::DoTests();

422
sourcehook/test/test4.cpp Normal file
View File

@ -0,0 +1,422 @@
#include <string>
#include "sourcehook_impl.h"
#include "testevents.h"
// TEST4
// Tests of plugin management system
namespace
{
StateList g_States;
SourceHook::ISourceHook *g_SHPtr;
SourceHook::Plugin g_PLID;
MAKE_STATE(State_Func1_Called);
MAKE_STATE(State_Func2_Called);
MAKE_STATE(State_Func3_Called);
MAKE_STATE(State_Func1H_Called);
MAKE_STATE(State_Func2H_Called);
MAKE_STATE(State_Func3H_Called);
MAKE_STATE_2(State_PluginInUse, int, bool);
class Test
{
public:
virtual void Func1()
{
ADD_STATE(State_Func1_Called);
}
virtual void Func2()
{
ADD_STATE(State_Func2_Called);
}
virtual void Func3()
{
ADD_STATE(State_Func3_Called);
}
};
SH_DECL_HOOK0_void(Test, Func1, SH_NOATTRIB, 0);
SH_DECL_HOOK0_void(Test, Func2, SH_NOATTRIB, 0);
SH_DECL_HOOK0_void(Test, Func3, SH_NOATTRIB, 0);
void Handler_Func1()
{
ADD_STATE(State_Func1H_Called);
}
void Handler_Func2()
{
ADD_STATE(State_Func2H_Called);
}
void Handler_Func3()
{
ADD_STATE(State_Func3H_Called);
}
}
bool TestPlugSys(std::string &error)
{
SourceHook::CSourceHookImpl g_SHImpl;
g_SHPtr = &g_SHImpl;
g_PLID = 1;
Test inst;
Test *pInst = &inst;
// 1)
// Add hooks, then issue a complete shutdown
SH_ADD_HOOK_STATICFUNC(Test, Func1, pInst, Handler_Func1, false);
SH_ADD_HOOK_STATICFUNC(Test, Func2, pInst, Handler_Func2, true);
SH_ADD_HOOK_STATICFUNC(Test, Func3, pInst, Handler_Func3, false);
pInst->Func1();
pInst->Func2();
pInst->Func3();
CHECK_STATES((&g_States,
new State_Func1H_Called,
new State_Func1_Called,
new State_Func2_Called,
new State_Func2H_Called,
new State_Func3H_Called,
new State_Func3_Called,
NULL), "Part 1.1");
g_SHImpl.CompleteShutdown();
pInst->Func1();
pInst->Func2();
pInst->Func3();
CHECK_STATES((&g_States,
new State_Func1_Called,
new State_Func2_Called,
new State_Func3_Called,
NULL), "Part 1.2");
// 2)
// Add hooks from "different plugins", then shutdown the plugins
g_PLID = 1;
SH_ADD_HOOK_STATICFUNC(Test, Func1, pInst, Handler_Func1, false);
g_PLID = 2;
SH_ADD_HOOK_STATICFUNC(Test, Func2, pInst, Handler_Func2, true);
g_PLID = 3;
SH_ADD_HOOK_STATICFUNC(Test, Func3, pInst, Handler_Func3, false);
g_PLID = 1;
SH_ADD_HOOK_STATICFUNC(Test, Func2, pInst, Handler_Func2, true);
SH_ADD_HOOK_STATICFUNC(Test, Func3, pInst, Handler_Func3, false);
g_PLID = 2;
SH_ADD_HOOK_STATICFUNC(Test, Func1, pInst, Handler_Func1, false);
SH_ADD_HOOK_STATICFUNC(Test, Func3, pInst, Handler_Func3, false);
g_PLID = 3;
SH_ADD_HOOK_STATICFUNC(Test, Func1, pInst, Handler_Func1, false);
SH_ADD_HOOK_STATICFUNC(Test, Func2, pInst, Handler_Func2, true);
pInst->Func1();
pInst->Func2();
pInst->Func3();
CHECK_STATES((&g_States,
new State_Func1H_Called,
new State_Func1H_Called,
new State_Func1H_Called,
new State_Func1_Called,
new State_Func2_Called,
new State_Func2H_Called,
new State_Func2H_Called,
new State_Func2H_Called,
new State_Func3H_Called,
new State_Func3H_Called,
new State_Func3H_Called,
new State_Func3_Called,
NULL), "Part 2.1");
ADD_STATE(State_PluginInUse(1, g_SHImpl.IsPluginInUse(1)));
ADD_STATE(State_PluginInUse(2, g_SHImpl.IsPluginInUse(2)));
ADD_STATE(State_PluginInUse(3, g_SHImpl.IsPluginInUse(3)));
ADD_STATE(State_PluginInUse(4, g_SHImpl.IsPluginInUse(4)));
CHECK_STATES((&g_States,
new State_PluginInUse(1, true),
new State_PluginInUse(2, true),
new State_PluginInUse(3, true),
new State_PluginInUse(4, false),
NULL), "Part 2.2");
// Unload plugins one by one
g_SHImpl.UnloadPlugin(3);
pInst->Func1();
pInst->Func2();
pInst->Func3();
CHECK_STATES((&g_States,
new State_Func1H_Called,
new State_Func1H_Called,
new State_Func1_Called,
new State_Func2_Called,
new State_Func2H_Called,
new State_Func2H_Called,
new State_Func3H_Called,
new State_Func3H_Called,
new State_Func3_Called,
NULL), "Part 2.3.1");
ADD_STATE(State_PluginInUse(1, g_SHImpl.IsPluginInUse(1)));
ADD_STATE(State_PluginInUse(2, g_SHImpl.IsPluginInUse(2)));
ADD_STATE(State_PluginInUse(3, g_SHImpl.IsPluginInUse(3)));
ADD_STATE(State_PluginInUse(4, g_SHImpl.IsPluginInUse(4)));
CHECK_STATES((&g_States,
new State_PluginInUse(1, true),
new State_PluginInUse(2, true),
new State_PluginInUse(3, false),
new State_PluginInUse(4, false),
NULL), "Part 2.3.2");
g_SHImpl.UnloadPlugin(2);
pInst->Func1();
pInst->Func2();
pInst->Func3();
CHECK_STATES((&g_States,
new State_Func1H_Called,
new State_Func1_Called,
new State_Func2_Called,
new State_Func2H_Called,
new State_Func3H_Called,
new State_Func3_Called,
NULL), "Part 2.4.1");
ADD_STATE(State_PluginInUse(1, g_SHImpl.IsPluginInUse(1)));
ADD_STATE(State_PluginInUse(2, g_SHImpl.IsPluginInUse(2)));
ADD_STATE(State_PluginInUse(3, g_SHImpl.IsPluginInUse(3)));
ADD_STATE(State_PluginInUse(4, g_SHImpl.IsPluginInUse(4)));
CHECK_STATES((&g_States,
new State_PluginInUse(1, true),
new State_PluginInUse(2, false),
new State_PluginInUse(3, false),
new State_PluginInUse(4, false),
NULL), "Part 2.4.2");
g_SHImpl.UnloadPlugin(1);
pInst->Func1();
pInst->Func2();
pInst->Func3();
CHECK_STATES((&g_States,
new State_Func1_Called,
new State_Func2_Called,
new State_Func3_Called,
NULL), "Part 2.5.1");
ADD_STATE(State_PluginInUse(1, g_SHImpl.IsPluginInUse(1)));
ADD_STATE(State_PluginInUse(2, g_SHImpl.IsPluginInUse(2)));
ADD_STATE(State_PluginInUse(3, g_SHImpl.IsPluginInUse(3)));
ADD_STATE(State_PluginInUse(4, g_SHImpl.IsPluginInUse(4)));
CHECK_STATES((&g_States,
new State_PluginInUse(1, false),
new State_PluginInUse(2, false),
new State_PluginInUse(3, false),
new State_PluginInUse(4, false),
NULL), "Part 2.5.2");
// 3)
// Add hooks from "different plugins", then pause the plugins
g_PLID = 1;
SH_ADD_HOOK_STATICFUNC(Test, Func1, pInst, Handler_Func1, false);
g_PLID = 2;
SH_ADD_HOOK_STATICFUNC(Test, Func2, pInst, Handler_Func2, true);
g_PLID = 3;
SH_ADD_HOOK_STATICFUNC(Test, Func3, pInst, Handler_Func3, false);
g_PLID = 1;
SH_ADD_HOOK_STATICFUNC(Test, Func2, pInst, Handler_Func2, true);
SH_ADD_HOOK_STATICFUNC(Test, Func3, pInst, Handler_Func3, false);
g_PLID = 2;
SH_ADD_HOOK_STATICFUNC(Test, Func1, pInst, Handler_Func1, false);
SH_ADD_HOOK_STATICFUNC(Test, Func3, pInst, Handler_Func3, false);
g_PLID = 3;
SH_ADD_HOOK_STATICFUNC(Test, Func1, pInst, Handler_Func1, false);
SH_ADD_HOOK_STATICFUNC(Test, Func2, pInst, Handler_Func2, true);
pInst->Func1();
pInst->Func2();
pInst->Func3();
CHECK_STATES((&g_States,
new State_Func1H_Called,
new State_Func1H_Called,
new State_Func1H_Called,
new State_Func1_Called,
new State_Func2_Called,
new State_Func2H_Called,
new State_Func2H_Called,
new State_Func2H_Called,
new State_Func3H_Called,
new State_Func3H_Called,
new State_Func3H_Called,
new State_Func3_Called,
NULL), "Part 3.1");
ADD_STATE(State_PluginInUse(1, g_SHImpl.IsPluginInUse(1)));
ADD_STATE(State_PluginInUse(2, g_SHImpl.IsPluginInUse(2)));
ADD_STATE(State_PluginInUse(3, g_SHImpl.IsPluginInUse(3)));
ADD_STATE(State_PluginInUse(4, g_SHImpl.IsPluginInUse(4)));
CHECK_STATES((&g_States,
new State_PluginInUse(1, true),
new State_PluginInUse(2, true),
new State_PluginInUse(3, true),
new State_PluginInUse(4, false),
NULL), "Part 3.2");
// Unload plugins one by one
g_SHImpl.PausePlugin(3);
pInst->Func1();
pInst->Func2();
pInst->Func3();
CHECK_STATES((&g_States,
new State_Func1H_Called,
new State_Func1H_Called,
new State_Func1_Called,
new State_Func2_Called,
new State_Func2H_Called,
new State_Func2H_Called,
new State_Func3H_Called,
new State_Func3H_Called,
new State_Func3_Called,
NULL), "Part 3.3.1");
ADD_STATE(State_PluginInUse(1, g_SHImpl.IsPluginInUse(1)));
ADD_STATE(State_PluginInUse(2, g_SHImpl.IsPluginInUse(2)));
ADD_STATE(State_PluginInUse(3, g_SHImpl.IsPluginInUse(3)));
ADD_STATE(State_PluginInUse(4, g_SHImpl.IsPluginInUse(4)));
CHECK_STATES((&g_States,
new State_PluginInUse(1, true),
new State_PluginInUse(2, true),
new State_PluginInUse(3, true),
new State_PluginInUse(4, false),
NULL), "Part 3.3.2");
g_SHImpl.PausePlugin(2);
pInst->Func1();
pInst->Func2();
pInst->Func3();
CHECK_STATES((&g_States,
new State_Func1H_Called,
new State_Func1_Called,
new State_Func2_Called,
new State_Func2H_Called,
new State_Func3H_Called,
new State_Func3_Called,
NULL), "Part 3.4.1");
ADD_STATE(State_PluginInUse(1, g_SHImpl.IsPluginInUse(1)));
ADD_STATE(State_PluginInUse(2, g_SHImpl.IsPluginInUse(2)));
ADD_STATE(State_PluginInUse(3, g_SHImpl.IsPluginInUse(3)));
ADD_STATE(State_PluginInUse(4, g_SHImpl.IsPluginInUse(4)));
CHECK_STATES((&g_States,
new State_PluginInUse(1, true),
new State_PluginInUse(2, true),
new State_PluginInUse(3, true),
new State_PluginInUse(4, false),
NULL), "Part 3.4.2");
g_SHImpl.PausePlugin(1);
pInst->Func1();
pInst->Func2();
pInst->Func3();
CHECK_STATES((&g_States,
new State_Func1_Called,
new State_Func2_Called,
new State_Func3_Called,
NULL), "Part 3.5.1");
ADD_STATE(State_PluginInUse(1, g_SHImpl.IsPluginInUse(1)));
ADD_STATE(State_PluginInUse(2, g_SHImpl.IsPluginInUse(2)));
ADD_STATE(State_PluginInUse(3, g_SHImpl.IsPluginInUse(3)));
ADD_STATE(State_PluginInUse(4, g_SHImpl.IsPluginInUse(4)));
CHECK_STATES((&g_States,
new State_PluginInUse(1, true),
new State_PluginInUse(2, true),
new State_PluginInUse(3, true),
new State_PluginInUse(4, false),
NULL), "Part 3.5.2");
g_SHImpl.UnpausePlugin(1);
g_SHImpl.UnpausePlugin(2);
g_SHImpl.UnpausePlugin(3);
ADD_STATE(State_PluginInUse(1, g_SHImpl.IsPluginInUse(1)));
ADD_STATE(State_PluginInUse(2, g_SHImpl.IsPluginInUse(2)));
ADD_STATE(State_PluginInUse(3, g_SHImpl.IsPluginInUse(3)));
ADD_STATE(State_PluginInUse(4, g_SHImpl.IsPluginInUse(4)));
CHECK_STATES((&g_States,
new State_PluginInUse(1, true),
new State_PluginInUse(2, true),
new State_PluginInUse(3, true),
new State_PluginInUse(4, false),
NULL), "Part 3.6");
pInst->Func1();
pInst->Func2();
pInst->Func3();
CHECK_STATES((&g_States,
new State_Func1H_Called,
new State_Func1H_Called,
new State_Func1H_Called,
new State_Func1_Called,
new State_Func2_Called,
new State_Func2H_Called,
new State_Func2H_Called,
new State_Func2H_Called,
new State_Func3H_Called,
new State_Func3H_Called,
new State_Func3H_Called,
new State_Func3_Called,
NULL), "Part 3.7");
// 4) Shutdown :)
g_SHImpl.CompleteShutdown();
pInst->Func1();
pInst->Func2();
pInst->Func3();
CHECK_STATES((&g_States,
new State_Func1_Called,
new State_Func2_Called,
new State_Func3_Called,
NULL), "Part 4");
return true;
}

View File

@ -14,6 +14,7 @@
#include <typeinfo>
#include <stdarg.h>
#include <iostream>
#include <string>
extern bool g_Verbose;
@ -31,6 +32,8 @@ namespace
{
return (typeid(other) == typeid(this)) ? true : false;
}
virtual void Dump() = 0;
};
typedef std::list<State*> StateList;
@ -38,6 +41,12 @@ namespace
#define ADD_STATE(name) g_States.push_back(new name)
void DumpStates(StateList *sl)
{
for (StateList::iterator iter = sl->begin(); iter != sl->end(); ++iter)
(*iter)->Dump();
}
bool StatesOk(StateList *sl, ...)
{
StateList requiredstates;
@ -54,6 +63,14 @@ namespace
if (requiredstates.size() != sl->size())
{
if (g_Verbose)
{
std::cout << std::endl << "FAIL: Should be:" << std::endl;
DumpStates(&requiredstates);
std::cout << std::endl << "FAIL: Is:" << std::endl;
DumpStates(sl);
}
for (StateList::iterator iter = requiredstates.begin(); iter != requiredstates.end(); ++iter)
delete *iter;
for (StateList::iterator iter = sl->begin(); iter != sl->end(); ++iter)
@ -86,7 +103,11 @@ namespace
//#define CHECK_STATES(mwah, myerr) if (!StatesOk mwah) { error=myerr; return false; } else if (g_Verbose) { std::cout << "No error: " << myerr << std::endl; }
#define CHECK_STATES(mwah, myerr) if (!StatesOk mwah) { error=myerr; return false; }
#define MAKE_STATE(name) struct name : State {};
#define MAKE_STATE(name) struct name : State { \
virtual void Dump() { \
std::cout << " " << #name << std::endl; } \
};
#define MAKE_STATE_1(name, p1_type) struct name : State { \
p1_type m_Param1; \
name(p1_type param1) : m_Param1(param1) {} \
@ -96,6 +117,8 @@ namespace
return false; \
return other2->m_Param1 == m_Param1;\
} \
virtual void Dump() { \
std::cout << " " << #name << "; Param1=" << m_Param1 << std::endl; } \
}
#define MAKE_STATE_2(name, p1_type, p2_type) struct name : State { \
@ -108,6 +131,8 @@ namespace
return false; \
return other2->m_Param1 == m_Param1 && other2->m_Param2 == m_Param2;\
} \
virtual void Dump() { \
std::cout << " " << #name << "; Param1=" << m_Param1 << "; Param2=" << m_Param2 << std::endl; } \
}
#endif