1 /******************************************************************************
4 Copyright 1993, 1998 The Open Group
6 Permission to use, copy, modify, distribute, and sell this software and its
7 documentation for any purpose is hereby granted without fee, provided that
8 the above copyright notice appear in all copies and that both that
9 copyright notice and this permission notice appear in supporting
12 The above copyright notice and this permission notice shall be included in
13 all copies or substantial portions of the Software.
15 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
19 AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
20 CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
22 Except as contained in this notice, the name of The Open Group shall not be
23 used in advertising or otherwise to promote the sale, use or other dealings
24 in this Software without prior written authorization from The Open Group.
26 Author: Ralph Mor, X Consortium
27 ******************************************************************************/
35 #include <X11/ICE/ICElib.h>
36 #include "ICElibint.h"
37 #include <X11/Xtrans/Xtrans.h>
40 #include <X11/Xwinsock.h>
41 #include <X11/Xw32defs.h>
55 if (!iceConn->scratch || size > iceConn->scratch_size)
58 free (iceConn->scratch);
60 iceConn->scratch = (char *) malloc ((unsigned) size);
61 iceConn->scratch_size = size;
64 return (iceConn->scratch);
70 * Output/Input buffer functions
79 (unsigned long) (iceConn->outbufptr - iceConn->outbuf),
82 iceConn->outbufptr = iceConn->outbuf;
92 return (iceConn->outbufmax - iceConn->outbuf);
101 return (iceConn->inbufmax - iceConn->inbuf);
107 * informational functions
111 IceConnectionStatus (
115 return (iceConn->connection_status);
124 return strdup(iceConn->vendor);
133 return strdup(iceConn->release);
142 return (_IceVersions[iceConn->my_ice_version_index].major_version);
147 IceProtocolRevision (
151 return (_IceVersions[iceConn->my_ice_version_index].minor_version);
156 IceConnectionNumber (
160 return (_IceTransGetConnectionNumber (iceConn->trans_conn));
165 IceConnectionString (
169 if (iceConn->connection_string)
171 return strdup(iceConn->connection_string);
179 IceLastSentSequenceNumber (
183 return (iceConn->send_sequence);
188 IceLastReceivedSequenceNumber (
192 return (iceConn->receive_sequence);
201 return (iceConn->swap);
207 * Read "n" bytes from a connection.
209 * Return Status 0 if we detected an EXPECTED closed connection.
215 register IceConn iceConn,
216 unsigned long nbytes,
220 register unsigned long nleft;
228 nread = _IceTransRead (iceConn->trans_conn, ptr, (int) nleft);
235 errno = WSAGetLastError();
237 if (iceConn->want_to_close)
240 * We sent a WantToClose message and now we detected that
241 * the other side closed the connection.
244 _IceConnectionClosed (iceConn); /* invoke watch procs */
245 _IceFreeConnection (iceConn);
252 * Fatal IO error. First notify each protocol's IceIOErrorProc
253 * callback, then invoke the application IO error handler.
256 iceConn->io_ok = False;
258 if (iceConn->connection_status == IceConnectPending)
261 * Don't invoke IO error handler if we are in the
262 * middle of a connection setup.
268 if (iceConn->process_msg_info)
272 for (i = iceConn->his_min_opcode;
273 i <= iceConn->his_max_opcode; i++)
275 _IceProcessMsgInfo *process;
277 process = &iceConn->process_msg_info[
278 i - iceConn->his_min_opcode];
280 if ((process != NULL) && process->in_use)
282 IceIOErrorProc IOErrProc = process->accept_flag ?
283 process->protocol->accept_client->io_error_proc :
284 process->protocol->orig_client->io_error_proc;
287 (*IOErrProc) (iceConn);
292 (*_IceIOErrorHandler) (iceConn);
307 * If we read a message header with a bad major or minor opcode,
308 * we need to advance to the end of the message. This way, the next
309 * message can be processed correctly.
314 register IceConn iceConn,
315 register unsigned long nbytes
322 unsigned long rbytes = nbytes > 512 ? 512 : nbytes;
324 _IceRead (iceConn, rbytes, temp);
332 * Write "n" bytes to a connection.
337 register IceConn iceConn,
338 unsigned long nbytes,
342 register unsigned long nleft;
350 nwritten = _IceTransWrite (iceConn->trans_conn, ptr, (int) nleft);
357 errno = WSAGetLastError();
360 * Fatal IO error. First notify each protocol's IceIOErrorProc
361 * callback, then invoke the application IO error handler.
364 iceConn->io_ok = False;
366 if (iceConn->connection_status == IceConnectPending)
369 * Don't invoke IO error handler if we are in the
370 * middle of a connection setup.
376 if (iceConn->process_msg_info)
380 for (i = iceConn->his_min_opcode;
381 i <= iceConn->his_max_opcode; i++)
383 _IceProcessMsgInfo *process;
385 process = &iceConn->process_msg_info[
386 i - iceConn->his_min_opcode];
390 IceIOErrorProc IOErrProc = process->accept_flag ?
391 process->protocol->accept_client->io_error_proc :
392 process->protocol->orig_client->io_error_proc;
395 (*IOErrProc) (iceConn);
400 (*_IceIOErrorHandler) (iceConn);
413 unsigned long nbytes,
417 int numShorts = nbytes / 2;
420 while (index < numShorts)
422 int spaceLeft, count, i;
423 int shortsLeft = numShorts - index;
425 spaceLeft = iceConn->outbufmax - iceConn->outbufptr - 1;
430 spaceLeft = iceConn->outbufmax - iceConn->outbufptr - 1;
433 count = (shortsLeft < spaceLeft / 2) ? shortsLeft : spaceLeft / 2;
435 for (i = 0; i < count; i++)
436 STORE_CARD16 (iceConn->outbufptr, data[index++]);
443 unsigned long nbytes,
447 int numLongs = nbytes / 4;
450 while (index < numLongs)
452 int spaceLeft, count, i;
453 int longsLeft = numLongs - index;
455 spaceLeft = iceConn->outbufmax - iceConn->outbufptr - 1;
460 spaceLeft = iceConn->outbufmax - iceConn->outbufptr - 1;
463 count = (longsLeft < spaceLeft / 4) ? longsLeft : spaceLeft / 4;
465 for (i = 0; i < count; i++)
466 STORE_CARD32 (iceConn->outbufptr, data[index++]);
474 unsigned long nbytes,
478 /* NOT IMPLEMENTED YET */
485 unsigned long nbytes,
489 /* NOT IMPLEMENTED YET */
497 _IceAddOpcodeMapping (
503 if (hisOpcode <= 0 || hisOpcode > 255)
507 else if (iceConn->process_msg_info == NULL)
509 iceConn->process_msg_info = (_IceProcessMsgInfo *) malloc (
510 sizeof (_IceProcessMsgInfo));
511 iceConn->his_min_opcode = iceConn->his_max_opcode = hisOpcode;
513 else if (hisOpcode < iceConn->his_min_opcode)
515 _IceProcessMsgInfo *oldVec = iceConn->process_msg_info;
516 int oldsize = iceConn->his_max_opcode - iceConn->his_min_opcode + 1;
517 int newsize = iceConn->his_max_opcode - hisOpcode + 1;
520 iceConn->process_msg_info = (_IceProcessMsgInfo *) malloc (
521 newsize * sizeof (_IceProcessMsgInfo));
523 memcpy (&iceConn->process_msg_info[
524 iceConn->his_min_opcode - hisOpcode], oldVec,
525 oldsize * sizeof (_IceProcessMsgInfo));
527 free ((char *) oldVec);
529 for (i = hisOpcode + 1; i < iceConn->his_min_opcode; i++)
531 iceConn->process_msg_info[i -
532 iceConn->his_min_opcode].in_use = False;
534 iceConn->process_msg_info[i -
535 iceConn->his_min_opcode].protocol = NULL;
538 iceConn->his_min_opcode = hisOpcode;
540 else if (hisOpcode > iceConn->his_max_opcode)
542 _IceProcessMsgInfo *oldVec = iceConn->process_msg_info;
543 int oldsize = iceConn->his_max_opcode - iceConn->his_min_opcode + 1;
544 int newsize = hisOpcode - iceConn->his_min_opcode + 1;
547 iceConn->process_msg_info = (_IceProcessMsgInfo *) malloc (
548 newsize * sizeof (_IceProcessMsgInfo));
550 memcpy (iceConn->process_msg_info, oldVec,
551 oldsize * sizeof (_IceProcessMsgInfo));
553 free ((char *) oldVec);
555 for (i = iceConn->his_max_opcode + 1; i < hisOpcode; i++)
557 iceConn->process_msg_info[i -
558 iceConn->his_min_opcode].in_use = False;
560 iceConn->process_msg_info[i -
561 iceConn->his_min_opcode].protocol = NULL;
564 iceConn->his_max_opcode = hisOpcode;
567 iceConn->process_msg_info[hisOpcode -
568 iceConn->his_min_opcode].in_use = True;
570 iceConn->process_msg_info[hisOpcode -
571 iceConn->his_min_opcode].my_opcode = myOpcode;
573 iceConn->process_msg_info[hisOpcode -
574 iceConn->his_min_opcode].protocol = &_IceProtocols[myOpcode - 1];
580 IceGetPeerName (IceConn iceConn)
582 return (_IceTransGetPeerNetworkId (iceConn->trans_conn));
587 _IceGetPeerName (IceConn iceConn)
589 return (IceGetPeerName(iceConn));