1 /////////////////////////////////////////////////////////////////////////////
2 // Name: src/common/socket.cpp
3 // Purpose: Socket handler classes
4 // Authors: Guilhem Lavaux, Guillermo Rodriguez Garcia
6 // Copyright: (C) 1999-1997, Guilhem Lavaux
7 // (C) 1999-2000, Guillermo Rodriguez Garcia
8 // (C) 2008 Vadim Zeitlin
10 // License: wxWindows licence
11 /////////////////////////////////////////////////////////////////////////////
13 // ==========================================================================
15 // ==========================================================================
17 // For compilers that support precompilation, includes "wx.h".
18 #include "wx/wxprec.h"
26 #include "wx/socket.h"
29 #include "wx/object.h"
30 #include "wx/string.h"
37 #include "wx/module.h"
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"
46 #include "wx/private/fd.h"
47 #include "wx/private/socket.h"
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
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
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."
68 #define wxSOCKET_MSG_NOSIGNAL 0
71 // DLL options compatibility check:
73 WX_CHECK_BUILD_OPTIONS("wxNet")
75 // --------------------------------------------------------------------------
76 // macros and constants
77 // --------------------------------------------------------------------------
80 #define MAX_DISCARD_SIZE (10 * 1024)
82 #define wxTRACE_Socket _T("wxSocket")
84 // --------------------------------------------------------------------------
86 // --------------------------------------------------------------------------
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
)
94 // ----------------------------------------------------------------------------
96 // ----------------------------------------------------------------------------
101 void SetTimeValFromMS(timeval
& tv
, unsigned long ms
)
103 tv
.tv_sec
= (ms
/ 1000);
104 tv
.tv_usec
= (ms
% 1000) * 1000;
107 } // anonymous namespace
109 // --------------------------------------------------------------------------
111 // --------------------------------------------------------------------------
113 class wxSocketState
: public wxObject
116 wxSocketFlags m_flags
;
117 wxSocketEventFlags m_eventmask
;
122 wxSocketState() : wxObject() {}
124 DECLARE_NO_COPY_CLASS(wxSocketState
)
127 // ============================================================================
129 // ============================================================================
131 wxSocketManager
*wxSocketManager::ms_manager
= NULL
;
134 void wxSocketManager::Set(wxSocketManager
*manager
)
136 wxASSERT_MSG( !ms_manager
, "too late to set manager now" );
138 ms_manager
= manager
;
142 void wxSocketManager::Init()
144 wxASSERT_MSG( !ms_manager
, "shouldn't be initialized twice" );
147 Details: Initialize() creates a hidden window as a sink for socket
148 events, such as 'read completed'. wxMSW has only one message loop
149 for the main thread. If Initialize is called in a secondary thread,
150 the socket window will be created for the secondary thread, but
151 since there is no message loop on this thread, it will never
152 receive events and all socket operations will time out.
153 BTW, the main thread must not be stopped using sleep or block
154 on a semaphore (a bad idea in any case) or socket operations
157 On the Mac side, Initialize() stores a pointer to the CFRunLoop for
158 the main thread. Because secondary threads do not have run loops,
159 adding event notifications to the "Current" loop would have no
160 effect at all, events would never fire.
162 wxASSERT_MSG( wxIsMainThread(),
163 "sockets must be initialized from the main thread" );
165 wxAppConsole
* const app
= wxAppConsole::GetInstance();
166 wxCHECK_RET( app
, "sockets can't be initialized without wxApp" );
168 ms_manager
= app
->GetTraits()->GetSocketManager();
171 // ==========================================================================
173 // ==========================================================================
175 wxSocketImpl::wxSocketImpl(wxSocketBase
& wxsocket
)
176 : m_wxsocket(&wxsocket
)
178 m_fd
= INVALID_SOCKET
;
179 m_error
= wxSOCKET_NOERROR
;
183 SetTimeout(wxsocket
.GetTimeout() * 1000);
185 m_establishing
= false;
189 m_initialRecvBufferSize
= -1;
190 m_initialSendBufferSize
= -1;
193 wxSocketImpl::~wxSocketImpl()
195 if ( m_fd
!= INVALID_SOCKET
)
199 bool wxSocketImpl::PreCreateCheck(const wxSockAddressImpl
& addr
)
201 if ( m_fd
!= INVALID_SOCKET
)
203 m_error
= wxSOCKET_INVSOCK
;
209 m_error
= wxSOCKET_INVADDR
;
216 void wxSocketImpl::PostCreation()
218 // FreeBSD variants can't use MSG_NOSIGNAL, and instead use a socket option
220 EnableSocketOption(SO_NOSIGPIPE
);
224 EnableSocketOption(SO_REUSEADDR
);
228 wxASSERT_MSG( !m_stream
, "broadcasting is for datagram sockets only" );
230 EnableSocketOption(SO_BROADCAST
);
233 if ( m_initialRecvBufferSize
>= 0 )
234 SetSocketOption(SO_RCVBUF
, m_initialRecvBufferSize
);
235 if ( m_initialSendBufferSize
>= 0 )
236 SetSocketOption(SO_SNDBUF
, m_initialSendBufferSize
);
238 // we always put our sockets in unblocked mode and handle blocking
239 // ourselves in DoRead/Write() if wxSOCKET_WAITALL is specified
240 UnblockAndRegisterWithEventLoop();
243 wxSocketError
wxSocketImpl::UpdateLocalAddress()
245 WX_SOCKLEN_T lenAddr
= m_local
.GetLen();
246 if ( getsockname(m_fd
, m_local
.GetWritableAddr(), &lenAddr
) != 0 )
249 m_error
= wxSOCKET_IOERR
;
253 return wxSOCKET_NOERROR
;
256 wxSocketError
wxSocketImpl::CreateServer()
258 if ( !PreCreateCheck(m_local
) )
264 // do create the socket
265 m_fd
= socket(m_local
.GetFamily(), SOCK_STREAM
, 0);
267 if ( m_fd
== INVALID_SOCKET
)
269 m_error
= wxSOCKET_IOERR
;
270 return wxSOCKET_IOERR
;
275 // and then bind to and listen on it
277 // FIXME: should we test for m_dobind here?
278 if ( bind(m_fd
, m_local
.GetAddr(), m_local
.GetLen()) != 0 )
279 m_error
= wxSOCKET_IOERR
;
283 if ( listen(m_fd
, 5) != 0 )
284 m_error
= wxSOCKET_IOERR
;
293 // finally retrieve the address we effectively bound to
294 return UpdateLocalAddress();
297 wxSocketError
wxSocketImpl::CreateClient(bool wait
)
299 if ( !PreCreateCheck(m_peer
) )
302 m_fd
= socket(m_peer
.GetFamily(), SOCK_STREAM
, 0);
304 if ( m_fd
== INVALID_SOCKET
)
306 m_error
= wxSOCKET_IOERR
;
307 return wxSOCKET_IOERR
;
312 // If a local address has been set, then bind to it before calling connect
313 if ( m_local
.IsOk() )
315 if ( bind(m_fd
, m_local
.GetAddr(), m_local
.GetLen()) != 0 )
318 m_error
= wxSOCKET_IOERR
;
324 int rc
= connect(m_fd
, m_peer
.GetAddr(), m_peer
.GetLen());
325 if ( rc
== SOCKET_ERROR
)
327 wxSocketError err
= GetLastError();
328 if ( err
== wxSOCKET_WOULDBLOCK
)
330 m_establishing
= true;
332 // block waiting for connection if we should (otherwise just return
333 // wxSOCKET_WOULDBLOCK to the caller)
336 err
= SelectWithTimeout(wxSOCKET_CONNECTION_FLAG
)
339 m_establishing
= false;
347 m_error
= wxSOCKET_NOERROR
;
354 wxSocketError
wxSocketImpl::CreateUDP()
356 if ( !PreCreateCheck(m_local
) )
362 m_fd
= socket(m_local
.GetFamily(), SOCK_DGRAM
, 0);
364 if ( m_fd
== INVALID_SOCKET
)
366 m_error
= wxSOCKET_IOERR
;
367 return wxSOCKET_IOERR
;
374 if ( bind(m_fd
, m_local
.GetAddr(), m_local
.GetLen()) != 0 )
377 m_error
= wxSOCKET_IOERR
;
381 return UpdateLocalAddress();
384 return wxSOCKET_NOERROR
;
387 wxSocketImpl
*wxSocketImpl::Accept(wxSocketBase
& wxsocket
)
389 wxSockAddressStorage from
;
390 WX_SOCKLEN_T fromlen
= sizeof(from
);
391 const SOCKET fd
= accept(m_fd
, &from
.addr
, &fromlen
);
393 if ( fd
== INVALID_SOCKET
)
396 wxSocketImpl
* const sock
= Create(wxsocket
);
398 sock
->m_peer
= wxSockAddressImpl(from
.addr
, fromlen
);
400 sock
->UnblockAndRegisterWithEventLoop();
406 void wxSocketImpl::Close()
408 if ( m_fd
!= INVALID_SOCKET
)
411 m_fd
= INVALID_SOCKET
;
416 * Disallow further read/write operations on this socket, close
417 * the fd and disable all callbacks.
419 void wxSocketImpl::Shutdown()
421 if ( m_fd
!= INVALID_SOCKET
)
423 shutdown(m_fd
, 1 /* SD_SEND */);
429 * Sets the timeout for blocking calls. Time is expressed in
432 void wxSocketImpl::SetTimeout(unsigned long millis
)
434 SetTimeValFromMS(m_timeout
, millis
);
437 void wxSocketImpl::NotifyOnStateChange(wxSocketNotify event
)
439 m_wxsocket
->OnRequest(event
);
442 /* Address handling */
443 wxSocketError
wxSocketImpl::SetLocal(const wxSockAddressImpl
& local
)
445 /* the socket must be initialized, or it must be a server */
446 if (m_fd
!= INVALID_SOCKET
&& !m_server
)
448 m_error
= wxSOCKET_INVSOCK
;
449 return wxSOCKET_INVSOCK
;
454 m_error
= wxSOCKET_INVADDR
;
455 return wxSOCKET_INVADDR
;
460 return wxSOCKET_NOERROR
;
463 wxSocketError
wxSocketImpl::SetPeer(const wxSockAddressImpl
& peer
)
467 m_error
= wxSOCKET_INVADDR
;
468 return wxSOCKET_INVADDR
;
473 return wxSOCKET_NOERROR
;
476 const wxSockAddressImpl
& wxSocketImpl::GetLocal()
478 if ( !m_local
.IsOk() )
479 UpdateLocalAddress();
484 // ----------------------------------------------------------------------------
486 // ----------------------------------------------------------------------------
488 // this macro wraps the given expression (normally a syscall) in a loop which
489 // ignores any interruptions, i.e. reevaluates it again if it failed and errno
492 #define DO_WHILE_EINTR( rc, syscall ) \
496 while ( rc == -1 && errno == EINTR )
498 #define DO_WHILE_EINTR( rc, syscall ) rc = (syscall)
501 int wxSocketImpl::RecvStream(void *buffer
, int size
)
504 DO_WHILE_EINTR( ret
, recv(m_fd
, static_cast<char *>(buffer
), size
, 0) );
508 // receiving 0 bytes for a TCP socket indicates that the connection was
509 // closed by peer so shut down our end as well (for UDP sockets empty
510 // datagrams are also possible)
511 m_establishing
= false;
512 NotifyOnStateChange(wxSOCKET_LOST
);
516 // do not return an error in this case however
522 int wxSocketImpl::SendStream(const void *buffer
, int size
)
525 DO_WHILE_EINTR( ret
, send(m_fd
, static_cast<const char *>(buffer
), size
,
526 wxSOCKET_MSG_NOSIGNAL
) );
531 int wxSocketImpl::RecvDgram(void *buffer
, int size
)
533 wxSockAddressStorage from
;
534 WX_SOCKLEN_T fromlen
= sizeof(from
);
537 DO_WHILE_EINTR( ret
, recvfrom(m_fd
, static_cast<char *>(buffer
), size
,
538 0, &from
.addr
, &fromlen
) );
540 if ( ret
== SOCKET_ERROR
)
543 m_peer
= wxSockAddressImpl(from
.addr
, fromlen
);
544 if ( !m_peer
.IsOk() )
550 int wxSocketImpl::SendDgram(const void *buffer
, int size
)
552 if ( !m_peer
.IsOk() )
554 m_error
= wxSOCKET_INVADDR
;
559 DO_WHILE_EINTR( ret
, sendto(m_fd
, static_cast<const char *>(buffer
), size
,
560 0, m_peer
.GetAddr(), m_peer
.GetLen()) );
565 int wxSocketImpl::Read(void *buffer
, int size
)
567 // server sockets can't be used for IO, only to accept new connections
568 if ( m_fd
== INVALID_SOCKET
|| m_server
)
570 m_error
= wxSOCKET_INVSOCK
;
574 int ret
= m_stream
? RecvStream(buffer
, size
)
575 : RecvDgram(buffer
, size
);
577 m_error
= ret
== SOCKET_ERROR
? GetLastError() : wxSOCKET_NOERROR
;
582 int wxSocketImpl::Write(const void *buffer
, int size
)
584 if ( m_fd
== INVALID_SOCKET
|| m_server
)
586 m_error
= wxSOCKET_INVSOCK
;
590 int ret
= m_stream
? SendStream(buffer
, size
)
591 : SendDgram(buffer
, size
);
593 m_error
= ret
== SOCKET_ERROR
? GetLastError() : wxSOCKET_NOERROR
;
598 // ==========================================================================
600 // ==========================================================================
602 // --------------------------------------------------------------------------
603 // Initialization and shutdown
604 // --------------------------------------------------------------------------
606 // FIXME-MT: all this is MT-unsafe, of course, we should protect all accesses
607 // to m_countInit with a crit section
608 size_t wxSocketBase::m_countInit
= 0;
610 bool wxSocketBase::IsInitialized()
612 return m_countInit
> 0;
615 bool wxSocketBase::Initialize()
617 if ( !m_countInit
++ )
619 wxSocketManager
* const manager
= wxSocketManager::Get();
620 if ( !manager
|| !manager
->OnInit() )
631 void wxSocketBase::Shutdown()
633 // we should be initialized
634 wxASSERT_MSG( m_countInit
> 0, _T("extra call to Shutdown()") );
635 if ( --m_countInit
== 0 )
637 wxSocketManager
* const manager
= wxSocketManager::Get();
638 wxCHECK_RET( manager
, "should have a socket manager" );
644 // --------------------------------------------------------------------------
646 // --------------------------------------------------------------------------
648 void wxSocketBase::Init()
651 m_type
= wxSOCKET_UNINIT
;
662 m_beingDeleted
= false;
677 if ( !IsInitialized() )
679 // this Initialize() will be undone by wxSocketModule::OnExit(), all
680 // the other calls to it should be matched by a call to Shutdown()
685 wxSocketBase::wxSocketBase()
690 wxSocketBase::wxSocketBase(wxSocketFlags flags
, wxSocketType type
)
699 wxSocketBase::~wxSocketBase()
701 // Just in case the app called Destroy() *and* then deleted the socket
702 // immediately: don't leave dangling pointers.
703 wxAppTraits
*traits
= wxTheApp
? wxTheApp
->GetTraits() : NULL
;
705 traits
->RemoveFromPendingDelete(this);
707 // Shutdown and close the socket
711 // Destroy the implementation object
714 // Free the pushback buffer
719 bool wxSocketBase::Destroy()
721 // Delayed destruction: the socket will be deleted during the next idle
722 // loop iteration. This ensures that all pending events have been
724 m_beingDeleted
= true;
726 // Shutdown and close the socket
729 // Suppress events from now on
732 // schedule this object for deletion
733 wxAppTraits
*traits
= wxTheApp
? wxTheApp
->GetTraits() : NULL
;
736 // let the traits object decide what to do with us
737 traits
->ScheduleForDestroy(this);
739 else // no app or no traits
741 // in wxBase we might have no app object at all, don't leak memory
748 // ----------------------------------------------------------------------------
750 // ----------------------------------------------------------------------------
752 void wxSocketBase::SetError(wxSocketError error
)
754 m_impl
->m_error
= error
;
757 wxSocketError
wxSocketBase::LastError() const
759 return m_impl
->GetError();
762 // --------------------------------------------------------------------------
764 // --------------------------------------------------------------------------
766 // The following IO operations update m_lcount:
767 // {Read, Write, ReadMsg, WriteMsg, Peek, Unread, Discard}
768 bool wxSocketBase::Close()
770 // Interrupt pending waits
776 m_establishing
= false;
780 void wxSocketBase::ShutdownOutput()
786 wxSocketBase
& wxSocketBase::Read(void* buffer
, wxUint32 nbytes
)
791 m_lcount
= DoRead(buffer
, nbytes
);
793 // Allow read events from now on
799 wxUint32
wxSocketBase::DoRead(void* buffer_
, wxUint32 nbytes
)
801 wxCHECK_MSG( m_impl
, 0, "socket must be valid" );
803 // We use pointer arithmetic here which doesn't work with void pointers.
804 char *buffer
= static_cast<char *>(buffer_
);
805 wxCHECK_MSG( buffer
, 0, "NULL buffer" );
807 // Try the push back buffer first, even before checking whether the socket
808 // is valid to allow reading previously pushed back data from an already
810 wxUint32 total
= GetPushback(buffer
, nbytes
, false);
816 // our socket is non-blocking so Read() will return immediately if
817 // there is nothing to read yet and it's more efficient to try it first
818 // before entering DoWait() which is going to start dispatching GUI
819 // events and, even more importantly, we must do this under Windows
820 // where we're not going to get notifications about socket being ready
821 // for reading before we read all the existing data from it
822 const int ret
= m_connected
? m_impl
->Read(buffer
, nbytes
) : 0;
825 if ( m_impl
->GetLastError() == wxSOCKET_WOULDBLOCK
)
827 // if we don't want to wait, just return immediately
828 if ( m_flags
& wxSOCKET_NOWAIT
)
831 // otherwise wait until the socket becomes ready for reading or
832 // an error occurs on it
833 if ( !DoWaitWithTimeout(wxSOCKET_INPUT_FLAG
|
834 wxSOCKET_LOST_FLAG
) )
836 // and exit if the timeout elapsed before it did
837 SetError(wxSOCKET_TIMEDOUT
);
846 SetError(wxSOCKET_IOERR
);
852 // for connection-oriented (e.g. TCP) sockets we can only read
853 // 0 bytes if the other end has been closed, and for connectionless
854 // ones (UDP) this flag doesn't make sense anyhow so we can set it
855 // to true too without doing any harm
858 // we're not going to read anything else and so if we haven't read
859 // anything (or not everything in wxSOCKET_WAITALL case) already,
861 if ( (m_flags
& wxSOCKET_WAITALL
) || !total
)
862 SetError(wxSOCKET_IOERR
);
868 // if we are happy to read something and not the entire nbytes bytes,
870 if ( !(m_flags
& wxSOCKET_WAITALL
) )
880 wxSocketBase
& wxSocketBase::ReadMsg(void* buffer
, wxUint32 nbytes
)
884 unsigned char sig
[4];
885 unsigned char len
[4];
891 int old_flags
= m_flags
;
892 SetFlags((m_flags
& wxSOCKET_BLOCK
) | wxSOCKET_WAITALL
);
895 if ( DoRead(&msg
, sizeof(msg
)) == sizeof(msg
) )
897 wxUint32 sig
= (wxUint32
)msg
.sig
[0];
898 sig
|= (wxUint32
)(msg
.sig
[1] << 8);
899 sig
|= (wxUint32
)(msg
.sig
[2] << 16);
900 sig
|= (wxUint32
)(msg
.sig
[3] << 24);
902 if ( sig
== 0xfeeddead )
904 wxUint32 len
= (wxUint32
)msg
.len
[0];
905 len
|= (wxUint32
)(msg
.len
[1] << 8);
906 len
|= (wxUint32
)(msg
.len
[2] << 16);
907 len
|= (wxUint32
)(msg
.len
[3] << 24);
918 // Don't attempt to read if the msg was zero bytes long.
919 m_lcount
= len
? DoRead(buffer
, len
) : 0;
923 char discard_buffer
[MAX_DISCARD_SIZE
];
926 // NOTE: discarded bytes don't add to m_lcount.
929 discard_len
= len2
> MAX_DISCARD_SIZE
932 discard_len
= DoRead(discard_buffer
, (wxUint32
)discard_len
);
933 len2
-= (wxUint32
)discard_len
;
935 while ((discard_len
> 0) && len2
);
938 if ( !len2
&& DoRead(&msg
, sizeof(msg
)) == sizeof(msg
) )
940 sig
= (wxUint32
)msg
.sig
[0];
941 sig
|= (wxUint32
)(msg
.sig
[1] << 8);
942 sig
|= (wxUint32
)(msg
.sig
[2] << 16);
943 sig
|= (wxUint32
)(msg
.sig
[3] << 24);
945 if ( sig
== 0xdeadfeed )
952 SetError(wxSOCKET_IOERR
);
960 wxSocketBase
& wxSocketBase::Peek(void* buffer
, wxUint32 nbytes
)
965 m_lcount
= DoRead(buffer
, nbytes
);
966 Pushback(buffer
, m_lcount
);
968 // Allow read events again
974 wxSocketBase
& wxSocketBase::Write(const void *buffer
, wxUint32 nbytes
)
979 m_lcount
= DoWrite(buffer
, nbytes
);
981 // Allow write events again
987 // This function is a mirror image of DoRead() except that it doesn't use the
988 // push back buffer and doesn't treat 0 return value specially (normally this
989 // shouldn't happen at all here), so please see comments there for explanations
990 wxUint32
wxSocketBase::DoWrite(const void *buffer_
, wxUint32 nbytes
)
992 wxCHECK_MSG( m_impl
, 0, "socket must be valid" );
994 const char *buffer
= static_cast<const char *>(buffer_
);
995 wxCHECK_MSG( buffer
, 0, "NULL buffer" );
1002 if ( (m_flags
& wxSOCKET_WAITALL
) || !total
)
1003 SetError(wxSOCKET_IOERR
);
1007 const int ret
= m_impl
->Write(buffer
, nbytes
);
1010 if ( m_impl
->GetLastError() == wxSOCKET_WOULDBLOCK
)
1012 if ( m_flags
& wxSOCKET_NOWAIT
)
1015 if ( !DoWaitWithTimeout(wxSOCKET_OUTPUT_FLAG
|
1016 wxSOCKET_LOST_FLAG
) )
1018 SetError(wxSOCKET_TIMEDOUT
);
1024 else // "real" error
1026 SetError(wxSOCKET_IOERR
);
1033 if ( !(m_flags
& wxSOCKET_WAITALL
) )
1043 wxSocketBase
& wxSocketBase::WriteMsg(const void *buffer
, wxUint32 nbytes
)
1047 unsigned char sig
[4];
1048 unsigned char len
[4];
1051 // Mask write events
1054 const int old_flags
= m_flags
;
1055 SetFlags((m_flags
& wxSOCKET_BLOCK
) | wxSOCKET_WAITALL
);
1057 msg
.sig
[0] = (unsigned char) 0xad;
1058 msg
.sig
[1] = (unsigned char) 0xde;
1059 msg
.sig
[2] = (unsigned char) 0xed;
1060 msg
.sig
[3] = (unsigned char) 0xfe;
1062 msg
.len
[0] = (unsigned char) (nbytes
& 0xff);
1063 msg
.len
[1] = (unsigned char) ((nbytes
>> 8) & 0xff);
1064 msg
.len
[2] = (unsigned char) ((nbytes
>> 16) & 0xff);
1065 msg
.len
[3] = (unsigned char) ((nbytes
>> 24) & 0xff);
1068 if ( DoWrite(&msg
, sizeof(msg
)) == sizeof(msg
) )
1070 m_lcount
= DoWrite(buffer
, nbytes
);
1071 if ( m_lcount
== nbytes
)
1073 msg
.sig
[0] = (unsigned char) 0xed;
1074 msg
.sig
[1] = (unsigned char) 0xfe;
1075 msg
.sig
[2] = (unsigned char) 0xad;
1076 msg
.sig
[3] = (unsigned char) 0xde;
1080 msg
.len
[3] = (char) 0;
1082 if ( DoWrite(&msg
, sizeof(msg
)) == sizeof(msg
))
1088 SetError(wxSOCKET_IOERR
);
1091 SetFlags(old_flags
);
1096 wxSocketBase
& wxSocketBase::Unread(const void *buffer
, wxUint32 nbytes
)
1099 Pushback(buffer
, nbytes
);
1101 SetError(wxSOCKET_NOERROR
);
1107 wxSocketBase
& wxSocketBase::Discard()
1109 char *buffer
= new char[MAX_DISCARD_SIZE
];
1116 const int old_flags
= m_flags
;
1117 SetFlags(wxSOCKET_NOWAIT
);
1121 ret
= DoRead(buffer
, MAX_DISCARD_SIZE
);
1124 while (ret
== MAX_DISCARD_SIZE
);
1128 SetError(wxSOCKET_NOERROR
);
1130 // Allow read events again
1133 SetFlags(old_flags
);
1138 // --------------------------------------------------------------------------
1140 // --------------------------------------------------------------------------
1143 This function will check for the events specified in the flags parameter,
1144 and it will return a mask indicating which operations can be performed.
1146 wxSocketEventFlags
wxSocketImpl::Select(wxSocketEventFlags flags
,
1147 const timeval
*timeout
)
1149 if ( m_fd
== INVALID_SOCKET
)
1150 return (wxSOCKET_LOST_FLAG
& flags
);
1156 tv
.tv_sec
= tv
.tv_usec
= 0;
1158 // prepare the FD sets, passing NULL for the one(s) we don't use
1160 readfds
, *preadfds
= NULL
,
1161 writefds
, *pwritefds
= NULL
,
1162 exceptfds
; // always want to know about errors
1164 if ( flags
& wxSOCKET_INPUT_FLAG
)
1166 preadfds
= &readfds
;
1167 wxFD_ZERO(preadfds
);
1168 wxFD_SET(m_fd
, preadfds
);
1171 // when using non-blocking connect() the socket becomes connected
1172 // (successfully or not) when it becomes writable
1173 if ( flags
& (wxSOCKET_OUTPUT_FLAG
| wxSOCKET_CONNECTION_FLAG
) )
1175 pwritefds
= &writefds
;
1176 wxFD_ZERO(pwritefds
);
1177 wxFD_SET(m_fd
, pwritefds
);
1180 wxFD_ZERO(&exceptfds
);
1181 wxFD_SET(m_fd
, &exceptfds
);
1183 const int rc
= select(m_fd
+ 1, preadfds
, pwritefds
, &exceptfds
, &tv
);
1185 // check for errors first
1186 if ( rc
== -1 || wxFD_ISSET(m_fd
, &exceptfds
) )
1188 m_establishing
= false;
1190 return wxSOCKET_LOST_FLAG
& flags
;
1196 wxASSERT_MSG( rc
== 1, "unexpected select() return value" );
1198 wxSocketEventFlags detected
= 0;
1199 if ( preadfds
&& wxFD_ISSET(m_fd
, preadfds
) )
1200 detected
|= wxSOCKET_INPUT_FLAG
;
1202 if ( pwritefds
&& wxFD_ISSET(m_fd
, pwritefds
) )
1204 // check for the case of non-blocking connect()
1205 if ( m_establishing
&& !m_server
)
1208 SOCKOPTLEN_T len
= sizeof(error
);
1209 m_establishing
= false;
1210 getsockopt(m_fd
, SOL_SOCKET
, SO_ERROR
, (char*)&error
, &len
);
1213 detected
= wxSOCKET_LOST_FLAG
;
1215 detected
|= wxSOCKET_CONNECTION_FLAG
;
1217 else // not called to get non-blocking connect() status
1219 detected
|= wxSOCKET_OUTPUT_FLAG
;
1223 return detected
& flags
;
1227 wxSocketBase::DoWait(long seconds
, long milliseconds
, wxSocketEventFlags flags
)
1229 // Use either the provided timeout or the default timeout value associated
1230 // with this socket.
1232 // TODO: allow waiting forever, see #9443
1233 const long timeout
= seconds
== -1 ? m_timeout
* 1000
1234 : seconds
* 1000 + milliseconds
;
1236 return DoWait(timeout
, flags
);
1240 wxSocketBase::DoWait(long timeout
, wxSocketEventFlags flags
)
1242 wxCHECK_MSG( m_impl
, false, "can't wait on invalid socket" );
1244 // we're never going to become ready if we're not connected (any more)
1245 if ( !m_connected
&& !m_establishing
)
1246 return (flags
& wxSOCKET_LOST_FLAG
) != 0;
1248 // This can be set to true from Interrupt() to exit this function a.s.a.p.
1249 m_interrupt
= false;
1252 const wxMilliClock_t timeEnd
= wxGetLocalTimeMillis() + timeout
;
1254 // Get the active event loop which we'll use for the message dispatching
1255 // when running in the main thread unless this was explicitly disabled by
1256 // setting wxSOCKET_BLOCK flag
1257 wxEventLoopBase
*eventLoop
;
1258 if ( !(m_flags
& wxSOCKET_BLOCK
) && wxIsMainThread() )
1260 eventLoop
= wxEventLoop::GetActive();
1262 else // in worker thread
1264 // We never dispatch messages from threads other than the main one.
1268 // Wait until we receive the event we're waiting for or the timeout expires
1269 // (but note that we always execute the loop at least once, even if timeout
1270 // is 0 as this is used for polling)
1271 bool gotEvent
= false;
1272 for ( bool firstTime
= true; !m_interrupt
; firstTime
= false )
1274 long timeLeft
= wxMilliClockToLong(timeEnd
- wxGetLocalTimeMillis());
1283 wxSocketEventFlags events
;
1286 // reset them before starting to wait
1289 eventLoop
->DispatchTimeout(timeLeft
);
1291 events
= m_eventsgot
;
1293 else // no event loop or waiting in another thread
1295 // as explained below, we should always check for wxSOCKET_LOST_FLAG
1297 SetTimeValFromMS(tv
, timeLeft
);
1298 events
= m_impl
->Select(flags
| wxSOCKET_LOST_FLAG
, &tv
);
1301 // always check for wxSOCKET_LOST_FLAG, even if flags doesn't include
1302 // it, as continuing to wait for anything else after getting it is
1304 if ( events
& wxSOCKET_LOST_FLAG
)
1306 m_connected
= false;
1307 m_establishing
= false;
1308 if ( flags
& wxSOCKET_LOST_FLAG
)
1313 // otherwise mask out the bits we're not interested in
1316 // Incoming connection (server) or connection established (client)?
1317 if ( events
& wxSOCKET_CONNECTION_FLAG
)
1320 m_establishing
= false;
1325 // Data available or output buffer ready?
1326 if ( (events
& wxSOCKET_INPUT_FLAG
) || (events
& wxSOCKET_OUTPUT_FLAG
) )
1336 bool wxSocketBase::Wait(long seconds
, long milliseconds
)
1338 return DoWait(seconds
, milliseconds
,
1339 wxSOCKET_INPUT_FLAG
|
1340 wxSOCKET_OUTPUT_FLAG
|
1341 wxSOCKET_CONNECTION_FLAG
|
1346 bool wxSocketBase::WaitForRead(long seconds
, long milliseconds
)
1348 // Check pushback buffer before entering DoWait
1352 // Check if the socket is not already ready for input, if it is, there is
1353 // no need to start waiting for it (worse, we'll actually never get a
1354 // notification about the socket becoming ready if it is already under
1356 if ( m_impl
->Select(wxSOCKET_INPUT_FLAG
) )
1359 // Note that wxSOCKET_LOST_FLAG has to be explicitly passed to DoWait
1360 // because of the semantics of WaitForRead: a return value of true means
1361 // that a Read call will return immediately, not that there is
1362 // actually data to read.
1363 return DoWait(seconds
, milliseconds
, wxSOCKET_INPUT_FLAG
| wxSOCKET_LOST_FLAG
);
1367 bool wxSocketBase::WaitForWrite(long seconds
, long milliseconds
)
1369 if ( m_impl
->Select(wxSOCKET_OUTPUT_FLAG
) )
1372 return DoWait(seconds
, milliseconds
, wxSOCKET_OUTPUT_FLAG
| wxSOCKET_LOST_FLAG
);
1375 bool wxSocketBase::WaitForLost(long seconds
, long milliseconds
)
1377 return DoWait(seconds
, milliseconds
, wxSOCKET_LOST_FLAG
);
1380 // --------------------------------------------------------------------------
1382 // --------------------------------------------------------------------------
1385 // Get local or peer address
1388 bool wxSocketBase::GetPeer(wxSockAddress
& addr
) const
1390 wxCHECK_MSG( m_impl
, false, "invalid socket" );
1392 const wxSockAddressImpl
& peer
= m_impl
->GetPeer();
1396 addr
.SetAddress(peer
);
1401 bool wxSocketBase::GetLocal(wxSockAddress
& addr
) const
1403 wxCHECK_MSG( m_impl
, false, "invalid socket" );
1405 const wxSockAddressImpl
& local
= m_impl
->GetLocal();
1406 if ( !local
.IsOk() )
1409 addr
.SetAddress(local
);
1415 // Save and restore socket state
1418 void wxSocketBase::SaveState()
1420 wxSocketState
*state
;
1422 state
= new wxSocketState();
1424 state
->m_flags
= m_flags
;
1425 state
->m_notify
= m_notify
;
1426 state
->m_eventmask
= m_eventmask
;
1427 state
->m_clientData
= m_clientData
;
1429 m_states
.Append(state
);
1432 void wxSocketBase::RestoreState()
1434 wxList::compatibility_iterator node
;
1435 wxSocketState
*state
;
1437 node
= m_states
.GetLast();
1441 state
= (wxSocketState
*)node
->GetData();
1443 m_flags
= state
->m_flags
;
1444 m_notify
= state
->m_notify
;
1445 m_eventmask
= state
->m_eventmask
;
1446 m_clientData
= state
->m_clientData
;
1448 m_states
.Erase(node
);
1453 // Timeout and flags
1456 void wxSocketBase::SetTimeout(long seconds
)
1458 m_timeout
= seconds
;
1461 m_impl
->SetTimeout(m_timeout
* 1000);
1464 void wxSocketBase::SetFlags(wxSocketFlags flags
)
1466 // Do some sanity checking on the flags used: not all values can be used
1468 wxASSERT_MSG( !(flags
& wxSOCKET_NOWAIT
) ||
1469 !(flags
& (wxSOCKET_WAITALL
| wxSOCKET_BLOCK
)),
1470 "Using wxSOCKET_WAITALL or wxSOCKET_BLOCK with "
1471 "wxSOCKET_NOWAIT doesn't make sense" );
1477 // --------------------------------------------------------------------------
1479 // --------------------------------------------------------------------------
1481 void wxSocketBase::OnRequest(wxSocketNotify notification
)
1483 wxSocketEventFlags flag
= 0;
1484 switch ( notification
)
1486 case wxSOCKET_INPUT
:
1487 flag
= wxSOCKET_INPUT_FLAG
;
1490 case wxSOCKET_OUTPUT
:
1491 flag
= wxSOCKET_OUTPUT_FLAG
;
1494 case wxSOCKET_CONNECTION
:
1495 flag
= wxSOCKET_CONNECTION_FLAG
;
1499 flag
= wxSOCKET_LOST_FLAG
;
1503 wxFAIL_MSG( "unknown wxSocket notification" );
1506 // if we lost the connection the socket is now closed
1507 if ( notification
== wxSOCKET_LOST
)
1510 // remember the events which were generated for this socket, we're going to
1511 // use this in DoWait()
1512 m_eventsgot
|= flag
;
1514 // send the wx event if enabled and we're interested in it
1515 if ( m_notify
&& (m_eventmask
& flag
) && m_handler
)
1517 // If we are in the middle of a R/W operation, do not propagate events
1518 // to users. Also, filter 'late' events which are no longer valid.
1519 if ( notification
== wxSOCKET_INPUT
)
1521 if ( m_reading
|| !m_impl
->Select(wxSOCKET_INPUT_FLAG
) )
1524 else if ( notification
== wxSOCKET_OUTPUT
)
1526 if ( m_writing
|| !m_impl
->Select(wxSOCKET_OUTPUT_FLAG
) )
1530 wxSocketEvent
event(m_id
);
1531 event
.m_event
= notification
;
1532 event
.m_clientData
= m_clientData
;
1533 event
.SetEventObject(this);
1535 m_handler
->AddPendingEvent(event
);
1539 void wxSocketBase::Notify(bool notify
)
1544 void wxSocketBase::SetNotify(wxSocketEventFlags flags
)
1546 m_eventmask
= flags
;
1549 void wxSocketBase::SetEventHandler(wxEvtHandler
& handler
, int id
)
1551 m_handler
= &handler
;
1555 // --------------------------------------------------------------------------
1557 // --------------------------------------------------------------------------
1559 void wxSocketBase::Pushback(const void *buffer
, wxUint32 size
)
1563 if (m_unread
== NULL
)
1564 m_unread
= malloc(size
);
1569 tmp
= malloc(m_unrd_size
+ size
);
1570 memcpy((char *)tmp
+ size
, m_unread
, m_unrd_size
);
1576 m_unrd_size
+= size
;
1578 memcpy(m_unread
, buffer
, size
);
1581 wxUint32
wxSocketBase::GetPushback(void *buffer
, wxUint32 size
, bool peek
)
1583 wxCHECK_MSG( buffer
, 0, "NULL buffer" );
1588 if (size
> (m_unrd_size
-m_unrd_cur
))
1589 size
= m_unrd_size
-m_unrd_cur
;
1591 memcpy(buffer
, (char *)m_unread
+ m_unrd_cur
, size
);
1596 if (m_unrd_size
== m_unrd_cur
)
1609 // ==========================================================================
1611 // ==========================================================================
1613 // --------------------------------------------------------------------------
1615 // --------------------------------------------------------------------------
1617 wxSocketServer::wxSocketServer(const wxSockAddress
& addr
,
1618 wxSocketFlags flags
)
1619 : wxSocketBase(flags
, wxSOCKET_SERVER
)
1621 wxLogTrace( wxTRACE_Socket
, _T("Opening wxSocketServer") );
1623 m_impl
= wxSocketImpl::Create(*this);
1627 wxLogTrace( wxTRACE_Socket
, _T("*** Failed to create m_impl") );
1631 // Setup the socket as server
1632 m_impl
->SetLocal(addr
.GetAddress());
1634 if (GetFlags() & wxSOCKET_REUSEADDR
) {
1635 m_impl
->SetReusable();
1637 if (GetFlags() & wxSOCKET_BROADCAST
) {
1638 m_impl
->SetBroadcast();
1640 if (GetFlags() & wxSOCKET_NOBIND
) {
1641 m_impl
->DontDoBind();
1644 if (m_impl
->CreateServer() != wxSOCKET_NOERROR
)
1649 wxLogTrace( wxTRACE_Socket
, _T("*** CreateServer() failed") );
1653 wxLogTrace( wxTRACE_Socket
, _T("wxSocketServer on fd %d"), m_impl
->m_fd
);
1656 // --------------------------------------------------------------------------
1658 // --------------------------------------------------------------------------
1660 bool wxSocketServer::AcceptWith(wxSocketBase
& sock
, bool wait
)
1662 if ( !m_impl
|| (m_impl
->m_fd
== INVALID_SOCKET
) || !m_impl
->IsServer() )
1664 wxFAIL_MSG( "can only be called for a valid server socket" );
1666 SetError(wxSOCKET_INVSOCK
);
1673 // wait until we get a connection
1674 if ( !m_impl
->SelectWithTimeout(wxSOCKET_INPUT_FLAG
) )
1676 SetError(wxSOCKET_TIMEDOUT
);
1682 sock
.m_impl
= m_impl
->Accept(sock
);
1686 SetError(m_impl
->GetLastError());
1691 sock
.m_type
= wxSOCKET_BASE
;
1692 sock
.m_connected
= true;
1697 wxSocketBase
*wxSocketServer::Accept(bool wait
)
1699 wxSocketBase
* sock
= new wxSocketBase();
1701 sock
->SetFlags(m_flags
);
1703 if (!AcceptWith(*sock
, wait
))
1712 bool wxSocketServer::WaitForAccept(long seconds
, long milliseconds
)
1714 return DoWait(seconds
, milliseconds
, wxSOCKET_CONNECTION_FLAG
);
1717 bool wxSocketBase::GetOption(int level
, int optname
, void *optval
, int *optlen
)
1719 wxASSERT_MSG( m_impl
, _T("Socket not initialised") );
1721 SOCKOPTLEN_T lenreal
= *optlen
;
1722 if ( getsockopt(m_impl
->m_fd
, level
, optname
,
1723 static_cast<char *>(optval
), &lenreal
) != 0 )
1732 wxSocketBase::SetOption(int level
, int optname
, const void *optval
, int optlen
)
1734 wxASSERT_MSG( m_impl
, _T("Socket not initialised") );
1736 return setsockopt(m_impl
->m_fd
, level
, optname
,
1737 static_cast<const char *>(optval
), optlen
) == 0;
1740 bool wxSocketBase::SetLocal(const wxIPV4address
& local
)
1742 m_localAddress
= local
;
1747 // ==========================================================================
1749 // ==========================================================================
1751 // --------------------------------------------------------------------------
1753 // --------------------------------------------------------------------------
1755 wxSocketClient::wxSocketClient(wxSocketFlags flags
)
1756 : wxSocketBase(flags
, wxSOCKET_CLIENT
)
1758 m_initialRecvBufferSize
=
1759 m_initialSendBufferSize
= -1;
1762 wxSocketClient::~wxSocketClient()
1766 // --------------------------------------------------------------------------
1768 // --------------------------------------------------------------------------
1770 bool wxSocketClient::DoConnect(const wxSockAddress
& remote
,
1771 const wxSockAddress
* local
,
1776 // Shutdown and destroy the old socket
1781 m_connected
= false;
1782 m_establishing
= false;
1784 // Create and set up the new one
1785 m_impl
= wxSocketImpl::Create(*this);
1789 // Reuse makes sense for clients too, if we are trying to rebind to the same port
1790 if (GetFlags() & wxSOCKET_REUSEADDR
)
1791 m_impl
->SetReusable();
1792 if (GetFlags() & wxSOCKET_BROADCAST
)
1793 m_impl
->SetBroadcast();
1794 if (GetFlags() & wxSOCKET_NOBIND
)
1795 m_impl
->DontDoBind();
1797 // Bind to the local IP address and port, when provided or if one had been
1799 if ( !local
&& m_localAddress
.GetAddress().IsOk() )
1800 local
= &m_localAddress
;
1803 m_impl
->SetLocal(local
->GetAddress());
1805 m_impl
->SetInitialSocketBuffers(m_initialRecvBufferSize
, m_initialSendBufferSize
);
1807 m_impl
->SetPeer(remote
.GetAddress());
1809 // Finally do create the socket and connect to the peer
1810 const wxSocketError err
= m_impl
->CreateClient(wait
);
1812 if ( err
!= wxSOCKET_NOERROR
)
1814 if ( err
== wxSOCKET_WOULDBLOCK
)
1816 wxASSERT_MSG( !wait
, "shouldn't get this for blocking connect" );
1818 m_establishing
= true;
1828 bool wxSocketClient::Connect(const wxSockAddress
& remote
, bool wait
)
1830 return DoConnect(remote
, NULL
, wait
);
1833 bool wxSocketClient::Connect(const wxSockAddress
& remote
,
1834 const wxSockAddress
& local
,
1837 return DoConnect(remote
, &local
, wait
);
1840 bool wxSocketClient::WaitOnConnect(long seconds
, long milliseconds
)
1844 // this happens if the initial attempt to connect succeeded without
1849 wxCHECK_MSG( m_establishing
&& m_impl
, false,
1850 "No connection establishment attempt in progress" );
1852 // we must specify wxSOCKET_LOST_FLAG here explicitly because we must return
1853 // true if the connection establishment process is finished, whether it is
1854 // over because we successfully connected or because we were not able to
1856 return DoWait(seconds
, milliseconds
,
1857 wxSOCKET_CONNECTION_FLAG
| wxSOCKET_LOST_FLAG
);
1860 // ==========================================================================
1862 // ==========================================================================
1864 wxDatagramSocket::wxDatagramSocket( const wxSockAddress
& addr
,
1865 wxSocketFlags flags
)
1866 : wxSocketBase( flags
, wxSOCKET_DATAGRAM
)
1868 // Create the socket
1869 m_impl
= wxSocketImpl::Create(*this);
1874 // Setup the socket as non connection oriented
1875 m_impl
->SetLocal(addr
.GetAddress());
1876 if (flags
& wxSOCKET_REUSEADDR
)
1878 m_impl
->SetReusable();
1880 if (GetFlags() & wxSOCKET_BROADCAST
)
1882 m_impl
->SetBroadcast();
1884 if (GetFlags() & wxSOCKET_NOBIND
)
1886 m_impl
->DontDoBind();
1889 if ( m_impl
->CreateUDP() != wxSOCKET_NOERROR
)
1896 // Initialize all stuff
1897 m_connected
= false;
1898 m_establishing
= false;
1901 wxDatagramSocket
& wxDatagramSocket::RecvFrom( wxSockAddress
& addr
,
1910 wxDatagramSocket
& wxDatagramSocket::SendTo( const wxSockAddress
& addr
,
1914 wxASSERT_MSG( m_impl
, _T("Socket not initialised") );
1916 m_impl
->SetPeer(addr
.GetAddress());
1921 // ==========================================================================
1923 // ==========================================================================
1925 class wxSocketModule
: public wxModule
1928 virtual bool OnInit()
1930 // wxSocketBase will call Initialize() itself only if sockets are
1931 // really used, don't do it from here
1935 virtual void OnExit()
1937 if ( wxSocketBase::IsInitialized() )
1938 wxSocketBase::Shutdown();
1942 DECLARE_DYNAMIC_CLASS(wxSocketModule
)
1945 IMPLEMENT_DYNAMIC_CLASS(wxSocketModule
, wxModule
)
1947 #endif // wxUSE_SOCKETS