Client.cpp 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182
  1. #include "Client.h"
  2. #include "../lib/Connection.h"
  3. #include "../lib/CThreadHelper.h"
  4. #include "../lib/CGameState.h"
  5. #include "../lib/BattleAction.h"
  6. #include "../lib/CGameInterface.h"
  7. #include "CheckTime.h"
  8. #include "../lib/BattleState.h"
  9. //#define NOT_LIB
  10. #include "../lib/RegisterTypes.cpp"
  11. template <typename T> class CApplyOnCL;
  12. class CBaseForCLApply
  13. {
  14. public:
  15. virtual void applyOnClAfter(CClient *cl, void *pack) const =0;
  16. virtual void applyOnClBefore(CClient *cl, void *pack) const =0;
  17. virtual ~CBaseForCLApply(){}
  18. template<typename U> static CBaseForCLApply *getApplier(const U * t=NULL)
  19. {
  20. return new CApplyOnCL<U>;
  21. }
  22. };
  23. template <typename T> class CApplyOnCL : public CBaseForCLApply
  24. {
  25. public:
  26. void applyOnClAfter(CClient *cl, void *pack) const
  27. {
  28. T *ptr = static_cast<T*>(pack);
  29. ptr->applyCl(cl);
  30. }
  31. void applyOnClBefore(CClient *cl, void *pack) const
  32. {
  33. T *ptr = static_cast<T*>(pack);
  34. ptr->applyFirstCl(cl);
  35. }
  36. };
  37. static CApplier<CBaseForCLApply> *applier = NULL;
  38. void CClient::run()
  39. {
  40. setThreadName(-1, "CClient::run");
  41. try
  42. {
  43. CPack *pack = NULL;
  44. while(!terminate)
  45. {
  46. pack = serv->retreivePack(); //get the package from the server
  47. if (terminate)
  48. {
  49. delete pack;
  50. pack = NULL;
  51. break;
  52. }
  53. handlePack(pack);
  54. pack = NULL;
  55. }
  56. }
  57. catch (const std::exception& e)
  58. {
  59. tlog3 << "Lost connection to server, ending listening thread!\n";
  60. tlog1 << e.what() << std::endl;
  61. if(!terminate) //rethrow (-> boom!) only if closing connection was unexpected
  62. {
  63. tlog1 << "Something wrong, lost connection while game is still ongoing...\n";
  64. throw;
  65. }
  66. }
  67. }
  68. void CClient::handlePack( CPack * pack )
  69. {
  70. CBaseForCLApply *apply = applier->apps[typeList.getTypeID(pack)]; //find the applier
  71. if(apply)
  72. {
  73. apply->applyOnClBefore(this,pack);
  74. tlog5 << "\tMade first apply on cl\n";
  75. gs->apply(pack);
  76. tlog5 << "\tApplied on gs\n";
  77. apply->applyOnClAfter(this,pack);
  78. tlog5 << "\tMade second apply on cl\n";
  79. }
  80. else
  81. {
  82. tlog1 << "Message cannot be applied, cannot find applier! TypeID " << typeList.getTypeID(pack) << std::endl;
  83. }
  84. delete pack;
  85. }
  86. void CClient::requestMoveFromAI(const CStack *s)
  87. {
  88. boost::thread(&CClient::requestMoveFromAIWorker, this, s);
  89. }
  90. void CClient::requestMoveFromAIWorker(const CStack *s)
  91. {
  92. BattleAction ba;
  93. try
  94. {
  95. boost::shared_lock<boost::shared_mutex> shl(*gs->mx);
  96. Bomb *b = new Bomb(MAKE_DECIDION_TIME + HANGUP_TIME, "activeStack timer");
  97. CheckTime timer;
  98. ba = ai->activeStack(s);
  99. postDecisionCall(timer.timeSinceStart());
  100. b->disarm();
  101. }
  102. catch(...)
  103. {
  104. tlog0 << "AI thrown an exception!\n";
  105. //TODO: disqualify?
  106. ba = BattleAction::makeDefend(s);
  107. }
  108. try
  109. {
  110. MakeAction temp_action(ba);
  111. tlog0 << "Checking if action looks valid... ";
  112. bool valid = gs->isValidAction(temp_action, true);
  113. if(gs->curB->sides[temp_action.ba.side] != color)
  114. {
  115. tlog1 << "Wrong side set!\n";
  116. valid = false;
  117. }
  118. if(!valid)
  119. {
  120. tlog1 << "Warning: action seems to be invalid! Stack will defend\n";
  121. temp_action.ba = BattleAction::makeDefend(s);
  122. }
  123. else
  124. tlog1 << "Doesn't look suspicious.\n";
  125. *serv << &temp_action;
  126. }
  127. catch(...)
  128. {
  129. tlog1 << "Failed sending action!\n";
  130. }
  131. }
  132. CClient::CClient()
  133. {
  134. gs = NULL;
  135. serv = NULL;
  136. ai = NULL;
  137. curbaction = NULL;
  138. terminate = false;
  139. color = 250;
  140. applier = new CApplier<CBaseForCLApply>;
  141. registerTypes2(*applier);
  142. }
  143. void CClient::commenceTacticPhaseForInt(CBattleGameInterface *battleInt)
  144. {
  145. setThreadName(-1, "CClient::commenceTacticPhaseForInt");
  146. try
  147. {
  148. boost::shared_lock<boost::shared_mutex> shl(*gs->mx);
  149. Bomb *b = new Bomb(TACTICS_TIME + HANGUP_TIME, "yourTacticPhase timer");
  150. CheckTime timer;
  151. battleInt->yourTacticPhase(gs->curB->tacticDistance);
  152. postDecisionCall(timer.timeSinceStart(), "AI was using tactics ordering", TACTICS_TIME);
  153. b->disarm();
  154. if(gs && !!gs->curB && gs->curB->tacticDistance) //while awaiting for end of tactics phase, many things can happen (end of battle... or game)
  155. {
  156. MakeAction ma(BattleAction::makeEndOFTacticPhase(battleInt->playerID));
  157. serv->sendPack(ma);
  158. }
  159. } HANDLE_EXCEPTION
  160. }