00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00022 #include "AEngine.h"
00023 #include "AUtil.h"
00024 #include "ASharedFunc.h"
00025 #include "AState.h"
00026
00027 GUID netGuid = { 0x809af2bd, 0x7881, 0x468b, { 0xa5, 0x3c, 0x48, 0xd5, 0x48, 0x69, 0x0, 0xd9 } };
00028
00029
00030 NDX_Connect& net_direct()
00031 {
00032 return AS.net_ndxConnect;
00033 }
00034
00035 void net_runAsServer(string myIP, string myName, int maxNumPlayers)
00036 {
00037 NDX_Connect &net = AS.net_ndxConnect;
00038 if(!net.Create(&netGuid)) throw Error("Can't create DirectPlay");
00039
00040 net.SetGuarenteed(true);
00041 if(!net.ConnectTCPIP( (char*)myIP.c_str() )) throw Error("Can't connect to Server : " + myIP );
00042 if(!net.CreateGame("Aierra Engine Game", (char*)myName.c_str(), maxNumPlayers ))
00043 throw Error("Can't Create Game");
00044
00045 AS.net_isServer = true;
00046 AS.net_myName = myName;
00047 AS.net_serverSendQueue.resize(0);
00048 AS.net_gameFinalized = false;
00049 AS.net_myPlayerNum = -1;
00050 AS.net_isInit = true;
00051 AS.net_isFakeServer = false;
00052 }
00053
00054 void net_runAsFakeServer(string myName, int maxNumPlayers)
00055 {
00056 AS.net_isServer = true;
00057 AS.net_myName = myName;
00058 AS.net_serverSendQueue.resize(0);
00059 AS.net_gameFinalized = false;
00060 AS.net_myPlayerNum = -1;
00061 AS.net_isInit = true;
00062 AS.net_isFakeServer = true;
00063 }
00064
00065 bool net_connectToServer(string ip, string myName)
00066 {
00067 NDX_Connect &net = AS.net_ndxConnect;
00068 if(!net.Create(&netGuid))
00069 {
00070 sys_console() << "Can't create DirectPlay" << endl;
00071 return false;
00072 }
00073
00074 net.SetGuarenteed(true);
00075 if(!net.ConnectTCPIP( (char*)ip.c_str() ))
00076 {
00077 sys_console() << "Can't connect to Server : " << ip << endl;
00078 return false;
00079 }
00080
00081 net.ScanForGames(20,false);
00082 if(net.NumGames>0)
00083 {
00084 if(!net.JoinGame(0, (char*)myName.c_str()))
00085 {
00086 sys_console() << "Can't Join Game" << endl;
00087 return false;
00088 }
00089 }
00090 else
00091 {
00092 sys_console() << "No Game Found on that server" << endl;
00093 return false;
00094 }
00095
00096 AS.net_isServer = false;
00097 AS.net_myName = myName;
00098 AS.net_serverSendQueue.resize(0);
00099 AS.net_myPlayerNum = -1;
00100 AS.net_isInit = true;
00101 return true;
00102 }
00103
00104 void net_acceptMorePlayers()
00105 {
00106 if(AS.net_isFakeServer) return;
00107 if(AS.net_gameFinalized) throw Error("Game already finalized. Can't accept more players");
00108 AS.net_ndxConnect.ScanForPlayers();
00109 }
00110
00111
00112 void net_broadcast( string &msg )
00113 {
00114 if(AS.net_isFakeServer) return;
00115 AS.net_ndxConnect.Send( DPID_ALLPLAYERS, &msg[0], (DWORD)msg.length()+1 );
00116 }
00117
00118 void net_finalizeGame()
00119 {
00120 NDX_Connect &net = AS.net_ndxConnect;
00121 for( int i=0; i<net.NumPlayers; i++ )
00122 {
00123 ostringstream strm;
00124 strm << "Assign <begin_name>" << net.Players[i].Name << "<end_name> " << i;
00125 net_send( strm.str() );
00126
00127 if( AS.net_myName == net.Players[i].Name ) AS.net_myPlayerNum = i;
00128 }
00129
00130
00131 ostringstream strm;
00132 strm << "ServerDPID " << AS.net_ndxConnect.LocalDPID;
00133 net_broadcast( strm.str() );
00134 }
00135
00136 bool net_amIServer()
00137 {
00138 return AS.net_isServer;
00139 }
00140
00141 vector<string> net_getAllPlayers()
00142 {
00143 vector<string> result;
00144
00145 if(AS.net_isFakeServer)
00146 {
00147 result.push_back(AS.net_myName);
00148 return result;
00149 }
00150
00151 NDX_Connect &net = AS.net_ndxConnect;
00152 if(!AS.net_gameFinalized) net.ScanForPlayers();
00153
00154 for( int i=0; i<net.NumPlayers; i++ )
00155 result.push_back( net.Players[i].Name );
00156
00157 return result;
00158 }
00159
00160 void net_send( string msg )
00161 {
00162 if(!AS.net_isInit) return;
00163 msg += "\0";
00164 if(AS.net_isServer)
00165 {
00166 AS.net_serverSendQueue.push_back(msg);
00167 }
00168 else
00169 {
00170 AS.net_ndxConnect.Send( AS.net_serverDPID, &msg[0], (DWORD)msg.length()+1 );
00171 }
00172 }
00173
00174 string net_getPlayerName()
00175 {
00176 return AS.net_myName;
00177 }
00178
00179 int net_getPlayerNumber()
00180 {
00181 return AS.net_myPlayerNum;
00182 }
00183
00184 void net_disconnect()
00185 {
00187 AS.net_ndxConnect.CloseGame();
00188 AS.net_ndxConnect.CloseConnection();
00189 }
00190
00191 string net_recv()
00192 {
00193 if(!AS.net_isInit) return "";
00194 NDX_Connect &net = AS.net_ndxConnect;
00195
00196 if(AS.net_isServer)
00197 {
00198 if( AS.net_serverSendQueue.size()>0 )
00199 {
00200 string s = *AS.net_serverSendQueue.begin();
00201 AS.net_serverSendQueue.pop_front();
00202 net_broadcast(s);
00203 if( s.find("Assign <begin_name>")==0 )
00204 {
00205
00206 sys_console() << s << endl;
00207
00208 s = s.substr(19);
00209 int i = (int)s.find("<end_name>");
00210 string name = s.substr(0,i);
00211
00212
00213 string numStr = s.substr(i+10);
00214 istringstream numStrm(numStr.c_str());
00215 int num;
00216 numStrm >> num;
00217
00218 if( name==AS.net_myName ) AS.net_myPlayerNum = num;
00219 AS.net_mapNameToNum[name] = num;
00220 AS.net_mapNumToName[num] = name;
00221
00222 return net_recv();
00223 }
00224 return s;
00225 }
00226 else if(!AS.net_isFakeServer)
00227 {
00228 if(!net.Receive()) return "";
00229 if(net.FromDPID==DPID_SYSMSG) return net_recv();
00230 string s((char*)net.RBuffer);
00231 net_broadcast(s);
00232 return s;
00233
00234 }
00235 }
00236 else
00237 {
00238 if(!net.Receive()) return "";
00239 if(net.FromDPID==DPID_SYSMSG) return net_recv();
00240 string s((char*)net.RBuffer);
00241 if( s.find("Assign <begin_name>")==0 )
00242 {
00243
00244 sys_console() << s << endl;
00245
00246 s = s.substr(19);
00247 int i = (int)s.find("<end_name>");
00248 string name = s.substr(0,i);
00249
00250
00251 string numStr = s.substr(i+10);
00252 istringstream numStrm(numStr.c_str());
00253 int num;
00254 numStrm >> num;
00255
00256 if( name==AS.net_myName )
00257 {
00258 AS.net_myPlayerNum = num;
00259 sys_console() << "My num is " << num << endl;
00260 }
00261 AS.net_mapNameToNum[name] = num;
00262 AS.net_mapNumToName[num] = name;
00263 sys_console() << "mapping " << name << " to " << num << endl;
00264
00265 return net_recv();
00266 }
00267 else if (s.find("ServerDPID")==0 )
00268 {
00269 string tmp;
00270 istringstream strm(s);
00271 strm >> tmp >> AS.net_serverDPID;
00272 return net_recv();
00273 }
00274
00275 return s;
00276 }
00277
00278 return "";
00279 }
00280
00281 int net_getPlayerNumUsingName(string playerName)
00282 {
00283 map<string,int>::iterator iter = AS.net_mapNameToNum.find(playerName);
00284 if( iter==AS.net_mapNameToNum.end() ) return 0;
00285 return (iter)->second;
00286 }
00287
00288 string net_getPlayerNameUsingNum(int num)
00289 {
00290 map<int,string>::iterator iter = AS.net_mapNumToName.find(num);
00291 if( iter==AS.net_mapNumToName.end() ) return "NoNamePlayer";
00292 return (iter)->second;
00293 }
00294
00295 string net_getSelfIP()
00296 {
00297 static bool init = false;
00298 if(!init)
00299 {
00300 init = true;
00301 WSAData wsa;
00302 WSAStartup( MAKEWORD(1,1), &wsa );
00303 }
00304
00305 char hostName[500];
00306 int rc = gethostname(&hostName[0],499);
00307 if(rc!=0) rc = WSAGetLastError();
00308 assert(rc != WSAEFAULT);
00309 assert(rc != WSANOTINITIALISED );
00310 assert(rc != WSAENETDOWN );
00311 assert(rc != WSAEINPROGRESS );
00312
00313 struct hostent *phost = gethostbyname(hostName);
00314 char oip[50];
00315 for (int i = 0; phost->h_addr_list[i] != 0; ++i)
00316 {
00317 struct in_addr addr;
00318 memcpy(&addr, phost->h_addr_list[i], sizeof(struct in_addr));
00319 strcpy(oip,inet_ntoa(addr));
00320 break;
00321 }
00322
00323 return string(oip);
00324 }
00325