]> git.saurik.com Git - wxWidgets.git/blob - include/wx/unix/private/sockunix.h
rename wxSocketSelectManager to wxSocketFDIOManager, the old name was confusing as...
[wxWidgets.git] / include / wx / unix / private / sockunix.h
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: wx/unix/private/sockunix.h
3 // Purpose: wxSocketImpl implementation for Unix systems
4 // Authors: Guilhem Lavaux, Vadim Zeitlin
5 // Created: April 1997
6 // RCS-ID: $Id$
7 // Copyright: (c) 1997 Guilhem Lavaux
8 // (c) 2008 Vadim Zeitlin
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
11
12 #ifndef _WX_UNIX_GSOCKUNX_H_
13 #define _WX_UNIX_GSOCKUNX_H_
14
15 #include <unistd.h>
16 #include <sys/ioctl.h>
17 #include "wx/private/fdiodispatcher.h"
18
19 class wxSocketImplUnix : public wxSocketImpl,
20 public wxFDIOHandler
21 {
22 public:
23 wxSocketImplUnix(wxSocketBase& wxsocket)
24 : wxSocketImpl(wxsocket)
25 {
26 m_fds[0] =
27 m_fds[1] = -1;
28
29 m_enabledCallbacks = 0;
30 }
31
32 virtual wxSocketError GetLastError() const;
33
34 // wxFDIOHandler methods
35 virtual void OnReadWaiting();
36 virtual void OnWriteWaiting();
37 virtual void OnExceptionWaiting();
38
39 // Unix-specific functions used by wxSocketFDIOManager only
40 bool HasAnyEnabledCallbacks() const { return m_enabledCallbacks != 0; }
41 void EnableCallback(wxFDIODispatcherEntryFlags flag)
42 { m_enabledCallbacks |= flag; }
43 void DisableCallback(wxFDIODispatcherEntryFlags flag)
44 { m_enabledCallbacks &= ~flag; }
45 int GetEnabledCallbacks() const { return m_enabledCallbacks; }
46
47 private:
48 virtual void DoClose()
49 {
50 DisableEvents();
51
52 close(m_fd);
53 }
54
55 virtual void UnblockAndRegisterWithEventLoop()
56 {
57 int trueArg = 1;
58 ioctl(m_fd, FIONBIO, &trueArg);
59
60 EnableEvents();
61 }
62
63 // enable or disable notifications for socket input/output events
64 void EnableEvents() { DoEnableEvents(true); }
65 void DisableEvents() { DoEnableEvents(false); }
66
67 // really enable or disable socket input/output events
68 void DoEnableEvents(bool enable);
69
70 protected:
71 // descriptors for input and output event notification channels associated
72 // with the socket
73 int m_fds[2];
74
75 // the events which are currently enabled for this socket, combination of
76 // wxFDIO_INPUT and wxFDIO_OUTPUT values
77 int m_enabledCallbacks;
78
79 private:
80 // notify the associated wxSocket about a change in socket state and shut
81 // down the socket if the event is wxSOCKET_LOST
82 void OnStateChange(wxSocketNotify event);
83
84 // give it access to our m_fds
85 friend class wxSocketFDBasedManager;
86 };
87
88 // A version of wxSocketManager which uses FDs for socket IO
89 class wxSocketFDBasedManager : public wxSocketManager
90 {
91 public:
92 // no special initialization/cleanup needed when using FDs
93 virtual bool OnInit() { return true; }
94 virtual void OnExit() { }
95
96 protected:
97 // identifies either input or output direction
98 //
99 // NB: the values of this enum shouldn't change
100 enum SocketDir
101 {
102 FD_INPUT,
103 FD_OUTPUT
104 };
105
106 // get the FD index corresponding to the given wxSocketNotify
107 SocketDir GetDirForEvent(wxSocketImpl *socket, wxSocketNotify event)
108 {
109 switch ( event )
110 {
111 default:
112 wxFAIL_MSG( "unknown socket event" );
113 return FD_INPUT; // we must return something
114
115 case wxSOCKET_LOST:
116 wxFAIL_MSG( "unexpected socket event" );
117 return FD_INPUT; // as above
118
119 case wxSOCKET_INPUT:
120 return FD_INPUT;
121
122 case wxSOCKET_OUTPUT:
123 return FD_OUTPUT;
124
125 case wxSOCKET_CONNECTION:
126 // for server sockets we're interested in events indicating
127 // that a new connection is pending, i.e. that accept() will
128 // succeed and this is indicated by socket becoming ready for
129 // reading, while for the other ones we're interested in the
130 // completion of non-blocking connect() which is indicated by
131 // the socket becoming ready for writing
132 return socket->IsServer() ? FD_INPUT : FD_OUTPUT;
133 }
134 }
135
136 // access the FDs we store
137 int& FD(wxSocketImplUnix *socket, SocketDir d)
138 {
139 return socket->m_fds[d];
140 }
141 };
142
143 // Common base class for all ports using X11-like (and hence implemented in
144 // X11, Motif and GTK) AddInput() and RemoveInput() functions
145 class wxSocketInputBasedManager : public wxSocketFDBasedManager
146 {
147 public:
148 virtual void Install_Callback(wxSocketImpl *socket_, wxSocketNotify event)
149 {
150 wxSocketImplUnix * const
151 socket = static_cast<wxSocketImplUnix *>(socket_);
152
153 wxCHECK_RET( socket->m_fd != -1,
154 "shouldn't be called on invalid socket" );
155
156 const SocketDir d = GetDirForEvent(socket, event);
157
158 int& fd = FD(socket, d);
159 if ( fd != -1 )
160 RemoveInput(fd);
161
162 fd = AddInput(socket, socket->m_fd, d);
163 }
164
165 virtual void Uninstall_Callback(wxSocketImpl *socket_, wxSocketNotify event)
166 {
167 wxSocketImplUnix * const
168 socket = static_cast<wxSocketImplUnix *>(socket_);
169
170 const SocketDir d = GetDirForEvent(socket, event);
171
172 int& fd = FD(socket, d);
173 if ( fd != -1 )
174 {
175 RemoveInput(fd);
176 fd = -1;
177 }
178 }
179
180 private:
181 // these functions map directly to XtAdd/RemoveInput() or
182 // gdk_input_add/remove()
183 virtual int AddInput(wxFDIOHandler *handler, int fd, SocketDir d) = 0;
184 virtual void RemoveInput(int fd) = 0;
185 };
186
187 #endif /* _WX_UNIX_GSOCKUNX_H_ */