]> git.saurik.com Git - wxWidgets.git/blob - src/common/socket.cpp
no changes, just reformat/indent consistently
[wxWidgets.git] / src / common / socket.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: src/common/socket.cpp
3 // Purpose: Socket handler classes
4 // Authors: Guilhem Lavaux, Guillermo Rodriguez Garcia
5 // Created: April 1997
6 // Copyright: (C) 1999-1997, Guilhem Lavaux
7 // (C) 1999-2000, Guillermo Rodriguez Garcia
8 // (C) 2008 Vadim Zeitlin
9 // RCS_ID: $Id$
10 // License: wxWindows licence
11 /////////////////////////////////////////////////////////////////////////////
12
13 // ==========================================================================
14 // Declarations
15 // ==========================================================================
16
17 // For compilers that support precompilation, includes "wx.h".
18 #include "wx/wxprec.h"
19
20 #ifdef __BORLANDC__
21 #pragma hdrstop
22 #endif
23
24 #if wxUSE_SOCKETS
25
26 #include "wx/socket.h"
27
28 #ifndef WX_PRECOMP
29 #include "wx/object.h"
30 #include "wx/string.h"
31 #include "wx/intl.h"
32 #include "wx/log.h"
33 #include "wx/event.h"
34 #include "wx/app.h"
35 #include "wx/utils.h"
36 #include "wx/timer.h"
37 #include "wx/module.h"
38 #endif
39
40 #include "wx/apptrait.h"
41 #include "wx/sckaddr.h"
42 #include "wx/stopwatch.h"
43 #include "wx/thread.h"
44 #include "wx/evtloop.h"
45
46 #include "wx/private/fd.h"
47 #include "wx/private/socket.h"
48
49 #ifdef __UNIX__
50 #include <errno.h>
51 #endif
52
53 // we use MSG_NOSIGNAL to avoid getting SIGPIPE when sending data to a remote
54 // host which closed the connection if it is available, otherwise we rely on
55 // SO_NOSIGPIPE existency
56 //
57 // this should cover all the current Unix systems (Windows never sends any
58 // signals anyhow) but if we find one that has neither we should explicitly
59 // ignore SIGPIPE for it
60 #ifdef MSG_NOSIGNAL
61 #define wxSOCKET_MSG_NOSIGNAL MSG_NOSIGNAL
62 #else // MSG_NOSIGNAL not available (BSD including OS X)
63 #if defined(__UNIX__) && !defined(SO_NOSIGPIPE)
64 #error "Writing to socket could generate unhandled SIGPIPE."
65 #error "Please post information about your system to wx-dev."
66 #endif
67
68 #define wxSOCKET_MSG_NOSIGNAL 0
69 #endif
70
71 // DLL options compatibility check:
72 #include "wx/build.h"
73 WX_CHECK_BUILD_OPTIONS("wxNet")
74
75 // --------------------------------------------------------------------------
76 // macros and constants
77 // --------------------------------------------------------------------------
78
79 // discard buffer
80 #define MAX_DISCARD_SIZE (10 * 1024)
81
82 #define wxTRACE_Socket _T("wxSocket")
83
84 // --------------------------------------------------------------------------
85 // wxWin macros
86 // --------------------------------------------------------------------------
87
88 IMPLEMENT_CLASS(wxSocketBase, wxObject)
89 IMPLEMENT_CLASS(wxSocketServer, wxSocketBase)
90 IMPLEMENT_CLASS(wxSocketClient, wxSocketBase)
91 IMPLEMENT_CLASS(wxDatagramSocket, wxSocketBase)
92 IMPLEMENT_DYNAMIC_CLASS(wxSocketEvent, wxEvent)
93
94 // ----------------------------------------------------------------------------
95 // private functions
96 // ----------------------------------------------------------------------------
97
98 namespace
99 {
100
101 void SetTimeValFromMS(timeval& tv, unsigned long ms)
102 {
103 tv.tv_sec = (ms / 1000);
104 tv.tv_usec = (ms % 1000) * 1000;
105 }
106
107 } // anonymous namespace
108
109 // --------------------------------------------------------------------------
110 // private classes
111 // --------------------------------------------------------------------------
112
113 class wxSocketState : public wxObject
114 {
115 public:
116 wxSocketFlags m_flags;
117 wxSocketEventFlags m_eventmask;
118 bool m_notify;
119 void *m_clientData;
120
121 public:
122 wxSocketState() : wxObject() {}
123
124 DECLARE_NO_COPY_CLASS(wxSocketState)
125 };
126
127 // wxSocketWaitModeChanger: temporarily change the socket flags affecting its
128 // wait mode
129 class wxSocketWaitModeChanger
130 {
131 public:
132 // temporarily set the flags to include the flag value which may be either
133 // wxSOCKET_NOWAIT or wxSOCKET_WAITALL
134 wxSocketWaitModeChanger(wxSocketBase *socket, int flag)
135 : m_socket(socket),
136 m_oldflags(socket->GetFlags())
137
138 {
139 wxASSERT_MSG( flag == wxSOCKET_WAITALL || flag == wxSOCKET_NOWAIT,
140 "not a wait flag" );
141
142 // preserve wxSOCKET_BLOCK value when switching to wxSOCKET_WAITALL
143 // mode but not when switching to wxSOCKET_NOWAIT as the latter is
144 // incompatible with wxSOCKET_BLOCK
145 if ( flag != wxSOCKET_NOWAIT )
146 flag |= m_oldflags & wxSOCKET_BLOCK;
147
148 socket->SetFlags(flag);
149 }
150
151 ~wxSocketWaitModeChanger()
152 {
153 m_socket->SetFlags(m_oldflags);
154 }
155
156 private:
157 wxSocketBase * const m_socket;
158 const int m_oldflags;
159
160 DECLARE_NO_COPY_CLASS(wxSocketWaitModeChanger)
161 };
162
163 // wxSocketRead/WriteGuard are instantiated before starting reading
164 // from/writing to the socket
165 class wxSocketReadGuard
166 {
167 public:
168 wxSocketReadGuard(wxSocketBase *socket)
169 : m_socket(socket)
170 {
171 wxASSERT_MSG( !m_socket->m_reading, "read reentrancy?" );
172
173 m_socket->m_reading = true;
174 }
175
176 ~wxSocketReadGuard()
177 {
178 m_socket->m_reading = false;
179
180 m_socket->m_impl->ReenableEvents(wxSOCKET_INPUT_FLAG);
181 }
182
183 private:
184 wxSocketBase * const m_socket;
185
186 DECLARE_NO_COPY_CLASS(wxSocketReadGuard)
187 };
188
189 class wxSocketWriteGuard
190 {
191 public:
192 wxSocketWriteGuard(wxSocketBase *socket)
193 : m_socket(socket)
194 {
195 wxASSERT_MSG( !m_socket->m_writing, "write reentrancy?" );
196
197 m_socket->m_writing = true;
198
199 m_socket->m_impl->ReenableEvents(wxSOCKET_OUTPUT_FLAG);
200 }
201
202 ~wxSocketWriteGuard()
203 {
204 m_socket->m_writing = false;
205 }
206
207 private:
208 wxSocketBase * const m_socket;
209
210 DECLARE_NO_COPY_CLASS(wxSocketWriteGuard)
211 };
212
213 // ============================================================================
214 // wxSocketManager
215 // ============================================================================
216
217 wxSocketManager *wxSocketManager::ms_manager = NULL;
218
219 /* static */
220 void wxSocketManager::Set(wxSocketManager *manager)
221 {
222 wxASSERT_MSG( !ms_manager, "too late to set manager now" );
223
224 ms_manager = manager;
225 }
226
227 /* static */
228 void wxSocketManager::Init()
229 {
230 wxASSERT_MSG( !ms_manager, "shouldn't be initialized twice" );
231
232 /*
233 Details: Initialize() creates a hidden window as a sink for socket
234 events, such as 'read completed'. wxMSW has only one message loop
235 for the main thread. If Initialize is called in a secondary thread,
236 the socket window will be created for the secondary thread, but
237 since there is no message loop on this thread, it will never
238 receive events and all socket operations will time out.
239 BTW, the main thread must not be stopped using sleep or block
240 on a semaphore (a bad idea in any case) or socket operations
241 will time out.
242
243 On the Mac side, Initialize() stores a pointer to the CFRunLoop for
244 the main thread. Because secondary threads do not have run loops,
245 adding event notifications to the "Current" loop would have no
246 effect at all, events would never fire.
247 */
248 wxASSERT_MSG( wxIsMainThread(),
249 "sockets must be initialized from the main thread" );
250
251 wxAppConsole * const app = wxAppConsole::GetInstance();
252 wxCHECK_RET( app, "sockets can't be initialized without wxApp" );
253
254 ms_manager = app->GetTraits()->GetSocketManager();
255 }
256
257 // ==========================================================================
258 // wxSocketImpl
259 // ==========================================================================
260
261 wxSocketImpl::wxSocketImpl(wxSocketBase& wxsocket)
262 : m_wxsocket(&wxsocket)
263 {
264 m_fd = INVALID_SOCKET;
265 m_error = wxSOCKET_NOERROR;
266 m_server = false;
267 m_stream = true;
268
269 SetTimeout(wxsocket.GetTimeout() * 1000);
270
271 m_establishing = false;
272 m_reusable = false;
273 m_broadcast = false;
274 m_dobind = true;
275 m_initialRecvBufferSize = -1;
276 m_initialSendBufferSize = -1;
277 }
278
279 wxSocketImpl::~wxSocketImpl()
280 {
281 if ( m_fd != INVALID_SOCKET )
282 Shutdown();
283 }
284
285 bool wxSocketImpl::PreCreateCheck(const wxSockAddressImpl& addr)
286 {
287 if ( m_fd != INVALID_SOCKET )
288 {
289 m_error = wxSOCKET_INVSOCK;
290 return false;
291 }
292
293 if ( !addr.IsOk() )
294 {
295 m_error = wxSOCKET_INVADDR;
296 return false;
297 }
298
299 return true;
300 }
301
302 void wxSocketImpl::PostCreation()
303 {
304 // FreeBSD variants can't use MSG_NOSIGNAL, and instead use a socket option
305 #ifdef SO_NOSIGPIPE
306 EnableSocketOption(SO_NOSIGPIPE);
307 #endif
308
309 if ( m_reusable )
310 EnableSocketOption(SO_REUSEADDR);
311
312 if ( m_broadcast )
313 {
314 wxASSERT_MSG( !m_stream, "broadcasting is for datagram sockets only" );
315
316 EnableSocketOption(SO_BROADCAST);
317 }
318
319 if ( m_initialRecvBufferSize >= 0 )
320 SetSocketOption(SO_RCVBUF, m_initialRecvBufferSize);
321 if ( m_initialSendBufferSize >= 0 )
322 SetSocketOption(SO_SNDBUF, m_initialSendBufferSize);
323
324 // we always put our sockets in unblocked mode and handle blocking
325 // ourselves in DoRead/Write() if wxSOCKET_WAITALL is specified
326 UnblockAndRegisterWithEventLoop();
327 }
328
329 wxSocketError wxSocketImpl::UpdateLocalAddress()
330 {
331 WX_SOCKLEN_T lenAddr = m_local.GetLen();
332 if ( getsockname(m_fd, m_local.GetWritableAddr(), &lenAddr) != 0 )
333 {
334 Close();
335 m_error = wxSOCKET_IOERR;
336 return m_error;
337 }
338
339 return wxSOCKET_NOERROR;
340 }
341
342 wxSocketError wxSocketImpl::CreateServer()
343 {
344 if ( !PreCreateCheck(m_local) )
345 return m_error;
346
347 m_server = true;
348 m_stream = true;
349
350 // do create the socket
351 m_fd = socket(m_local.GetFamily(), SOCK_STREAM, 0);
352
353 if ( m_fd == INVALID_SOCKET )
354 {
355 m_error = wxSOCKET_IOERR;
356 return wxSOCKET_IOERR;
357 }
358
359 PostCreation();
360
361 // and then bind to and listen on it
362 //
363 // FIXME: should we test for m_dobind here?
364 if ( bind(m_fd, m_local.GetAddr(), m_local.GetLen()) != 0 )
365 m_error = wxSOCKET_IOERR;
366
367 if ( IsOk() )
368 {
369 if ( listen(m_fd, 5) != 0 )
370 m_error = wxSOCKET_IOERR;
371 }
372
373 if ( !IsOk() )
374 {
375 Close();
376 return m_error;
377 }
378
379 // finally retrieve the address we effectively bound to
380 return UpdateLocalAddress();
381 }
382
383 wxSocketError wxSocketImpl::CreateClient(bool wait)
384 {
385 if ( !PreCreateCheck(m_peer) )
386 return m_error;
387
388 m_fd = socket(m_peer.GetFamily(), SOCK_STREAM, 0);
389
390 if ( m_fd == INVALID_SOCKET )
391 {
392 m_error = wxSOCKET_IOERR;
393 return wxSOCKET_IOERR;
394 }
395
396 PostCreation();
397
398 // If a local address has been set, then bind to it before calling connect
399 if ( m_local.IsOk() )
400 {
401 if ( bind(m_fd, m_local.GetAddr(), m_local.GetLen()) != 0 )
402 {
403 Close();
404 m_error = wxSOCKET_IOERR;
405 return m_error;
406 }
407 }
408
409 // Do connect now
410 int rc = connect(m_fd, m_peer.GetAddr(), m_peer.GetLen());
411 if ( rc == SOCKET_ERROR )
412 {
413 wxSocketError err = GetLastError();
414 if ( err == wxSOCKET_WOULDBLOCK )
415 {
416 m_establishing = true;
417
418 // block waiting for connection if we should (otherwise just return
419 // wxSOCKET_WOULDBLOCK to the caller)
420 if ( wait )
421 {
422 err = SelectWithTimeout(wxSOCKET_CONNECTION_FLAG)
423 ? wxSOCKET_NOERROR
424 : wxSOCKET_TIMEDOUT;
425 m_establishing = false;
426 }
427 }
428
429 m_error = err;
430 }
431 else // connected
432 {
433 m_error = wxSOCKET_NOERROR;
434 }
435
436 return m_error;
437 }
438
439
440 wxSocketError wxSocketImpl::CreateUDP()
441 {
442 if ( !PreCreateCheck(m_local) )
443 return m_error;
444
445 m_stream = false;
446 m_server = false;
447
448 m_fd = socket(m_local.GetFamily(), SOCK_DGRAM, 0);
449
450 if ( m_fd == INVALID_SOCKET )
451 {
452 m_error = wxSOCKET_IOERR;
453 return wxSOCKET_IOERR;
454 }
455
456 PostCreation();
457
458 if ( m_dobind )
459 {
460 if ( bind(m_fd, m_local.GetAddr(), m_local.GetLen()) != 0 )
461 {
462 Close();
463 m_error = wxSOCKET_IOERR;
464 return m_error;
465 }
466
467 return UpdateLocalAddress();
468 }
469
470 return wxSOCKET_NOERROR;
471 }
472
473 wxSocketImpl *wxSocketImpl::Accept(wxSocketBase& wxsocket)
474 {
475 wxSockAddressStorage from;
476 WX_SOCKLEN_T fromlen = sizeof(from);
477 const SOCKET fd = accept(m_fd, &from.addr, &fromlen);
478
479 // accepting is similar to reading in the sense that it resets "ready for
480 // read" flag on the socket
481 ReenableEvents(wxSOCKET_INPUT_FLAG);
482
483 if ( fd == INVALID_SOCKET )
484 return NULL;
485
486 wxSocketImpl * const sock = Create(wxsocket);
487 sock->m_fd = fd;
488 sock->m_peer = wxSockAddressImpl(from.addr, fromlen);
489
490 sock->UnblockAndRegisterWithEventLoop();
491
492 return sock;
493 }
494
495
496 void wxSocketImpl::Close()
497 {
498 if ( m_fd != INVALID_SOCKET )
499 {
500 DoClose();
501 m_fd = INVALID_SOCKET;
502 }
503 }
504
505 void wxSocketImpl::Shutdown()
506 {
507 if ( m_fd != INVALID_SOCKET )
508 {
509 shutdown(m_fd, 1 /* SD_SEND */);
510 Close();
511 }
512 }
513
514 /*
515 * Sets the timeout for blocking calls. Time is expressed in
516 * milliseconds.
517 */
518 void wxSocketImpl::SetTimeout(unsigned long millis)
519 {
520 SetTimeValFromMS(m_timeout, millis);
521 }
522
523 void wxSocketImpl::NotifyOnStateChange(wxSocketNotify event)
524 {
525 m_wxsocket->OnRequest(event);
526 }
527
528 /* Address handling */
529 wxSocketError wxSocketImpl::SetLocal(const wxSockAddressImpl& local)
530 {
531 /* the socket must be initialized, or it must be a server */
532 if (m_fd != INVALID_SOCKET && !m_server)
533 {
534 m_error = wxSOCKET_INVSOCK;
535 return wxSOCKET_INVSOCK;
536 }
537
538 if ( !local.IsOk() )
539 {
540 m_error = wxSOCKET_INVADDR;
541 return wxSOCKET_INVADDR;
542 }
543
544 m_local = local;
545
546 return wxSOCKET_NOERROR;
547 }
548
549 wxSocketError wxSocketImpl::SetPeer(const wxSockAddressImpl& peer)
550 {
551 if ( !peer.IsOk() )
552 {
553 m_error = wxSOCKET_INVADDR;
554 return wxSOCKET_INVADDR;
555 }
556
557 m_peer = peer;
558
559 return wxSOCKET_NOERROR;
560 }
561
562 const wxSockAddressImpl& wxSocketImpl::GetLocal()
563 {
564 if ( !m_local.IsOk() )
565 UpdateLocalAddress();
566
567 return m_local;
568 }
569
570 // ----------------------------------------------------------------------------
571 // wxSocketImpl IO
572 // ----------------------------------------------------------------------------
573
574 // this macro wraps the given expression (normally a syscall) in a loop which
575 // ignores any interruptions, i.e. reevaluates it again if it failed and errno
576 // is EINTR
577 #ifdef __UNIX__
578 #define DO_WHILE_EINTR( rc, syscall ) \
579 do { \
580 rc = (syscall); \
581 } \
582 while ( rc == -1 && errno == EINTR )
583 #else
584 #define DO_WHILE_EINTR( rc, syscall ) rc = (syscall)
585 #endif
586
587 int wxSocketImpl::RecvStream(void *buffer, int size)
588 {
589 int ret;
590 DO_WHILE_EINTR( ret, recv(m_fd, static_cast<char *>(buffer), size, 0) );
591
592 if ( !ret )
593 {
594 // receiving 0 bytes for a TCP socket indicates that the connection was
595 // closed by peer so shut down our end as well (for UDP sockets empty
596 // datagrams are also possible)
597 m_establishing = false;
598 NotifyOnStateChange(wxSOCKET_LOST);
599
600 Shutdown();
601
602 // do not return an error in this case however
603 }
604
605 return ret;
606 }
607
608 int wxSocketImpl::SendStream(const void *buffer, int size)
609 {
610 int ret;
611 DO_WHILE_EINTR( ret, send(m_fd, static_cast<const char *>(buffer), size,
612 wxSOCKET_MSG_NOSIGNAL) );
613
614 return ret;
615 }
616
617 int wxSocketImpl::RecvDgram(void *buffer, int size)
618 {
619 wxSockAddressStorage from;
620 WX_SOCKLEN_T fromlen = sizeof(from);
621
622 int ret;
623 DO_WHILE_EINTR( ret, recvfrom(m_fd, static_cast<char *>(buffer), size,
624 0, &from.addr, &fromlen) );
625
626 if ( ret == SOCKET_ERROR )
627 return SOCKET_ERROR;
628
629 m_peer = wxSockAddressImpl(from.addr, fromlen);
630 if ( !m_peer.IsOk() )
631 return -1;
632
633 return ret;
634 }
635
636 int wxSocketImpl::SendDgram(const void *buffer, int size)
637 {
638 if ( !m_peer.IsOk() )
639 {
640 m_error = wxSOCKET_INVADDR;
641 return -1;
642 }
643
644 int ret;
645 DO_WHILE_EINTR( ret, sendto(m_fd, static_cast<const char *>(buffer), size,
646 0, m_peer.GetAddr(), m_peer.GetLen()) );
647
648 return ret;
649 }
650
651 int wxSocketImpl::Read(void *buffer, int size)
652 {
653 // server sockets can't be used for IO, only to accept new connections
654 if ( m_fd == INVALID_SOCKET || m_server )
655 {
656 m_error = wxSOCKET_INVSOCK;
657 return -1;
658 }
659
660 int ret = m_stream ? RecvStream(buffer, size)
661 : RecvDgram(buffer, size);
662
663 m_error = ret == SOCKET_ERROR ? GetLastError() : wxSOCKET_NOERROR;
664
665 return ret;
666 }
667
668 int wxSocketImpl::Write(const void *buffer, int size)
669 {
670 if ( m_fd == INVALID_SOCKET || m_server )
671 {
672 m_error = wxSOCKET_INVSOCK;
673 return -1;
674 }
675
676 int ret = m_stream ? SendStream(buffer, size)
677 : SendDgram(buffer, size);
678
679 m_error = ret == SOCKET_ERROR ? GetLastError() : wxSOCKET_NOERROR;
680
681 return ret;
682 }
683
684 // ==========================================================================
685 // wxSocketBase
686 // ==========================================================================
687
688 // --------------------------------------------------------------------------
689 // Initialization and shutdown
690 // --------------------------------------------------------------------------
691
692 // FIXME-MT: all this is MT-unsafe, of course, we should protect all accesses
693 // to m_countInit with a crit section
694 size_t wxSocketBase::m_countInit = 0;
695
696 bool wxSocketBase::IsInitialized()
697 {
698 return m_countInit > 0;
699 }
700
701 bool wxSocketBase::Initialize()
702 {
703 if ( !m_countInit++ )
704 {
705 wxSocketManager * const manager = wxSocketManager::Get();
706 if ( !manager || !manager->OnInit() )
707 {
708 m_countInit--;
709
710 return false;
711 }
712 }
713
714 return true;
715 }
716
717 void wxSocketBase::Shutdown()
718 {
719 // we should be initialized
720 wxASSERT_MSG( m_countInit > 0, _T("extra call to Shutdown()") );
721 if ( --m_countInit == 0 )
722 {
723 wxSocketManager * const manager = wxSocketManager::Get();
724 wxCHECK_RET( manager, "should have a socket manager" );
725
726 manager->OnExit();
727 }
728 }
729
730 // --------------------------------------------------------------------------
731 // Ctor and dtor
732 // --------------------------------------------------------------------------
733
734 void wxSocketBase::Init()
735 {
736 m_impl = NULL;
737 m_type = wxSOCKET_UNINIT;
738
739 // state
740 m_flags = 0;
741 m_connected =
742 m_establishing =
743 m_reading =
744 m_writing =
745 m_closed = false;
746 m_lcount = 0;
747 m_timeout = 600;
748 m_beingDeleted = false;
749
750 // pushback buffer
751 m_unread = NULL;
752 m_unrd_size = 0;
753 m_unrd_cur = 0;
754
755 // events
756 m_id = wxID_ANY;
757 m_handler = NULL;
758 m_clientData = NULL;
759 m_notify = false;
760 m_eventmask =
761 m_eventsgot = 0;
762
763 if ( !IsInitialized() )
764 {
765 // this Initialize() will be undone by wxSocketModule::OnExit(), all
766 // the other calls to it should be matched by a call to Shutdown()
767 Initialize();
768 }
769 }
770
771 wxSocketBase::wxSocketBase()
772 {
773 Init();
774 }
775
776 wxSocketBase::wxSocketBase(wxSocketFlags flags, wxSocketType type)
777 {
778 Init();
779
780 SetFlags(flags);
781
782 m_type = type;
783 }
784
785 wxSocketBase::~wxSocketBase()
786 {
787 // Just in case the app called Destroy() *and* then deleted the socket
788 // immediately: don't leave dangling pointers.
789 wxAppTraits *traits = wxTheApp ? wxTheApp->GetTraits() : NULL;
790 if ( traits )
791 traits->RemoveFromPendingDelete(this);
792
793 // Shutdown and close the socket
794 if (!m_beingDeleted)
795 Close();
796
797 // Destroy the implementation object
798 delete m_impl;
799
800 // Free the pushback buffer
801 if (m_unread)
802 free(m_unread);
803 }
804
805 bool wxSocketBase::Destroy()
806 {
807 // Delayed destruction: the socket will be deleted during the next idle
808 // loop iteration. This ensures that all pending events have been
809 // processed.
810 m_beingDeleted = true;
811
812 // Shutdown and close the socket
813 Close();
814
815 // Suppress events from now on
816 Notify(false);
817
818 // schedule this object for deletion
819 wxAppTraits *traits = wxTheApp ? wxTheApp->GetTraits() : NULL;
820 if ( traits )
821 {
822 // let the traits object decide what to do with us
823 traits->ScheduleForDestroy(this);
824 }
825 else // no app or no traits
826 {
827 // in wxBase we might have no app object at all, don't leak memory
828 delete this;
829 }
830
831 return true;
832 }
833
834 // ----------------------------------------------------------------------------
835 // simple accessors
836 // ----------------------------------------------------------------------------
837
838 void wxSocketBase::SetError(wxSocketError error)
839 {
840 m_impl->m_error = error;
841 }
842
843 wxSocketError wxSocketBase::LastError() const
844 {
845 return m_impl->GetError();
846 }
847
848 // --------------------------------------------------------------------------
849 // Basic IO calls
850 // --------------------------------------------------------------------------
851
852 // The following IO operations update m_lcount:
853 // {Read, Write, ReadMsg, WriteMsg, Peek, Unread, Discard}
854 bool wxSocketBase::Close()
855 {
856 // Interrupt pending waits
857 InterruptWait();
858
859 ShutdownOutput();
860
861 m_connected = false;
862 m_establishing = false;
863 return true;
864 }
865
866 void wxSocketBase::ShutdownOutput()
867 {
868 if ( m_impl )
869 m_impl->Shutdown();
870 }
871
872 wxSocketBase& wxSocketBase::Read(void* buffer, wxUint32 nbytes)
873 {
874 wxSocketReadGuard read(this);
875
876 m_lcount = DoRead(buffer, nbytes);
877
878 return *this;
879 }
880
881 wxUint32 wxSocketBase::DoRead(void* buffer_, wxUint32 nbytes)
882 {
883 wxCHECK_MSG( m_impl, 0, "socket must be valid" );
884
885 // We use pointer arithmetic here which doesn't work with void pointers.
886 char *buffer = static_cast<char *>(buffer_);
887 wxCHECK_MSG( buffer, 0, "NULL buffer" );
888
889 // Try the push back buffer first, even before checking whether the socket
890 // is valid to allow reading previously pushed back data from an already
891 // closed socket.
892 wxUint32 total = GetPushback(buffer, nbytes, false);
893 nbytes -= total;
894 buffer += total;
895
896 while ( nbytes )
897 {
898 // our socket is non-blocking so Read() will return immediately if
899 // there is nothing to read yet and it's more efficient to try it first
900 // before entering DoWait() which is going to start dispatching GUI
901 // events and, even more importantly, we must do this under Windows
902 // where we're not going to get notifications about socket being ready
903 // for reading before we read all the existing data from it
904 const int ret = m_connected ? m_impl->Read(buffer, nbytes) : 0;
905 if ( ret == -1 )
906 {
907 if ( m_impl->GetLastError() == wxSOCKET_WOULDBLOCK )
908 {
909 // if we don't want to wait, just return immediately
910 if ( m_flags & wxSOCKET_NOWAIT )
911 break;
912
913 // otherwise wait until the socket becomes ready for reading or
914 // an error occurs on it
915 if ( !DoWaitWithTimeout(wxSOCKET_INPUT_FLAG |
916 wxSOCKET_LOST_FLAG) )
917 {
918 // and exit if the timeout elapsed before it did
919 SetError(wxSOCKET_TIMEDOUT);
920 break;
921 }
922
923 // retry reading
924 continue;
925 }
926 else // "real" error
927 {
928 SetError(wxSOCKET_IOERR);
929 break;
930 }
931 }
932 else if ( ret == 0 )
933 {
934 // for connection-oriented (e.g. TCP) sockets we can only read
935 // 0 bytes if the other end has been closed, and for connectionless
936 // ones (UDP) this flag doesn't make sense anyhow so we can set it
937 // to true too without doing any harm
938 m_closed = true;
939
940 // we're not going to read anything else and so if we haven't read
941 // anything (or not everything in wxSOCKET_WAITALL case) already,
942 // signal an error
943 if ( (m_flags & wxSOCKET_WAITALL) || !total )
944 SetError(wxSOCKET_IOERR);
945 break;
946 }
947
948 total += ret;
949
950 // if we are happy to read something and not the entire nbytes bytes,
951 // then we're done
952 if ( !(m_flags & wxSOCKET_WAITALL) )
953 break;
954
955 nbytes -= ret;
956 buffer += ret;
957 }
958
959 return total;
960 }
961
962 wxSocketBase& wxSocketBase::ReadMsg(void* buffer, wxUint32 nbytes)
963 {
964 struct
965 {
966 unsigned char sig[4];
967 unsigned char len[4];
968 } msg;
969
970 wxSocketReadGuard read(this);
971
972 wxSocketWaitModeChanger changeFlags(this, wxSOCKET_WAITALL);
973
974 bool ok = false;
975 if ( DoRead(&msg, sizeof(msg)) == sizeof(msg) )
976 {
977 wxUint32 sig = (wxUint32)msg.sig[0];
978 sig |= (wxUint32)(msg.sig[1] << 8);
979 sig |= (wxUint32)(msg.sig[2] << 16);
980 sig |= (wxUint32)(msg.sig[3] << 24);
981
982 if ( sig == 0xfeeddead )
983 {
984 wxUint32 len = (wxUint32)msg.len[0];
985 len |= (wxUint32)(msg.len[1] << 8);
986 len |= (wxUint32)(msg.len[2] << 16);
987 len |= (wxUint32)(msg.len[3] << 24);
988
989 wxUint32 len2;
990 if (len > nbytes)
991 {
992 len2 = len - nbytes;
993 len = nbytes;
994 }
995 else
996 len2 = 0;
997
998 // Don't attempt to read if the msg was zero bytes long.
999 m_lcount = len ? DoRead(buffer, len) : 0;
1000
1001 if ( len2 )
1002 {
1003 char discard_buffer[MAX_DISCARD_SIZE];
1004 long discard_len;
1005
1006 // NOTE: discarded bytes don't add to m_lcount.
1007 do
1008 {
1009 discard_len = len2 > MAX_DISCARD_SIZE
1010 ? MAX_DISCARD_SIZE
1011 : len2;
1012 discard_len = DoRead(discard_buffer, (wxUint32)discard_len);
1013 len2 -= (wxUint32)discard_len;
1014 }
1015 while ((discard_len > 0) && len2);
1016 }
1017
1018 if ( !len2 && DoRead(&msg, sizeof(msg)) == sizeof(msg) )
1019 {
1020 sig = (wxUint32)msg.sig[0];
1021 sig |= (wxUint32)(msg.sig[1] << 8);
1022 sig |= (wxUint32)(msg.sig[2] << 16);
1023 sig |= (wxUint32)(msg.sig[3] << 24);
1024
1025 if ( sig == 0xdeadfeed )
1026 ok = true;
1027 }
1028 }
1029 }
1030
1031 if ( !ok )
1032 SetError(wxSOCKET_IOERR);
1033
1034 return *this;
1035 }
1036
1037 wxSocketBase& wxSocketBase::Peek(void* buffer, wxUint32 nbytes)
1038 {
1039 wxSocketReadGuard read(this);
1040
1041 m_lcount = DoRead(buffer, nbytes);
1042
1043 Pushback(buffer, m_lcount);
1044
1045 return *this;
1046 }
1047
1048 wxSocketBase& wxSocketBase::Write(const void *buffer, wxUint32 nbytes)
1049 {
1050 wxSocketWriteGuard write(this);
1051
1052 m_lcount = DoWrite(buffer, nbytes);
1053
1054 return *this;
1055 }
1056
1057 // This function is a mirror image of DoRead() except that it doesn't use the
1058 // push back buffer and doesn't treat 0 return value specially (normally this
1059 // shouldn't happen at all here), so please see comments there for explanations
1060 wxUint32 wxSocketBase::DoWrite(const void *buffer_, wxUint32 nbytes)
1061 {
1062 wxCHECK_MSG( m_impl, 0, "socket must be valid" );
1063
1064 const char *buffer = static_cast<const char *>(buffer_);
1065 wxCHECK_MSG( buffer, 0, "NULL buffer" );
1066
1067 wxUint32 total = 0;
1068 while ( nbytes )
1069 {
1070 if ( !m_connected )
1071 {
1072 if ( (m_flags & wxSOCKET_WAITALL) || !total )
1073 SetError(wxSOCKET_IOERR);
1074 break;
1075 }
1076
1077 const int ret = m_impl->Write(buffer, nbytes);
1078 if ( ret == -1 )
1079 {
1080 if ( m_impl->GetLastError() == wxSOCKET_WOULDBLOCK )
1081 {
1082 if ( m_flags & wxSOCKET_NOWAIT )
1083 break;
1084
1085 if ( !DoWaitWithTimeout(wxSOCKET_OUTPUT_FLAG |
1086 wxSOCKET_LOST_FLAG) )
1087 {
1088 SetError(wxSOCKET_TIMEDOUT);
1089 break;
1090 }
1091
1092 continue;
1093 }
1094 else // "real" error
1095 {
1096 SetError(wxSOCKET_IOERR);
1097 break;
1098 }
1099 }
1100
1101 total += ret;
1102
1103 if ( !(m_flags & wxSOCKET_WAITALL) )
1104 break;
1105
1106 nbytes -= ret;
1107 buffer += ret;
1108 }
1109
1110 return total;
1111 }
1112
1113 wxSocketBase& wxSocketBase::WriteMsg(const void *buffer, wxUint32 nbytes)
1114 {
1115 struct
1116 {
1117 unsigned char sig[4];
1118 unsigned char len[4];
1119 } msg;
1120
1121 wxSocketWriteGuard write(this);
1122
1123 wxSocketWaitModeChanger changeFlags(this, wxSOCKET_WAITALL);
1124
1125 msg.sig[0] = (unsigned char) 0xad;
1126 msg.sig[1] = (unsigned char) 0xde;
1127 msg.sig[2] = (unsigned char) 0xed;
1128 msg.sig[3] = (unsigned char) 0xfe;
1129
1130 msg.len[0] = (unsigned char) (nbytes & 0xff);
1131 msg.len[1] = (unsigned char) ((nbytes >> 8) & 0xff);
1132 msg.len[2] = (unsigned char) ((nbytes >> 16) & 0xff);
1133 msg.len[3] = (unsigned char) ((nbytes >> 24) & 0xff);
1134
1135 bool ok = false;
1136 if ( DoWrite(&msg, sizeof(msg)) == sizeof(msg) )
1137 {
1138 m_lcount = DoWrite(buffer, nbytes);
1139 if ( m_lcount == nbytes )
1140 {
1141 msg.sig[0] = (unsigned char) 0xed;
1142 msg.sig[1] = (unsigned char) 0xfe;
1143 msg.sig[2] = (unsigned char) 0xad;
1144 msg.sig[3] = (unsigned char) 0xde;
1145 msg.len[0] =
1146 msg.len[1] =
1147 msg.len[2] =
1148 msg.len[3] = (char) 0;
1149
1150 if ( DoWrite(&msg, sizeof(msg)) == sizeof(msg))
1151 ok = true;
1152 }
1153 }
1154
1155 if ( !ok )
1156 SetError(wxSOCKET_IOERR);
1157
1158 return *this;
1159 }
1160
1161 wxSocketBase& wxSocketBase::Unread(const void *buffer, wxUint32 nbytes)
1162 {
1163 if (nbytes != 0)
1164 Pushback(buffer, nbytes);
1165
1166 SetError(wxSOCKET_NOERROR);
1167 m_lcount = nbytes;
1168
1169 return *this;
1170 }
1171
1172 wxSocketBase& wxSocketBase::Discard()
1173 {
1174 char *buffer = new char[MAX_DISCARD_SIZE];
1175 wxUint32 ret;
1176 wxUint32 total = 0;
1177
1178 wxSocketReadGuard read(this);
1179
1180 wxSocketWaitModeChanger changeFlags(this, wxSOCKET_NOWAIT);
1181
1182 do
1183 {
1184 ret = DoRead(buffer, MAX_DISCARD_SIZE);
1185 total += ret;
1186 }
1187 while (ret == MAX_DISCARD_SIZE);
1188
1189 delete[] buffer;
1190 m_lcount = total;
1191 SetError(wxSOCKET_NOERROR);
1192
1193 return *this;
1194 }
1195
1196 // --------------------------------------------------------------------------
1197 // Wait functions
1198 // --------------------------------------------------------------------------
1199
1200 /*
1201 This function will check for the events specified in the flags parameter,
1202 and it will return a mask indicating which operations can be performed.
1203 */
1204 wxSocketEventFlags wxSocketImpl::Select(wxSocketEventFlags flags,
1205 const timeval *timeout)
1206 {
1207 if ( m_fd == INVALID_SOCKET )
1208 return (wxSOCKET_LOST_FLAG & flags);
1209
1210 struct timeval tv;
1211 if ( timeout )
1212 tv = *timeout;
1213 else
1214 tv.tv_sec = tv.tv_usec = 0;
1215
1216 // prepare the FD sets, passing NULL for the one(s) we don't use
1217 fd_set
1218 readfds, *preadfds = NULL,
1219 writefds, *pwritefds = NULL,
1220 exceptfds; // always want to know about errors
1221
1222 if ( flags & wxSOCKET_INPUT_FLAG )
1223 {
1224 preadfds = &readfds;
1225 wxFD_ZERO(preadfds);
1226 wxFD_SET(m_fd, preadfds);
1227 }
1228
1229 // when using non-blocking connect() the socket becomes connected
1230 // (successfully or not) when it becomes writable
1231 if ( flags & (wxSOCKET_OUTPUT_FLAG | wxSOCKET_CONNECTION_FLAG) )
1232 {
1233 pwritefds = &writefds;
1234 wxFD_ZERO(pwritefds);
1235 wxFD_SET(m_fd, pwritefds);
1236 }
1237
1238 wxFD_ZERO(&exceptfds);
1239 wxFD_SET(m_fd, &exceptfds);
1240
1241 const int rc = select(m_fd + 1, preadfds, pwritefds, &exceptfds, &tv);
1242
1243 // check for errors first
1244 if ( rc == -1 || wxFD_ISSET(m_fd, &exceptfds) )
1245 {
1246 m_establishing = false;
1247
1248 return wxSOCKET_LOST_FLAG & flags;
1249 }
1250
1251 if ( rc == 0 )
1252 return 0;
1253
1254 wxASSERT_MSG( rc == 1, "unexpected select() return value" );
1255
1256 wxSocketEventFlags detected = 0;
1257 if ( preadfds && wxFD_ISSET(m_fd, preadfds) )
1258 detected |= wxSOCKET_INPUT_FLAG;
1259
1260 if ( pwritefds && wxFD_ISSET(m_fd, pwritefds) )
1261 {
1262 // check for the case of non-blocking connect()
1263 if ( m_establishing && !m_server )
1264 {
1265 int error;
1266 SOCKOPTLEN_T len = sizeof(error);
1267 m_establishing = false;
1268 getsockopt(m_fd, SOL_SOCKET, SO_ERROR, (char*)&error, &len);
1269
1270 if ( error )
1271 detected = wxSOCKET_LOST_FLAG;
1272 else
1273 detected |= wxSOCKET_CONNECTION_FLAG;
1274 }
1275 else // not called to get non-blocking connect() status
1276 {
1277 detected |= wxSOCKET_OUTPUT_FLAG;
1278 }
1279 }
1280
1281 return detected & flags;
1282 }
1283
1284 bool
1285 wxSocketBase::DoWait(long seconds, long milliseconds, wxSocketEventFlags flags)
1286 {
1287 // Use either the provided timeout or the default timeout value associated
1288 // with this socket.
1289 //
1290 // TODO: allow waiting forever, see #9443
1291 const long timeout = seconds == -1 ? m_timeout * 1000
1292 : seconds * 1000 + milliseconds;
1293
1294 return DoWait(timeout, flags);
1295 }
1296
1297 bool
1298 wxSocketBase::DoWait(long timeout, wxSocketEventFlags flags)
1299 {
1300 wxCHECK_MSG( m_impl, false, "can't wait on invalid socket" );
1301
1302 // we're never going to become ready if we're not connected (any more)
1303 if ( !m_connected && !m_establishing )
1304 return (flags & wxSOCKET_LOST_FLAG) != 0;
1305
1306 // This can be set to true from Interrupt() to exit this function a.s.a.p.
1307 m_interrupt = false;
1308
1309
1310 const wxMilliClock_t timeEnd = wxGetLocalTimeMillis() + timeout;
1311
1312 // Get the active event loop which we'll use for the message dispatching
1313 // when running in the main thread unless this was explicitly disabled by
1314 // setting wxSOCKET_BLOCK flag
1315 wxEventLoopBase *eventLoop;
1316 if ( !(m_flags & wxSOCKET_BLOCK) && wxIsMainThread() )
1317 {
1318 eventLoop = wxEventLoop::GetActive();
1319 }
1320 else // in worker thread
1321 {
1322 // We never dispatch messages from threads other than the main one.
1323 eventLoop = NULL;
1324 }
1325
1326 // Wait until we receive the event we're waiting for or the timeout expires
1327 // (but note that we always execute the loop at least once, even if timeout
1328 // is 0 as this is used for polling)
1329 bool gotEvent = false;
1330 for ( bool firstTime = true; !m_interrupt ; firstTime = false )
1331 {
1332 long timeLeft = wxMilliClockToLong(timeEnd - wxGetLocalTimeMillis());
1333 if ( timeLeft < 0 )
1334 {
1335 if ( !firstTime )
1336 break; // timed out
1337
1338 timeLeft = 0;
1339 }
1340
1341 wxSocketEventFlags events;
1342 if ( eventLoop )
1343 {
1344 // reset them before starting to wait
1345 m_eventsgot = 0;
1346
1347 eventLoop->DispatchTimeout(timeLeft);
1348
1349 events = m_eventsgot;
1350 }
1351 else // no event loop or waiting in another thread
1352 {
1353 // as explained below, we should always check for wxSOCKET_LOST_FLAG
1354 timeval tv;
1355 SetTimeValFromMS(tv, timeLeft);
1356 events = m_impl->Select(flags | wxSOCKET_LOST_FLAG, &tv);
1357 }
1358
1359 // always check for wxSOCKET_LOST_FLAG, even if flags doesn't include
1360 // it, as continuing to wait for anything else after getting it is
1361 // pointless
1362 if ( events & wxSOCKET_LOST_FLAG )
1363 {
1364 m_connected = false;
1365 m_establishing = false;
1366 if ( flags & wxSOCKET_LOST_FLAG )
1367 gotEvent = true;
1368 break;
1369 }
1370
1371 // otherwise mask out the bits we're not interested in
1372 events &= flags;
1373
1374 // Incoming connection (server) or connection established (client)?
1375 if ( events & wxSOCKET_CONNECTION_FLAG )
1376 {
1377 m_connected = true;
1378 m_establishing = false;
1379 gotEvent = true;
1380 break;
1381 }
1382
1383 // Data available or output buffer ready?
1384 if ( (events & wxSOCKET_INPUT_FLAG) || (events & wxSOCKET_OUTPUT_FLAG) )
1385 {
1386 gotEvent = true;
1387 break;
1388 }
1389 }
1390
1391 return gotEvent;
1392 }
1393
1394 bool wxSocketBase::Wait(long seconds, long milliseconds)
1395 {
1396 return DoWait(seconds, milliseconds,
1397 wxSOCKET_INPUT_FLAG |
1398 wxSOCKET_OUTPUT_FLAG |
1399 wxSOCKET_CONNECTION_FLAG |
1400 wxSOCKET_LOST_FLAG
1401 );
1402 }
1403
1404 bool wxSocketBase::WaitForRead(long seconds, long milliseconds)
1405 {
1406 // Check pushback buffer before entering DoWait
1407 if ( m_unread )
1408 return true;
1409
1410 // Check if the socket is not already ready for input, if it is, there is
1411 // no need to start waiting for it (worse, we'll actually never get a
1412 // notification about the socket becoming ready if it is already under
1413 // Windows)
1414 if ( m_impl->Select(wxSOCKET_INPUT_FLAG) )
1415 return true;
1416
1417 // Note that wxSOCKET_LOST_FLAG has to be explicitly passed to DoWait
1418 // because of the semantics of WaitForRead: a return value of true means
1419 // that a Read call will return immediately, not that there is
1420 // actually data to read.
1421 return DoWait(seconds, milliseconds, wxSOCKET_INPUT_FLAG | wxSOCKET_LOST_FLAG);
1422 }
1423
1424
1425 bool wxSocketBase::WaitForWrite(long seconds, long milliseconds)
1426 {
1427 if ( m_impl->Select(wxSOCKET_OUTPUT_FLAG) )
1428 return true;
1429
1430 return DoWait(seconds, milliseconds, wxSOCKET_OUTPUT_FLAG | wxSOCKET_LOST_FLAG);
1431 }
1432
1433 bool wxSocketBase::WaitForLost(long seconds, long milliseconds)
1434 {
1435 return DoWait(seconds, milliseconds, wxSOCKET_LOST_FLAG);
1436 }
1437
1438 // --------------------------------------------------------------------------
1439 // Miscellaneous
1440 // --------------------------------------------------------------------------
1441
1442 //
1443 // Get local or peer address
1444 //
1445
1446 bool wxSocketBase::GetPeer(wxSockAddress& addr) const
1447 {
1448 wxCHECK_MSG( m_impl, false, "invalid socket" );
1449
1450 const wxSockAddressImpl& peer = m_impl->GetPeer();
1451 if ( !peer.IsOk() )
1452 return false;
1453
1454 addr.SetAddress(peer);
1455
1456 return true;
1457 }
1458
1459 bool wxSocketBase::GetLocal(wxSockAddress& addr) const
1460 {
1461 wxCHECK_MSG( m_impl, false, "invalid socket" );
1462
1463 const wxSockAddressImpl& local = m_impl->GetLocal();
1464 if ( !local.IsOk() )
1465 return false;
1466
1467 addr.SetAddress(local);
1468
1469 return true;
1470 }
1471
1472 //
1473 // Save and restore socket state
1474 //
1475
1476 void wxSocketBase::SaveState()
1477 {
1478 wxSocketState *state;
1479
1480 state = new wxSocketState();
1481
1482 state->m_flags = m_flags;
1483 state->m_notify = m_notify;
1484 state->m_eventmask = m_eventmask;
1485 state->m_clientData = m_clientData;
1486
1487 m_states.Append(state);
1488 }
1489
1490 void wxSocketBase::RestoreState()
1491 {
1492 wxList::compatibility_iterator node;
1493 wxSocketState *state;
1494
1495 node = m_states.GetLast();
1496 if (!node)
1497 return;
1498
1499 state = (wxSocketState *)node->GetData();
1500
1501 m_flags = state->m_flags;
1502 m_notify = state->m_notify;
1503 m_eventmask = state->m_eventmask;
1504 m_clientData = state->m_clientData;
1505
1506 m_states.Erase(node);
1507 delete state;
1508 }
1509
1510 //
1511 // Timeout and flags
1512 //
1513
1514 void wxSocketBase::SetTimeout(long seconds)
1515 {
1516 m_timeout = seconds;
1517
1518 if (m_impl)
1519 m_impl->SetTimeout(m_timeout * 1000);
1520 }
1521
1522 void wxSocketBase::SetFlags(wxSocketFlags flags)
1523 {
1524 // Do some sanity checking on the flags used: not all values can be used
1525 // together.
1526 wxASSERT_MSG( !(flags & wxSOCKET_NOWAIT) ||
1527 !(flags & (wxSOCKET_WAITALL | wxSOCKET_BLOCK)),
1528 "Using wxSOCKET_WAITALL or wxSOCKET_BLOCK with "
1529 "wxSOCKET_NOWAIT doesn't make sense" );
1530
1531 m_flags = flags;
1532 }
1533
1534
1535 // --------------------------------------------------------------------------
1536 // Event handling
1537 // --------------------------------------------------------------------------
1538
1539 void wxSocketBase::OnRequest(wxSocketNotify notification)
1540 {
1541 wxSocketEventFlags flag = 0;
1542 switch ( notification )
1543 {
1544 case wxSOCKET_INPUT:
1545 flag = wxSOCKET_INPUT_FLAG;
1546 break;
1547
1548 case wxSOCKET_OUTPUT:
1549 flag = wxSOCKET_OUTPUT_FLAG;
1550 break;
1551
1552 case wxSOCKET_CONNECTION:
1553 flag = wxSOCKET_CONNECTION_FLAG;
1554 break;
1555
1556 case wxSOCKET_LOST:
1557 flag = wxSOCKET_LOST_FLAG;
1558 break;
1559
1560 default:
1561 wxFAIL_MSG( "unknown wxSocket notification" );
1562 }
1563
1564 // if we lost the connection the socket is now closed
1565 if ( notification == wxSOCKET_LOST )
1566 m_closed = true;
1567
1568 // remember the events which were generated for this socket, we're going to
1569 // use this in DoWait()
1570 m_eventsgot |= flag;
1571
1572 // send the wx event if enabled and we're interested in it
1573 if ( m_notify && (m_eventmask & flag) && m_handler )
1574 {
1575 wxSocketEvent event(m_id);
1576 event.m_event = notification;
1577 event.m_clientData = m_clientData;
1578 event.SetEventObject(this);
1579
1580 m_handler->AddPendingEvent(event);
1581 }
1582 }
1583
1584 void wxSocketBase::Notify(bool notify)
1585 {
1586 m_notify = notify;
1587 }
1588
1589 void wxSocketBase::SetNotify(wxSocketEventFlags flags)
1590 {
1591 m_eventmask = flags;
1592 }
1593
1594 void wxSocketBase::SetEventHandler(wxEvtHandler& handler, int id)
1595 {
1596 m_handler = &handler;
1597 m_id = id;
1598 }
1599
1600 // --------------------------------------------------------------------------
1601 // Pushback buffer
1602 // --------------------------------------------------------------------------
1603
1604 void wxSocketBase::Pushback(const void *buffer, wxUint32 size)
1605 {
1606 if (!size) return;
1607
1608 if (m_unread == NULL)
1609 m_unread = malloc(size);
1610 else
1611 {
1612 void *tmp;
1613
1614 tmp = malloc(m_unrd_size + size);
1615 memcpy((char *)tmp + size, m_unread, m_unrd_size);
1616 free(m_unread);
1617
1618 m_unread = tmp;
1619 }
1620
1621 m_unrd_size += size;
1622
1623 memcpy(m_unread, buffer, size);
1624 }
1625
1626 wxUint32 wxSocketBase::GetPushback(void *buffer, wxUint32 size, bool peek)
1627 {
1628 wxCHECK_MSG( buffer, 0, "NULL buffer" );
1629
1630 if (!m_unrd_size)
1631 return 0;
1632
1633 if (size > (m_unrd_size-m_unrd_cur))
1634 size = m_unrd_size-m_unrd_cur;
1635
1636 memcpy(buffer, (char *)m_unread + m_unrd_cur, size);
1637
1638 if (!peek)
1639 {
1640 m_unrd_cur += size;
1641 if (m_unrd_size == m_unrd_cur)
1642 {
1643 free(m_unread);
1644 m_unread = NULL;
1645 m_unrd_size = 0;
1646 m_unrd_cur = 0;
1647 }
1648 }
1649
1650 return size;
1651 }
1652
1653
1654 // ==========================================================================
1655 // wxSocketServer
1656 // ==========================================================================
1657
1658 // --------------------------------------------------------------------------
1659 // Ctor
1660 // --------------------------------------------------------------------------
1661
1662 wxSocketServer::wxSocketServer(const wxSockAddress& addr,
1663 wxSocketFlags flags)
1664 : wxSocketBase(flags, wxSOCKET_SERVER)
1665 {
1666 wxLogTrace( wxTRACE_Socket, _T("Opening wxSocketServer") );
1667
1668 m_impl = wxSocketImpl::Create(*this);
1669
1670 if (!m_impl)
1671 {
1672 wxLogTrace( wxTRACE_Socket, _T("*** Failed to create m_impl") );
1673 return;
1674 }
1675
1676 // Setup the socket as server
1677 m_impl->SetLocal(addr.GetAddress());
1678
1679 if (GetFlags() & wxSOCKET_REUSEADDR) {
1680 m_impl->SetReusable();
1681 }
1682 if (GetFlags() & wxSOCKET_BROADCAST) {
1683 m_impl->SetBroadcast();
1684 }
1685 if (GetFlags() & wxSOCKET_NOBIND) {
1686 m_impl->DontDoBind();
1687 }
1688
1689 if (m_impl->CreateServer() != wxSOCKET_NOERROR)
1690 {
1691 delete m_impl;
1692 m_impl = NULL;
1693
1694 wxLogTrace( wxTRACE_Socket, _T("*** CreateServer() failed") );
1695 return;
1696 }
1697
1698 wxLogTrace( wxTRACE_Socket, _T("wxSocketServer on fd %d"), m_impl->m_fd );
1699 }
1700
1701 // --------------------------------------------------------------------------
1702 // Accept
1703 // --------------------------------------------------------------------------
1704
1705 bool wxSocketServer::AcceptWith(wxSocketBase& sock, bool wait)
1706 {
1707 if ( !m_impl || (m_impl->m_fd == INVALID_SOCKET) || !m_impl->IsServer() )
1708 {
1709 wxFAIL_MSG( "can only be called for a valid server socket" );
1710
1711 SetError(wxSOCKET_INVSOCK);
1712
1713 return false;
1714 }
1715
1716 if ( wait )
1717 {
1718 // wait until we get a connection
1719 if ( !m_impl->SelectWithTimeout(wxSOCKET_INPUT_FLAG) )
1720 {
1721 SetError(wxSOCKET_TIMEDOUT);
1722
1723 return false;
1724 }
1725 }
1726
1727 sock.m_impl = m_impl->Accept(sock);
1728
1729 if ( !sock.m_impl )
1730 {
1731 SetError(m_impl->GetLastError());
1732
1733 return false;
1734 }
1735
1736 sock.m_type = wxSOCKET_BASE;
1737 sock.m_connected = true;
1738
1739 return true;
1740 }
1741
1742 wxSocketBase *wxSocketServer::Accept(bool wait)
1743 {
1744 wxSocketBase* sock = new wxSocketBase();
1745
1746 sock->SetFlags(m_flags);
1747
1748 if (!AcceptWith(*sock, wait))
1749 {
1750 sock->Destroy();
1751 sock = NULL;
1752 }
1753
1754 return sock;
1755 }
1756
1757 bool wxSocketServer::WaitForAccept(long seconds, long milliseconds)
1758 {
1759 return DoWait(seconds, milliseconds, wxSOCKET_CONNECTION_FLAG);
1760 }
1761
1762 bool wxSocketBase::GetOption(int level, int optname, void *optval, int *optlen)
1763 {
1764 wxASSERT_MSG( m_impl, _T("Socket not initialised") );
1765
1766 SOCKOPTLEN_T lenreal = *optlen;
1767 if ( getsockopt(m_impl->m_fd, level, optname,
1768 static_cast<char *>(optval), &lenreal) != 0 )
1769 return false;
1770
1771 *optlen = lenreal;
1772
1773 return true;
1774 }
1775
1776 bool
1777 wxSocketBase::SetOption(int level, int optname, const void *optval, int optlen)
1778 {
1779 wxASSERT_MSG( m_impl, _T("Socket not initialised") );
1780
1781 return setsockopt(m_impl->m_fd, level, optname,
1782 static_cast<const char *>(optval), optlen) == 0;
1783 }
1784
1785 bool wxSocketBase::SetLocal(const wxIPV4address& local)
1786 {
1787 m_localAddress = local;
1788
1789 return true;
1790 }
1791
1792 // ==========================================================================
1793 // wxSocketClient
1794 // ==========================================================================
1795
1796 // --------------------------------------------------------------------------
1797 // Ctor and dtor
1798 // --------------------------------------------------------------------------
1799
1800 wxSocketClient::wxSocketClient(wxSocketFlags flags)
1801 : wxSocketBase(flags, wxSOCKET_CLIENT)
1802 {
1803 m_initialRecvBufferSize =
1804 m_initialSendBufferSize = -1;
1805 }
1806
1807 // --------------------------------------------------------------------------
1808 // Connect
1809 // --------------------------------------------------------------------------
1810
1811 bool wxSocketClient::DoConnect(const wxSockAddress& remote,
1812 const wxSockAddress* local,
1813 bool wait)
1814 {
1815 if ( m_impl )
1816 {
1817 // Shutdown and destroy the old socket
1818 Close();
1819 delete m_impl;
1820 }
1821
1822 m_connected = false;
1823 m_establishing = false;
1824
1825 // Create and set up the new one
1826 m_impl = wxSocketImpl::Create(*this);
1827 if ( !m_impl )
1828 return false;
1829
1830 // Reuse makes sense for clients too, if we are trying to rebind to the same port
1831 if (GetFlags() & wxSOCKET_REUSEADDR)
1832 m_impl->SetReusable();
1833 if (GetFlags() & wxSOCKET_BROADCAST)
1834 m_impl->SetBroadcast();
1835 if (GetFlags() & wxSOCKET_NOBIND)
1836 m_impl->DontDoBind();
1837
1838 // Bind to the local IP address and port, when provided or if one had been
1839 // set before
1840 if ( !local && m_localAddress.GetAddress().IsOk() )
1841 local = &m_localAddress;
1842
1843 if ( local )
1844 m_impl->SetLocal(local->GetAddress());
1845
1846 m_impl->SetInitialSocketBuffers(m_initialRecvBufferSize, m_initialSendBufferSize);
1847
1848 m_impl->SetPeer(remote.GetAddress());
1849
1850 // Finally do create the socket and connect to the peer
1851 const wxSocketError err = m_impl->CreateClient(wait);
1852
1853 if ( err != wxSOCKET_NOERROR )
1854 {
1855 if ( err == wxSOCKET_WOULDBLOCK )
1856 {
1857 wxASSERT_MSG( !wait, "shouldn't get this for blocking connect" );
1858
1859 m_establishing = true;
1860 }
1861
1862 return false;
1863 }
1864
1865 m_connected = true;
1866 return true;
1867 }
1868
1869 bool wxSocketClient::Connect(const wxSockAddress& remote, bool wait)
1870 {
1871 return DoConnect(remote, NULL, wait);
1872 }
1873
1874 bool wxSocketClient::Connect(const wxSockAddress& remote,
1875 const wxSockAddress& local,
1876 bool wait)
1877 {
1878 return DoConnect(remote, &local, wait);
1879 }
1880
1881 bool wxSocketClient::WaitOnConnect(long seconds, long milliseconds)
1882 {
1883 if ( m_connected )
1884 {
1885 // this happens if the initial attempt to connect succeeded without
1886 // blocking
1887 return true;
1888 }
1889
1890 wxCHECK_MSG( m_establishing && m_impl, false,
1891 "No connection establishment attempt in progress" );
1892
1893 // we must specify wxSOCKET_LOST_FLAG here explicitly because we must return
1894 // true if the connection establishment process is finished, whether it is
1895 // over because we successfully connected or because we were not able to
1896 // connect
1897 return DoWait(seconds, milliseconds,
1898 wxSOCKET_CONNECTION_FLAG | wxSOCKET_LOST_FLAG);
1899 }
1900
1901 // ==========================================================================
1902 // wxDatagramSocket
1903 // ==========================================================================
1904
1905 wxDatagramSocket::wxDatagramSocket( const wxSockAddress& addr,
1906 wxSocketFlags flags )
1907 : wxSocketBase( flags, wxSOCKET_DATAGRAM )
1908 {
1909 // Create the socket
1910 m_impl = wxSocketImpl::Create(*this);
1911
1912 if (!m_impl)
1913 return;
1914
1915 // Setup the socket as non connection oriented
1916 m_impl->SetLocal(addr.GetAddress());
1917 if (flags & wxSOCKET_REUSEADDR)
1918 {
1919 m_impl->SetReusable();
1920 }
1921 if (GetFlags() & wxSOCKET_BROADCAST)
1922 {
1923 m_impl->SetBroadcast();
1924 }
1925 if (GetFlags() & wxSOCKET_NOBIND)
1926 {
1927 m_impl->DontDoBind();
1928 }
1929
1930 if ( m_impl->CreateUDP() != wxSOCKET_NOERROR )
1931 {
1932 delete m_impl;
1933 m_impl = NULL;
1934 return;
1935 }
1936
1937 // Initialize all stuff
1938 m_connected = false;
1939 m_establishing = false;
1940 }
1941
1942 wxDatagramSocket& wxDatagramSocket::RecvFrom( wxSockAddress& addr,
1943 void* buf,
1944 wxUint32 nBytes )
1945 {
1946 Read(buf, nBytes);
1947 GetPeer(addr);
1948 return (*this);
1949 }
1950
1951 wxDatagramSocket& wxDatagramSocket::SendTo( const wxSockAddress& addr,
1952 const void* buf,
1953 wxUint32 nBytes )
1954 {
1955 wxASSERT_MSG( m_impl, _T("Socket not initialised") );
1956
1957 m_impl->SetPeer(addr.GetAddress());
1958 Write(buf, nBytes);
1959 return (*this);
1960 }
1961
1962 // ==========================================================================
1963 // wxSocketModule
1964 // ==========================================================================
1965
1966 class wxSocketModule : public wxModule
1967 {
1968 public:
1969 virtual bool OnInit()
1970 {
1971 // wxSocketBase will call Initialize() itself only if sockets are
1972 // really used, don't do it from here
1973 return true;
1974 }
1975
1976 virtual void OnExit()
1977 {
1978 if ( wxSocketBase::IsInitialized() )
1979 wxSocketBase::Shutdown();
1980 }
1981
1982 private:
1983 DECLARE_DYNAMIC_CLASS(wxSocketModule)
1984 };
1985
1986 IMPLEMENT_DYNAMIC_CLASS(wxSocketModule, wxModule)
1987
1988 #endif // wxUSE_SOCKETS