source: cheroxy/trunk/src/CRXSocket.cpp@ 14

Last change on this file since 14 was 14, checked in by cheese, 12 years ago

#1 add timeout to socket connection and fix test label in makefile

File size: 7.8 KB
Line 
1/**
2 * CRXSocket.cpp
3 */
4#include "CRXSocket.h"
5
6#include <string.h>
7
8#ifdef _WIN32
9# pragma comment (lib, "ws2_32.lib")
10# define close(__socket) closesocket(__socket)
11typedef int socklen_t;
12#endif
13
14bool CRXSocket::mInitialized = false;
15
16CRXSocket::CRXSocket (int aSocket)
17 : mSocket (aSocket)
18{
19 /*----------------------------------------------------------------*/
20 memset ((void *)&mAddress, 0x0, sizeof (struct sockaddr_in));
21
22 if (!CRXSocket::IsInitialized ())
23 CRXSocket::Initialize ();
24 /*----------------------------------------------------------------*/
25}
26
27CRXSocket::~CRXSocket (void)
28{
29 /*----------------------------------------------------------------*/
30 Close ();
31 /*----------------------------------------------------------------*/
32}
33
34void
35CRXSocket::Attach (int aSocket)
36{
37 /*----------------------------------------------------------------*/
38 mSocket = aSocket;
39 /*----------------------------------------------------------------*/
40}
41
42int
43CRXSocket::Detach (void)
44{
45 int aSocket = mSocket;
46
47 /*----------------------------------------------------------------*/
48 mSocket = 0;
49
50 /*----------------------------------------------------------------*/
51 return aSocket;
52}
53
54void
55CRXSocket::Close (void)
56{
57 /*----------------------------------------------------------------*/
58 if (mSocket <= 0)
59 return ;
60
61 close (mSocket);
62 mSocket = 0;
63 /*----------------------------------------------------------------*/
64}
65
66CRXSocket::operator int (void) const
67{
68 /*----------------------------------------------------------------*/
69 /*----------------------------------------------------------------*/
70 return mSocket;
71}
72
73CRXSocket &
74CRXSocket::operator = (int aSocket)
75{
76 /*----------------------------------------------------------------*/
77 Attach (aSocket);
78 /*----------------------------------------------------------------*/
79 return *this;
80}
81
82int
83CRXSocket::Initialize (void)
84{
85 int aResult = 0;
86
87 /*----------------------------------------------------------------*/
88 if (CRXSocket::IsInitialized ())
89 return aResult;
90
91#ifdef WIN32
92 WSADATA aWinSockData;
93
94 aResult = WSAStartup (MAKEWORD (2, 0), &aWinSockData);
95 if (aResult != 0)
96 {
97 return ERROR_TCPSOCKET_FAILED_TO_INITIALIZE;
98 }
99#endif
100
101 mInitialized = true;
102
103 /*----------------------------------------------------------------*/
104 return aResult;
105}
106
107void
108CRXSocket::Finalize (void)
109{
110 /*----------------------------------------------------------------*/
111#ifdef WIN32
112 WSACleanup ();
113#endif
114 /*----------------------------------------------------------------*/
115}
116
117bool
118CRXSocket::IsInitialized (void)
119{
120 /*----------------------------------------------------------------*/
121 /*----------------------------------------------------------------*/
122 return mInitialized;
123}
124
125bool
126CRXSocket::IsReady (void) const
127{
128 /*----------------------------------------------------------------*/
129 /*----------------------------------------------------------------*/
130 return IsInitialized () && IsCreated ();
131}
132
133bool
134CRXSocket::IsCreated (void) const
135{
136 /*----------------------------------------------------------------*/
137 /*----------------------------------------------------------------*/
138 return mSocket > 0 ? true : false;
139}
140
141int
142CRXSocket::CreateSocket (void)
143{
144 int aResult = -1;
145
146 /*----------------------------------------------------------------*/
147 if (!IsInitialized () || IsCreated ())
148 return ERROR_TCPSOCKET_ALREADY_IN_USE;
149
150 aResult = socket (PF_INET, SOCK_STREAM, IPPROTO_TCP);
151 if (aResult < 0)
152 {
153 }
154
155 mSocket = aResult;
156
157 /*----------------------------------------------------------------*/
158 return aResult;
159}
160
161int
162CRXSocket::Connect (const std::string aUrl,
163 const unsigned short aPort,
164 const int aTimeout)
165{
166 int aResult = -1;
167 struct hostent * aHostEnt;
168
169#ifndef _WIN32
170 struct timeval aTimeVal;
171 aTimeVal.tv_sec = aTimeout;
172 aTimeVal.tv_usec= 0;
173#else
174 int aTimeMilliSec = aTimeout * 1000;
175#endif
176
177 /*----------------------------------------------------------------*/
178 aResult = CreateSocket ();
179 if (aResult < 0)
180 {
181 return aResult;
182 }
183
184 mAddress.sin_family = AF_INET;
185 mAddress.sin_port = htons (aPort);
186 mAddress.sin_addr.s_addr = inet_addr (aUrl.c_str ());
187
188 if (mAddress.sin_addr.s_addr == (unsigned int)-1)
189 {
190 aHostEnt = gethostbyname (aUrl.c_str ());
191 if (aHostEnt == NULL)
192 {
193 return ERROR_TCPSOCKET_FAILED_TO_GET_HOSTNAME;
194 }
195 mAddress.sin_family = aHostEnt->h_addrtype;
196 memcpy (&(mAddress.sin_addr.s_addr), aHostEnt->h_addr, aHostEnt->h_length);
197 }
198
199 if (aTimeout > TCPSOCKET_NO_TIMEOUT)
200 {
201#ifdef _WIN32
202 aResult = setsockopt (mSocket,
203 SOL_SOCKET,
204 SO_RCVTIMEO,
205 (char *) &aTimeMilliSec,
206 sizeof (aTimeMilliSec));
207#else
208 aResult = setsockopt (mSocket,
209 SOL_SOCKET,
210 SO_RCVTIMEO,
211 &aTimeVal,
212 (socklen_t) sizeof (aTimeVal));
213#endif
214 if (aResult < 0)
215 {
216 return ERROR_TCPSOCKET_FAILED_TO_SETSOCKOPT;
217 }
218 }
219
220 aResult = connect (mSocket, (struct sockaddr*) &mAddress, sizeof (mAddress));
221 if (aResult < 0)
222 {
223 return ERROR_TCPSOCKET_FAILED_TO_CONNECT;
224 }
225
226 /*----------------------------------------------------------------*/
227 return aResult;
228}
229
230int
231CRXSocket::CreateServer (const unsigned short aPort,
232 const int aBacklog,
233 struct sockaddr_in * aAddress)
234{
235 int aResult = -1;
236
237 /*----------------------------------------------------------------*/
238 aResult = CreateSocket ();
239 if (aResult < 0)
240 {
241 return aResult;
242 }
243
244 mAddress.sin_family = AF_INET;
245 mAddress.sin_addr.s_addr= htonl (INADDR_ANY);
246 mAddress.sin_port = htons (aPort);
247
248 aResult = bind (mSocket, (struct sockaddr *)&mAddress, sizeof (struct sockaddr));
249 if (aResult < 0)
250 {
251 return ERROR_TCPSOCKET_FAILED_TO_BIND;
252 }
253
254 aResult = listen (mSocket, aBacklog);
255 if (aResult < 0)
256 {
257 return ERROR_TCPSOCKET_FAILED_TO_LISTEN;
258 }
259
260 if (aAddress != NULL)
261 {
262 memset ((void *)aAddress, 0x0, sizeof (struct sockaddr_in));
263 memcpy ((void *)aAddress, (void *)&mAddress, sizeof (struct sockaddr_in));
264 }
265
266 /*----------------------------------------------------------------*/
267 return aResult;
268}
269
270int
271CRXSocket::Accept (struct sockaddr_in * aRemoteAddress,
272 int * aAddressLength)
273{
274 int aResult = -1;
275
276 struct sockaddr_in aAddress;
277 socklen_t aLength = sizeof (aAddress);
278
279 /*----------------------------------------------------------------*/
280 if (!IsReady ()) return ERROR_TCPSOCKET_NOT_READY;
281
282 aResult = accept (mSocket, (struct sockaddr *) &aAddress, &aLength);
283 if (aResult < 0)
284 {
285 return aResult;
286 }
287
288 if (aRemoteAddress != NULL)
289 {
290 memset ((void *)aRemoteAddress, 0x0, sizeof (struct sockaddr_in));
291 memcpy ((void *)aRemoteAddress, (void *)&aAddress, sizeof (struct sockaddr_in));
292 }
293
294 if (aAddressLength != NULL)
295 *aAddressLength = aLength;
296
297 /*----------------------------------------------------------------*/
298 return aResult;
299}
300
301int
302CRXSocket::Send (char * aBuffer,
303 int aSize)
304{
305 int aResult = -1;
306
307 /*----------------------------------------------------------------*/
308 if (!IsReady ()) return ERROR_TCPSOCKET_NOT_READY;
309
310 aResult = send (mSocket, aBuffer, aSize, 0);
311 if (aResult != aSize)
312 {
313 return ERROR_TCPSOCKET_FAILED_TO_SEND;
314 }
315
316 /*----------------------------------------------------------------*/
317 return aResult;
318}
319
320int
321CRXSocket::Receive (char * aBuffer,
322 int aSize)
323{
324 int aResult = -1;
325
326 /*----------------------------------------------------------------*/
327 if (!IsReady ()) return ERROR_TCPSOCKET_NOT_READY;
328
329 aResult = recv (mSocket, aBuffer, aSize, 0);
330 if (aResult < 0)
331 {
332 return ERROR_TCPSOCKET_FAILED_TO_RECEIVE;
333 }
334
335 /*----------------------------------------------------------------*/
336 return aResult;
337}
Note: See TracBrowser for help on using the repository browser.