2
0

server_main.cpp 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148
  1. #include <iostream>
  2. #include <string>
  3. #include <boost/bind.hpp>
  4. #include <boost/asio.hpp>
  5. #include "../global.h"
  6. #include "../lib/Connection.h"
  7. #include "../CGameState.h"
  8. #include "zlib.h"
  9. #include <boost/thread.hpp>
  10. #include <boost/crc.hpp>
  11. #include <boost/serialization/split_member.hpp>
  12. #include "../StartInfo.h"
  13. std::string NAME = NAME_VER + std::string(" (server)");
  14. using boost::asio::ip::tcp;
  15. using namespace boost;
  16. using namespace boost::asio;
  17. using namespace boost::asio::ip;
  18. mutex smx1;
  19. class CVCMIServer
  20. {
  21. CGameState *gs;
  22. tcp::acceptor acceptor;
  23. std::map<int,CConnection*> connections;
  24. std::set<CConnection*> conns;
  25. ui32 seed;
  26. public:
  27. CVCMIServer(io_service& io_service)
  28. : acceptor(io_service, tcp::endpoint(tcp::v4(), 3030))
  29. {
  30. start();
  31. }
  32. void setUpConnection(CConnection *c, std::string mapname, si32 checksum)
  33. {
  34. ui8 quantity, pom;
  35. (*c) << mapname << checksum << seed;
  36. (*c) >> quantity;
  37. for(int i=0;i<quantity;i++)
  38. {
  39. (*c) >> pom;
  40. smx1.lock();
  41. connections[pom] = c;
  42. conns.insert(c);
  43. smx1.unlock();
  44. }
  45. }
  46. void newGame(CConnection &c)
  47. {
  48. boost::system::error_code error;
  49. StartInfo *si = new StartInfo;
  50. ui8 clients;
  51. std::string mapname;
  52. c >> clients;
  53. c >> mapname;
  54. //getting map
  55. gzFile map = gzopen(mapname.c_str(),"rb");
  56. if(!map){ c << int8_t(1); return; }
  57. std::vector<unsigned char> mapstr; int pom;
  58. while((pom=gzgetc(map))>=0)
  59. {
  60. mapstr.push_back(pom);
  61. }
  62. gzclose(map);
  63. //map is decompressed
  64. c << int8_t(0); //OK!
  65. gs = new CGameState();
  66. gs->scenarioOps = si;
  67. c > *si; //get start options
  68. boost::crc_32_type result;
  69. result.process_bytes(&(*mapstr.begin()),mapstr.size());
  70. int checksum = result.checksum();
  71. std::cout << "Checksum:" << checksum << std::endl;
  72. CConnection* cc; tcp::socket * ss;
  73. for(int i=0; i<clients; i++)
  74. {
  75. if(!i)
  76. {
  77. cc=&c;
  78. }
  79. else
  80. {
  81. tcp::socket * s = new tcp::socket(acceptor.io_service());
  82. acceptor.accept(*s,error);
  83. if(error) //retry
  84. {
  85. std::cout<<"Cannot establish connection - retrying..." << std::endl;
  86. i--;
  87. continue;
  88. }
  89. cc = new CConnection(s,NAME,std::cout);
  90. }
  91. setUpConnection(cc,mapname,checksum);
  92. }
  93. //TODO: wait for other connections
  94. }
  95. void start()
  96. {
  97. srand ( time(NULL) );
  98. seed = rand();
  99. boost::system::error_code error;
  100. std::cout<<"Listening for connections at port " << acceptor.local_endpoint().port() << std::endl;
  101. tcp::socket * s = new tcp::socket(acceptor.io_service());
  102. acceptor.accept(*s,error);
  103. if (error)
  104. {
  105. std::cout<<"Got connection but there is an error " << std::endl;
  106. return;
  107. }
  108. CConnection connection(s,NAME,std::cout);
  109. std::cout<<"Got connection!" << std::endl;
  110. while(1)
  111. {
  112. uint8_t mode;
  113. connection >> mode;
  114. switch (mode)
  115. {
  116. case 0:
  117. connection.socket->close();
  118. exit(0);
  119. break;
  120. case 1:
  121. connection.socket->close();
  122. return;
  123. break;
  124. case 2:
  125. newGame(connection);
  126. break;
  127. }
  128. }
  129. }
  130. };
  131. int _tmain(int argc, _TCHAR* argv[])
  132. {
  133. try
  134. {
  135. io_service io_service;
  136. CVCMIServer server(io_service);
  137. while(1)
  138. server.start();
  139. io_service.run();
  140. }
  141. catch (std::exception& e)
  142. {
  143. std::cerr << e.what() << std::endl;
  144. }
  145. return 0;
  146. }