00001 /* $Id$ */ 00002 00003 /* 00004 * This file is part of OpenTTD. 00005 * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2. 00006 * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 00007 * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see <http://www.gnu.org/licenses/>. 00008 */ 00009 00014 #ifdef ENABLE_NETWORK 00015 00016 #include "../../stdafx.h" 00017 #include "../../thread/thread.h" 00018 00019 #include "tcp.h" 00020 00022 static SmallVector<TCPConnecter *, 1> _tcp_connecters; 00023 00028 TCPConnecter::TCPConnecter(const NetworkAddress &address) : 00029 connected(false), 00030 aborted(false), 00031 killed(false), 00032 sock(INVALID_SOCKET), 00033 address(address) 00034 { 00035 *_tcp_connecters.Append() = this; 00036 if (!ThreadObject::New(TCPConnecter::ThreadEntry, this, &this->thread)) { 00037 this->Connect(); 00038 } 00039 } 00040 00042 void TCPConnecter::Connect() 00043 { 00044 this->sock = this->address.Connect(); 00045 if (this->sock == INVALID_SOCKET) { 00046 this->aborted = true; 00047 } else { 00048 this->connected = true; 00049 } 00050 } 00051 00056 /* static */ void TCPConnecter::ThreadEntry(void *param) 00057 { 00058 static_cast<TCPConnecter*>(param)->Connect(); 00059 } 00060 00067 /* static */ void TCPConnecter::CheckCallbacks() 00068 { 00069 for (TCPConnecter **iter = _tcp_connecters.Begin(); iter < _tcp_connecters.End(); /* nothing */) { 00070 TCPConnecter *cur = *iter; 00071 if ((cur->connected || cur->aborted) && cur->killed) { 00072 _tcp_connecters.Erase(iter); 00073 if (cur->sock != INVALID_SOCKET) closesocket(cur->sock); 00074 delete cur; 00075 continue; 00076 } 00077 if (cur->connected) { 00078 _tcp_connecters.Erase(iter); 00079 cur->OnConnect(cur->sock); 00080 delete cur; 00081 continue; 00082 } 00083 if (cur->aborted) { 00084 _tcp_connecters.Erase(iter); 00085 cur->OnFailure(); 00086 delete cur; 00087 continue; 00088 } 00089 iter++; 00090 } 00091 } 00092 00094 /* static */ void TCPConnecter::KillAll() 00095 { 00096 for (TCPConnecter **iter = _tcp_connecters.Begin(); iter != _tcp_connecters.End(); iter++) (*iter)->killed = true; 00097 } 00098 00099 #endif /* ENABLE_NETWORK */