1 | /* -*- C++ -*- |
2 | * Copyright (C) 2003,2005 Thiago Macieira <thiago@kde.org> |
3 | * |
4 | * |
5 | * Permission is hereby granted, free of charge, to any person obtaining |
6 | * a copy of this software and associated documentation files (the |
7 | * "Software"), to deal in the Software without restriction, including |
8 | * without limitation the rights to use, copy, modify, merge, publish, |
9 | * distribute, sublicense, and/or sell copies of the Software, and to |
10 | * permit persons to whom the Software is furnished to do so, subject to |
11 | * the following conditions: |
12 | * |
13 | * The above copyright notice and this permission notice shall be included |
14 | * in all copies or substantial portions of the Software. |
15 | * |
16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, |
17 | * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF |
18 | * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND |
19 | * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE |
20 | * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION |
21 | * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION |
22 | * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. |
23 | */ |
24 | |
25 | #ifndef KSTREAMSOCKET_H |
26 | #define KSTREAMSOCKET_H |
27 | |
28 | #include <QtCore/QString> |
29 | |
30 | #include "k3clientsocketbase.h" |
31 | |
32 | /** A namespace to store all networking-related (socket) classes. */ |
33 | namespace KNetwork { |
34 | |
35 | class KResolverEntry; |
36 | class KServerSocket; |
37 | class KBufferedSocket; |
38 | |
39 | class KStreamSocketPrivate; |
40 | /** @class KStreamSocket k3streamsocket.h k3streamsocket.h |
41 | * @brief Simple stream socket |
42 | * |
43 | * This class provides functionality to creating unbuffered, stream |
44 | * sockets. In the case of Internet (IP) sockets, this class creates and |
45 | * uses TCP/IP sockets. |
46 | * |
47 | * Objects of this class start, by default, on non-blocking mode. Call |
48 | * setBlocking if you wish to change that. |
49 | * |
50 | * KStreamSocket objects are thread-safe and can be used in auxiliary |
51 | * threads (i.e., not the thread in which the Qt event loop runs in). |
52 | * Note that KBufferedSocket cannot be used reliably in an auxiliary thread. |
53 | * |
54 | * Sample usage: |
55 | * \code |
56 | * QByteArray httpGet(const QString& hostname) |
57 | * { |
58 | * KStreamSocket socket(hostname, "http"); |
59 | * if (!socket.connect()) |
60 | * return QByteArray(); |
61 | * QByteArray data = socket.readAll(); |
62 | * return data; |
63 | * } |
64 | * \endcode |
65 | * |
66 | * Here's another sample, showing asynchronous operation: |
67 | * \code |
68 | * DataRetriever::DataRetriever(const QString& hostname, const QString& port) |
69 | * : socket(hostname, port) |
70 | * { |
71 | * // connect signals to our slots |
72 | * QObject::connect(&socket, SIGNAL(connected(const KNetwork::KResolverEntry&)), |
73 | * this, SLOT(slotSocketConnected())); |
74 | * QObject::connect(&socket, SIGNAL(gotError(int)), |
75 | * this, SLOT(slotSocketError(int))); |
76 | * QObject::connect(&socket, SIGNAL(readyRead()), |
77 | * this, SLOT(slotSocketReadyToRead())); |
78 | * QObject::connect(&socket, SIGNAL(readyWrite()), |
79 | * this, SLOT(slotSocketReadyToWrite())); |
80 | * |
81 | * // set non-blocking mode in order to work asynchronously |
82 | * socket.setBlocking(false); |
83 | * |
84 | * // turn on signal emission |
85 | * socket.enableRead(true); |
86 | * socket.enableWrite(true); |
87 | * |
88 | * // start connecting |
89 | * socket.connect(); |
90 | * } |
91 | * \endcode |
92 | * |
93 | * @see KNetwork::KBufferedSocket, KNetwork::KServerSocket |
94 | * @author Thiago Macieira <thiago@kde.org> |
95 | * @version 0.9 |
96 | * @deprecated Use KSocketFactory or KLocalSocket instead |
97 | */ |
98 | class KDECORE_EXPORT_DEPRECATED KStreamSocket: public KClientSocketBase |
99 | { |
100 | Q_OBJECT |
101 | |
102 | public: |
103 | /** |
104 | * Default constructor. |
105 | * |
106 | * @param node destination host |
107 | * @param service destination service to connect to |
108 | * @param parent the parent QObject object |
109 | */ |
110 | explicit KStreamSocket(const QString& node = QString(), const QString& service = QString(), |
111 | QObject* parent = 0L); |
112 | |
113 | /** |
114 | * Destructor. This closes the socket. |
115 | */ |
116 | virtual ~KStreamSocket(); |
117 | |
118 | /** |
119 | * Retrieves the timeout value (in milliseconds). |
120 | */ |
121 | int timeout() const; |
122 | |
123 | /** |
124 | * Retrieves the remaining timeout time (in milliseconds). This value |
125 | * equals timeout() if there's no connection in progress. |
126 | */ |
127 | int remainingTimeout() const; |
128 | |
129 | /** |
130 | * Sets the timeout value. Setting this value while a connection attempt |
131 | * is in progress will reset the timer. |
132 | * |
133 | * Please note that the timeout value is valid for the connection attempt |
134 | * only. No other operations are timed against this value -- including the |
135 | * name lookup associated. |
136 | * |
137 | * @param msecs the timeout value in milliseconds |
138 | */ |
139 | void setTimeout(int msecs); |
140 | |
141 | /** |
142 | * Binds this socket to the given nodename and service, |
143 | * or use the default ones if none are given. In order to bind to a service |
144 | * and allow the operating system to choose the interface, set @p node to |
145 | * QString(). |
146 | * |
147 | * Reimplemented from KClientSocketBase. |
148 | * |
149 | * Upon successful binding, the bound() signal will be |
150 | * emitted. If an error is found, the gotError() |
151 | * signal will be emitted. |
152 | * |
153 | * @note Due to the internals of the name lookup and binding |
154 | * mechanism, some (if not most) implementations of this function |
155 | * do not actually bind the socket until the connection |
156 | * is requested (see connect()). They only set the values |
157 | * for future reference. |
158 | * |
159 | * This function returns true on success. |
160 | * |
161 | * @param node the nodename |
162 | * @param service the service |
163 | */ |
164 | virtual bool bind(const QString& node = QString(), |
165 | const QString& service = QString()); |
166 | |
167 | /** |
168 | * Reimplemented from KClientSocketBase. Connect this socket to this |
169 | * specific address. |
170 | * |
171 | * Unlike bind(const QString&, const QString&) above, this function |
172 | * really does bind the socket. No lookup is performed. The bound() |
173 | * signal will be emitted. |
174 | */ |
175 | virtual bool bind(const KResolverEntry& entry); |
176 | |
177 | /** |
178 | * Reimplemented from KClientSocketBase. |
179 | * |
180 | * Attempts to connect to the these hostname and service, |
181 | * or use the default ones if none are given. If a connection attempt |
182 | * is already in progress, check on its state and set the error status |
183 | * (NoError, meaning the connection is completed, or InProgress). |
184 | * |
185 | * If the blocking mode for this object is on, this function will only |
186 | * return when all the resolved peer addresses have been tried or when |
187 | * a connection is established. |
188 | * |
189 | * Upon successfully connecting, the connected() signal |
190 | * will be emitted. If an error is found, the gotError() |
191 | * signal will be emitted. |
192 | * |
193 | * This function also implements timeout handling. |
194 | * |
195 | * @param node the remote node to connect to |
196 | * @param service the service on the remote node to connect to |
197 | * @param mode mode to operate this socket in |
198 | */ |
199 | virtual bool connect(const QString& node = QString(), |
200 | const QString& service = QString(), |
201 | OpenMode mode = ReadWrite); |
202 | |
203 | /** |
204 | * Unshadowing from KClientSocketBase. |
205 | */ |
206 | virtual bool connect(const KResolverEntry& entry, |
207 | OpenMode mode = ReadWrite); |
208 | |
209 | Q_SIGNALS: |
210 | /** |
211 | * This signal is emitted when a connection timeout occurs. |
212 | */ |
213 | void timedOut(); |
214 | |
215 | private Q_SLOTS: |
216 | void hostFoundSlot(); |
217 | void connectionEvent(); |
218 | void timeoutSlot(); |
219 | |
220 | private: |
221 | /** |
222 | * @internal |
223 | * If the user requested local bind before connection, bind the socket to one |
224 | * suitable address and return true. Also sets d->local to the address used. |
225 | * |
226 | * Return false in case of error. |
227 | */ |
228 | bool bindLocallyFor(const KResolverEntry& peer); |
229 | |
230 | /** |
231 | * @internal |
232 | * Finishes the connection process by setting internal values and |
233 | * emitting the proper signals. |
234 | * |
235 | * Note: assumes d->local iterator points to the address that we bound |
236 | * to. |
237 | */ |
238 | void connectionSucceeded(const KResolverEntry& peer); |
239 | |
240 | KStreamSocket(const KStreamSocket&); |
241 | KStreamSocket& operator=(const KStreamSocket&); |
242 | |
243 | KStreamSocketPrivate* const d; |
244 | |
245 | friend class KServerSocket; |
246 | friend class KBufferedSocket; |
247 | }; |
248 | |
249 | } // namespace KNetwork |
250 | |
251 | #endif |
252 | |