@@ -37,12 +37,7 @@ namespace HttpServer
3737 socket_handle = handle;
3838 }
3939
40- Socket::~Socket ()
41- {
42-
43- }
44-
45- int Socket::open ()
40+ System::native_socket_type Socket::open ()
4641 {
4742 close ();
4843
@@ -118,6 +113,18 @@ namespace HttpServer
118113 return -1 ;
119114 }
120115
116+ bool Socket::nonblock (bool isNonBlock)
117+ {
118+ #ifdef WIN32
119+ unsigned long value = isNonBlock;
120+ return 0 == ioctlsocket (socket_handle, FIONBIO, &value);
121+ #elif POSIX
122+ return -1 != fcntl (socket_handle, F_SETFL, isNonBlock ? O_NONBLOCK : O_SYNC);
123+ #else
124+ #error "Undefine platform"
125+ #endif
126+ }
127+
121128 size_t Socket::recv (std::vector<std::string::value_type> &buf) const
122129 {
123130 #ifdef WIN32
@@ -129,6 +136,47 @@ namespace HttpServer
129136 #endif
130137 }
131138
139+ size_t Socket::nonblock_recv (std::vector<std::string::value_type> &buf, const std::chrono::milliseconds &timeWait) const
140+ {
141+ #ifdef WIN32
142+ fd_set readset;
143+ FD_ZERO (&readset);
144+ FD_SET (socket_handle, &readset);
145+
146+ long seconds = timeWait.count () / 1000 ;
147+ timeval timeout {seconds, (timeWait.count () - seconds * 1000 ) * 1000 };
148+
149+ if (0 < select (socket_handle + 1 , &readset, nullptr , nullptr , &timeout) )
150+ {
151+ if (FD_ISSET (socket_handle, &readset) )
152+ {
153+ return ::recv (socket_handle, buf.data (), buf.size (), 0 );
154+ }
155+ }
156+
157+ return std::numeric_limits<size_t >::max ();
158+ #elif POSIX
159+ fd_set readset;
160+ FD_ZERO (&readset);
161+ FD_SET (socket_handle, &readset);
162+
163+ long seconds = timeWait.count () / 1000 ;
164+ timeval timeout {seconds, (timeWait.count () - seconds * 1000 ) * 1000 };
165+
166+ if (0 < select (socket_handle + 1 , &readset, nullptr , nullptr , &timeout) )
167+ {
168+ if (FD_ISSET (socket_handle, &readset) )
169+ {
170+ return ::recv (socket_handle, buf.data (), buf.size (), MSG_NOSIGNAL);
171+ }
172+ }
173+
174+ return std::numeric_limits<size_t >::max ();
175+ #else
176+ #error "Undefine platform"
177+ #endif
178+ }
179+
132180 size_t Socket::send (const std::string &buf) const
133181 {
134182 #ifdef WIN32
@@ -140,9 +188,102 @@ namespace HttpServer
140188 #endif
141189 }
142190
191+ size_t Socket::send (const std::vector<std::string::value_type> &buf, const size_t length) const
192+ {
193+ #ifdef WIN32
194+ return ::send (socket_handle, buf.data (), length, 0 );
195+ #elif POSIX
196+ return ::send (socket_handle, buf.data (), length, MSG_WAITALL | MSG_NOSIGNAL);
197+ #else
198+ #error "Undefine platform"
199+ #endif
200+ }
201+
202+ size_t Socket::nonblock_send (const std::string &buf, const std::chrono::milliseconds &timeWait) const
203+ {
204+ #ifdef WIN32
205+ fd_set writeset;
206+ FD_ZERO (&writeset);
207+ FD_SET (socket_handle, &writeset);
208+
209+ long seconds = timeWait.count () / 1000 ;
210+ timeval timeout {seconds, (timeWait.count () - seconds * 1000 ) * 1000 };
211+
212+ if (0 < select (socket_handle + 1 , nullptr , &writeset, nullptr , &timeout) )
213+ {
214+ if (FD_ISSET (socket_handle, &writeset) )
215+ {
216+ return ::send (socket_handle, buf.data (), buf.length (), 0 );
217+ }
218+ }
219+
220+ return std::numeric_limits<size_t >::max ();
221+ #elif POSIX
222+ fd_set writeset;
223+ FD_ZERO (&writeset);
224+ FD_SET (socket_handle, &writeset);
225+
226+ long seconds = timeWait.count () / 1000 ;
227+ timeval timeout {seconds, (timeWait.count () - seconds * 1000 ) * 1000 };
228+
229+ if (0 < select (socket_handle + 1 , nullptr , &writeset, nullptr , &timeout) )
230+ {
231+ if (FD_ISSET (socket_handle, &writeset) )
232+ {
233+ return ::send (socket_handle, buf.data (), buf.length (), MSG_NOSIGNAL);
234+ }
235+ }
236+
237+ return std::numeric_limits<size_t >::max ();
238+ #else
239+ #error "Undefine platform"
240+ #endif
241+ }
242+
243+ size_t Socket::nonblock_send (const std::vector<std::string::value_type> &buf, const size_t length, const std::chrono::milliseconds &timeWait) const
244+ {
245+ #ifdef WIN32
246+ fd_set writeset;
247+ FD_ZERO (&writeset);
248+ FD_SET (socket_handle, &writeset);
249+
250+ long seconds = timeWait.count () / 1000 ;
251+ timeval timeout {seconds, (timeWait.count () - seconds * 1000 ) * 1000 };
252+
253+ if (0 < select (socket_handle + 1 , nullptr , &writeset, nullptr , &timeout) )
254+ {
255+ if (FD_ISSET (socket_handle, &writeset) )
256+ {
257+ return ::send (socket_handle, buf.data (), length, 0 );
258+ }
259+ }
260+
261+ return std::numeric_limits<size_t >::max ();
262+ #elif POSIX
263+ fd_set writeset;
264+ FD_ZERO (&writeset);
265+ FD_SET (socket_handle, &writeset);
266+
267+ long seconds = timeWait.count () / 1000 ;
268+ timeval timeout {seconds, (timeWait.count () - seconds * 1000 ) * 1000 };
269+
270+ if (0 < select (socket_handle + 1 , nullptr , &writeset, nullptr , &timeout) )
271+ {
272+ if (FD_ISSET (socket_handle, &writeset) )
273+ {
274+ return ::send (socket_handle, buf.data (), length, MSG_WAITALL | MSG_NOSIGNAL);
275+ }
276+ }
277+
278+ return std::numeric_limits<size_t >::max ();
279+ #else
280+ #error "Undefine platform"
281+ #endif
282+ }
283+
143284 Socket &Socket::operator =(const Socket s)
144285 {
145286 socket_handle = s.socket_handle ;
146287 return *this ;
147288 }
148- };
289+ };
0 commit comments