Where Online Learning is simpler!
The C and C++ Include Header Files
/usr/include/X11/Xtrans/Xtranslcl.c
$ cat -n /usr/include/X11/Xtrans/Xtranslcl.c 1 /* 2 3 Copyright 1993, 1994, 1998 The Open Group 4 5 Permission to use, copy, modify, distribute, and sell this software and its 6 documentation for any purpose is hereby granted without fee, provided that 7 the above copyright notice appear in all copies and that both that 8 copyright notice and this permission notice appear in supporting 9 documentation. 10 11 The above copyright notice and this permission notice shall be included 12 in all copies or substantial portions of the Software. 13 14 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 15 OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 16 MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 17 IN NO EVENT SHALL THE OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR 18 OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 19 ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 20 OTHER DEALINGS IN THE SOFTWARE. 21 22 Except as contained in this notice, the name of The Open Group shall 23 not be used in advertising or otherwise to promote the sale, use or 24 other dealings in this Software without prior written authorization 25 from The Open Group. 26 27 * Copyright 1993, 1994 NCR Corporation - Dayton, Ohio, USA 28 * 29 * All Rights Reserved 30 * 31 * Permission to use, copy, modify, and distribute this software and its 32 * documentation for any purpose and without fee is hereby granted, provided 33 * that the above copyright notice appear in all copies and that both that 34 * copyright notice and this permission notice appear in supporting 35 * documentation, and that the name NCR not be used in advertising 36 * or publicity pertaining to distribution of the software without specific, 37 * written prior permission. NCR makes no representations about the 38 * suitability of this software for any purpose. It is provided "as is" 39 * without express or implied warranty. 40 * 41 * NCR DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, 42 * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN 43 * NO EVENT SHALL NCR BE LIABLE FOR ANY SPECIAL, INDIRECT OR 44 * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS 45 * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, 46 * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN 47 * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 48 */ 49 50 /* 51 * 52 * The connection code/ideas in lib/X and server/os for SVR4/Intel 53 * environments was contributed by the following companies/groups: 54 * 55 * MetroLink Inc 56 * NCR 57 * Pittsburgh Powercomputing Corporation (PPc)/Quarterdeck Office Systems 58 * SGCS 59 * Unix System Laboratories (USL) / Novell 60 * XFree86 61 * 62 * The goal is to have common connection code among all SVR4/Intel vendors. 63 * 64 * ALL THE ABOVE COMPANIES DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS 65 * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, 66 * IN NO EVENT SHALL THESE COMPANIES * BE LIABLE FOR ANY SPECIAL, INDIRECT 67 * OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS 68 * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE 69 * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE 70 * OR PERFORMANCE OF THIS SOFTWARE. 71 */ 72 73 #include
74 #include
75 #include
76 #include
77 #include
78 #if defined(SVR4) || defined(__SVR4) 79 #include
80 #endif 81 #ifdef __sun 82 # include
83 #else 84 # include
85 #endif 86 #include
87 #include
88 89 /* 90 * The local transports should be treated the same as a UNIX domain socket 91 * wrt authentication, etc. Because of this, we will use struct sockaddr_un 92 * for the address format. This will simplify the code in other places like 93 * The X Server. 94 */ 95 96 #include
97 #ifndef X_NO_SYS_UN 98 #include
99 #endif 100 101 102 /* Types of local connections supported: 103 * - PTS 104 * - named pipes 105 * - SCO 106 */ 107 #if !defined(__sun) 108 # define LOCAL_TRANS_PTS 109 #endif 110 #if defined(SVR4) || defined(__SVR4) 111 # define LOCAL_TRANS_NAMED 112 #endif 113 #if defined(__SCO__) || defined(__UNIXWARE__) 114 # define LOCAL_TRANS_SCO 115 #endif 116 117 static int TRANS(LocalClose)(XtransConnInfo ciptr); 118 119 /* 120 * These functions actually implement the local connection mechanisms. 121 */ 122 123 /* Type Not Supported */ 124 125 static int 126 TRANS(OpenFail)(XtransConnInfo ciptr _X_UNUSED, const char *port _X_UNUSED) 127 128 { 129 return -1; 130 } 131 132 #ifdef TRANS_REOPEN 133 134 static int 135 TRANS(ReopenFail)(XtransConnInfo ciptr _X_UNUSED, int fd _X_UNUSED, 136 const char *port _X_UNUSED) 137 138 { 139 return 0; 140 } 141 142 #endif /* TRANS_REOPEN */ 143 144 #if XTRANS_SEND_FDS 145 static int 146 TRANS(LocalRecvFdInvalid)(XtransConnInfo ciptr) 147 { 148 errno = EINVAL; 149 return -1; 150 } 151 152 static int 153 TRANS(LocalSendFdInvalid)(XtransConnInfo ciptr, int fd, int do_close) 154 { 155 errno = EINVAL; 156 return -1; 157 } 158 #endif 159 160 161 static int 162 TRANS(FillAddrInfo)(XtransConnInfo ciptr, 163 const char *sun_path, const char *peer_sun_path) 164 165 { 166 struct sockaddr_un *sunaddr; 167 struct sockaddr_un *p_sunaddr; 168 169 ciptr->family = AF_UNIX; 170 ciptr->addrlen = sizeof (struct sockaddr_un); 171 172 if ((sunaddr = malloc (ciptr->addrlen)) == NULL) 173 { 174 prmsg(1,"FillAddrInfo: failed to allocate memory for addr\n"); 175 return 0; 176 } 177 178 sunaddr->sun_family = AF_UNIX; 179 180 if (strlen(sun_path) > sizeof(sunaddr->sun_path) - 1) { 181 prmsg(1, "FillAddrInfo: path too long\n"); 182 free((char *) sunaddr); 183 return 0; 184 } 185 strcpy (sunaddr->sun_path, sun_path); 186 #if defined(BSD44SOCKETS) 187 sunaddr->sun_len = strlen (sunaddr->sun_path); 188 #endif 189 190 ciptr->addr = (char *) sunaddr; 191 192 ciptr->peeraddrlen = sizeof (struct sockaddr_un); 193 194 if ((p_sunaddr = malloc (ciptr->peeraddrlen)) == NULL) 195 { 196 prmsg(1, 197 "FillAddrInfo: failed to allocate memory for peer addr\n"); 198 free (sunaddr); 199 ciptr->addr = NULL; 200 201 return 0; 202 } 203 204 p_sunaddr->sun_family = AF_UNIX; 205 206 if (strlen(peer_sun_path) > sizeof(p_sunaddr->sun_path) - 1) { 207 prmsg(1, "FillAddrInfo: peer path too long\n"); 208 free((char *) p_sunaddr); 209 return 0; 210 } 211 strcpy (p_sunaddr->sun_path, peer_sun_path); 212 #if defined(BSD44SOCKETS) 213 p_sunaddr->sun_len = strlen (p_sunaddr->sun_path); 214 #endif 215 216 ciptr->peeraddr = (char *) p_sunaddr; 217 218 return 1; 219 } 220 221 222 223 #ifdef LOCAL_TRANS_PTS 224 /* PTS */ 225 226 #if defined(SYSV) && !defined(__SCO__) 227 #define SIGNAL_T int 228 #else 229 #define SIGNAL_T void 230 #endif /* SYSV */ 231 232 typedef SIGNAL_T (*PFV)(); 233 234 extern PFV signal(); 235 236 extern char *ptsname( 237 int 238 ); 239 240 static void _dummy(int sig _X_UNUSED) 241 242 { 243 } 244 #endif /* LOCAL_TRANS_PTS */ 245 246 #ifndef __sun 247 #define X_STREAMS_DIR "/dev/X" 248 #define DEV_SPX "/dev/spx" 249 #else 250 #ifndef X11_t 251 #define X_STREAMS_DIR "/dev/X" 252 #else 253 #define X_STREAMS_DIR "/tmp/.X11-pipe" 254 #endif 255 #endif 256 257 #define DEV_PTMX "/dev/ptmx" 258 259 #if defined(X11_t) 260 261 #define PTSNODENAME "/dev/X/server." 262 #ifdef __sun 263 #define NAMEDNODENAME "/tmp/.X11-pipe/X" 264 #else 265 #define NAMEDNODENAME "/dev/X/Nserver." 266 267 #define SCORNODENAME "/dev/X%1sR" 268 #define SCOSNODENAME "/dev/X%1sS" 269 #endif /* !__sun */ 270 #endif 271 #if defined(XIM_t) 272 #ifdef __sun 273 #define NAMEDNODENAME "/tmp/.XIM-pipe/XIM" 274 #else 275 #define PTSNODENAME "/dev/X/XIM." 276 #define NAMEDNODENAME "/dev/X/NXIM." 277 #define SCORNODENAME "/dev/XIM.%sR" 278 #define SCOSNODENAME "/dev/XIM.%sS" 279 #endif 280 #endif 281 #if defined(FS_t) || defined (FONT_t) 282 #ifdef __sun 283 #define NAMEDNODENAME "/tmp/.font-pipe/fs" 284 #else 285 /* 286 * USL has already defined something here. We need to check with them 287 * and see if their choice is usable here. 288 */ 289 #define PTSNODENAME "/dev/X/fontserver." 290 #define NAMEDNODENAME "/dev/X/Nfontserver." 291 #define SCORNODENAME "/dev/fontserver.%sR" 292 #define SCOSNODENAME "/dev/fontserver.%sS" 293 #endif 294 #endif 295 #if defined(ICE_t) 296 #ifdef __sun 297 #define NAMEDNODENAME "/tmp/.ICE-pipe/" 298 #else 299 #define PTSNODENAME "/dev/X/ICE." 300 #define NAMEDNODENAME "/dev/X/NICE." 301 #define SCORNODENAME "/dev/ICE.%sR" 302 #define SCOSNODENAME "/dev/ICE.%sS" 303 #endif 304 #endif 305 #if defined(TEST_t) 306 #ifdef __sun 307 #define NAMEDNODENAME "/tmp/.Test-unix/test" 308 #endif 309 #define PTSNODENAME "/dev/X/transtest." 310 #define NAMEDNODENAME "/dev/X/Ntranstest." 311 #define SCORNODENAME "/dev/transtest.%sR" 312 #define SCOSNODENAME "/dev/transtest.%sS" 313 #endif 314 315 316 317 #ifdef LOCAL_TRANS_PTS 318 #ifdef TRANS_CLIENT 319 320 static int 321 TRANS(PTSOpenClient)(XtransConnInfo ciptr, const char *port) 322 323 { 324 #ifdef PTSNODENAME 325 int fd,server,exitval,alarm_time,ret; 326 char server_path[64]; 327 char *slave, namelen; 328 char buf[20]; /* MAX_PATH_LEN?? */ 329 PFV savef; 330 pid_t saved_pid; 331 #endif 332 333 prmsg(2,"PTSOpenClient(%s)\n", port); 334 335 #if !defined(PTSNODENAME) 336 prmsg(1,"PTSOpenClient: Protocol is not supported by a pts connection\n"); 337 return -1; 338 #else 339 if (port && *port ) { 340 if( *port == '/' ) { /* A full pathname */ 341 snprintf(server_path, sizeof(server_path), "%s", port); 342 } else { 343 snprintf(server_path, sizeof(server_path), "%s%s", 344 PTSNODENAME, port); 345 } 346 } else { 347 snprintf(server_path, sizeof(server_path), "%s%d", 348 PTSNODENAME, getpid()); 349 } 350 351 352 /* 353 * Open the node the on which the server is listening. 354 */ 355 356 if ((server = open (server_path, O_RDWR)) < 0) { 357 prmsg(1,"PTSOpenClient: failed to open %s\n", server_path); 358 return -1; 359 } 360 361 362 /* 363 * Open the streams based pipe that will be this connection. 364 */ 365 366 if ((fd = open(DEV_PTMX, O_RDWR)) < 0) { 367 prmsg(1,"PTSOpenClient: failed to open %s\n", DEV_PTMX); 368 close(server); 369 return(-1); 370 } 371 372 (void) grantpt(fd); 373 (void) unlockpt(fd); 374 375 slave = ptsname(fd); /* get name */ 376 377 if( slave == NULL ) { 378 prmsg(1,"PTSOpenClient: failed to get ptsname()\n"); 379 close(fd); 380 close(server); 381 return -1; 382 } 383 384 /* 385 * This is neccesary for the case where a program is setuid to non-root. 386 * grantpt() calls /usr/lib/pt_chmod which is set-uid root. This program will 387 * set the owner of the pt device incorrectly if the uid is not restored 388 * before it is called. The problem is that once it gets restored, it 389 * cannot be changed back to its original condition, hence the fork(). 390 */ 391 392 if(!(saved_pid=fork())) { 393 uid_t saved_euid; 394 395 saved_euid = geteuid(); 396 /** sets the euid to the actual/real uid **/ 397 if (setuid( getuid() ) == -1) { 398 exit(1); 399 } 400 if( chown( slave, saved_euid, -1 ) < 0 ) { 401 exit( 1 ); 402 } 403 404 exit( 0 ); 405 } 406 407 waitpid(saved_pid, &exitval, 0); 408 if (WIFEXITED(exitval) && WEXITSTATUS(exitval) != 0) { 409 close(fd); 410 close(server); 411 prmsg(1, "PTSOpenClient: cannot set the owner of %s\n", 412 slave); 413 return(-1); 414 } 415 if (chmod(slave, 0666) < 0) { 416 close(fd); 417 close(server); 418 prmsg(1,"PTSOpenClient: Cannot chmod %s\n", slave); 419 return(-1); 420 } 421 422 /* 423 * write slave name to server 424 */ 425 426 namelen = strlen(slave); 427 buf[0] = namelen; 428 (void) sprintf(&buf[1], slave); 429 (void) write(server, buf, namelen+1); 430 (void) close(server); 431 432 /* 433 * wait for server to respond 434 */ 435 436 savef = signal(SIGALRM, _dummy); 437 alarm_time = alarm (30); /* CONNECT_TIMEOUT */ 438 439 ret = read(fd, buf, 1); 440 441 (void) alarm(alarm_time); 442 (void) signal(SIGALRM, savef); 443 444 if (ret != 1) { 445 prmsg(1, 446 "PTSOpenClient: failed to get acknoledgement from server\n"); 447 (void) close(fd); 448 fd = -1; 449 } 450 451 /* 452 * Everything looks good: fill in the XtransConnInfo structure. 453 */ 454 455 if (TRANS(FillAddrInfo) (ciptr, slave, server_path) == 0) 456 { 457 prmsg(1,"PTSOpenClient: failed to fill in addr info\n"); 458 close(fd); 459 return -1; 460 } 461 462 return(fd); 463 464 #endif /* !PTSNODENAME */ 465 } 466 467 #endif /* TRANS_CLIENT */ 468 469 470 #ifdef TRANS_SERVER 471 472 static int 473 TRANS(PTSOpenServer)(XtransConnInfo ciptr, const char *port) 474 475 { 476 #ifdef PTSNODENAME 477 int fd, server; 478 char server_path[64], *slave; 479 int mode; 480 #endif 481 482 prmsg(2,"PTSOpenServer(%s)\n", port); 483 484 #if !defined(PTSNODENAME) 485 prmsg(1,"PTSOpenServer: Protocol is not supported by a pts connection\n"); 486 return -1; 487 #else 488 if (port && *port ) { 489 if( *port == '/' ) { /* A full pathname */ 490 (void) sprintf(server_path, "%s", port); 491 } else { 492 (void) sprintf(server_path, "%s%s", PTSNODENAME, port); 493 } 494 } else { 495 (void) sprintf(server_path, "%s%d", PTSNODENAME, getpid()); 496 } 497 498 #ifdef HAS_STICKY_DIR_BIT 499 mode = 01777; 500 #else 501 mode = 0777; 502 #endif 503 if (trans_mkdir(X_STREAMS_DIR, mode) == -1) { 504 prmsg (1, "PTSOpenServer: mkdir(%s) failed, errno = %d\n", 505 X_STREAMS_DIR, errno); 506 return(-1); 507 } 508 509 #if 0 510 if( (fd=open(server_path, O_RDWR)) >= 0 ) { 511 /* 512 * This doesn't prevent the server from starting up, and doesn't 513 * prevent clients from trying to connect to the in-use PTS (which 514 * is often in use by something other than another server). 515 */ 516 prmsg(1, "PTSOpenServer: A server is already running on port %s\n", port); 517 prmsg(1, "PTSOpenServer: Remove %s if this is incorrect.\n", server_path); 518 close(fd); 519 return(-1); 520 } 521 #else 522 /* Just remove the old path (which is what happens with UNIXCONN) */ 523 #endif 524 525 unlink(server_path); 526 527 if( (fd=open(DEV_PTMX, O_RDWR)) < 0) { 528 prmsg(1, "PTSOpenServer: Unable to open %s\n", DEV_PTMX); 529 return(-1); 530 } 531 532 grantpt(fd); 533 unlockpt(fd); 534 535 if( (slave=ptsname(fd)) == NULL) { 536 prmsg(1, "PTSOpenServer: Unable to get slave device name\n"); 537 close(fd); 538 return(-1); 539 } 540 541 if( link(slave,server_path) < 0 ) { 542 prmsg(1, "PTSOpenServer: Unable to link %s to %s\n", slave, server_path); 543 close(fd); 544 return(-1); 545 } 546 547 if( chmod(server_path, 0666) < 0 ) { 548 prmsg(1, "PTSOpenServer: Unable to chmod %s to 0666\n", server_path); 549 close(fd); 550 return(-1); 551 } 552 553 if( (server=open(server_path, O_RDWR)) < 0 ) { 554 prmsg(1, "PTSOpenServer: Unable to open server device %s\n", server_path); 555 close(fd); 556 return(-1); 557 } 558 559 close(server); 560 561 /* 562 * Everything looks good: fill in the XtransConnInfo structure. 563 */ 564 565 if (TRANS(FillAddrInfo) (ciptr, server_path, server_path) == 0) 566 { 567 prmsg(1,"PTSOpenServer: failed to fill in addr info\n"); 568 close(fd); 569 return -1; 570 } 571 572 return fd; 573 574 #endif /* !PTSNODENAME */ 575 } 576 577 static int 578 TRANS(PTSAccept)(XtransConnInfo ciptr, XtransConnInfo newciptr, int *status) 579 580 { 581 int newfd; 582 int in; 583 unsigned char length; 584 char buf[256]; 585 struct sockaddr_un *sunaddr; 586 587 prmsg(2,"PTSAccept(%x->%d)\n",ciptr,ciptr->fd); 588 589 if( (in=read(ciptr->fd,&length,1)) <= 0 ){ 590 if( !in ) { 591 prmsg(2, 592 "PTSAccept: Incoming connection closed\n"); 593 } 594 else { 595 prmsg(1, 596 "PTSAccept: Error reading incoming connection. errno=%d \n", 597 errno); 598 } 599 *status = TRANS_ACCEPT_MISC_ERROR; 600 return -1; 601 } 602 603 if( (in=read(ciptr->fd,buf,length)) <= 0 ){ 604 if( !in ) { 605 prmsg(2, 606 "PTSAccept: Incoming connection closed\n"); 607 } 608 else { 609 prmsg(1, 610 "PTSAccept: Error reading device name for new connection. errno=%d \n", 611 errno); 612 } 613 *status = TRANS_ACCEPT_MISC_ERROR; 614 return -1; 615 } 616 617 buf[length] = '\0'; 618 619 if( (newfd=open(buf,O_RDWR)) < 0 ) { 620 prmsg(1, "PTSAccept: Failed to open %s\n",buf); 621 *status = TRANS_ACCEPT_MISC_ERROR; 622 return -1; 623 } 624 625 write(newfd,"1",1); 626 627 /* 628 * Everything looks good: fill in the XtransConnInfo structure. 629 */ 630 631 newciptr->addrlen=ciptr->addrlen; 632 if( (newciptr->addr = malloc(newciptr->addrlen)) == NULL ) { 633 prmsg(1,"PTSAccept: failed to allocate memory for peer addr\n"); 634 close(newfd); 635 *status = TRANS_ACCEPT_BAD_MALLOC; 636 return -1; 637 } 638 639 memcpy(newciptr->addr,ciptr->addr,newciptr->addrlen); 640 641 newciptr->peeraddrlen=sizeof(struct sockaddr_un); 642 if( (sunaddr = malloc(newciptr->peeraddrlen)) == NULL ) { 643 prmsg(1,"PTSAccept: failed to allocate memory for peer addr\n"); 644 free(newciptr->addr); 645 close(newfd); 646 *status = TRANS_ACCEPT_BAD_MALLOC; 647 return -1; 648 } 649 650 sunaddr->sun_family=AF_UNIX; 651 strcpy(sunaddr->sun_path,buf); 652 #if defined(BSD44SOCKETS) 653 sunaddr->sun_len=strlen(sunaddr->sun_path); 654 #endif 655 656 newciptr->peeraddr=(char *)sunaddr; 657 658 *status = 0; 659 660 return newfd; 661 } 662 663 #endif /* TRANS_SERVER */ 664 #endif /* LOCAL_TRANS_PTS */ 665 666 667 #ifdef LOCAL_TRANS_NAMED 668 669 /* NAMED */ 670 671 #ifdef TRANS_CLIENT 672 673 static int 674 TRANS(NAMEDOpenClient)(XtransConnInfo ciptr, const char *port) 675 676 { 677 #ifdef NAMEDNODENAME 678 int fd; 679 char server_path[64]; 680 struct stat filestat; 681 # ifndef __sun 682 extern int isastream(int); 683 # endif 684 #endif 685 686 prmsg(2,"NAMEDOpenClient(%s)\n", port); 687 688 #if !defined(NAMEDNODENAME) 689 prmsg(1,"NAMEDOpenClient: Protocol is not supported by a NAMED connection\n"); 690 return -1; 691 #else 692 if ( port && *port ) { 693 if( *port == '/' ) { /* A full pathname */ 694 (void) snprintf(server_path, sizeof(server_path), "%s", port); 695 } else { 696 (void) snprintf(server_path, sizeof(server_path), "%s%s", NAMEDNODENAME, port); 697 } 698 } else { 699 (void) snprintf(server_path, sizeof(server_path), "%s%ld", NAMEDNODENAME, (long)getpid()); 700 } 701 702 if ((fd = open(server_path, O_RDWR)) < 0) { 703 prmsg(1,"NAMEDOpenClient: Cannot open %s for NAMED connection\n", server_path); 704 return -1; 705 } 706 707 if (fstat(fd, &filestat) < 0 ) { 708 prmsg(1,"NAMEDOpenClient: Cannot stat %s for NAMED connection\n", server_path); 709 (void) close(fd); 710 return -1; 711 } 712 713 if ((filestat.st_mode & S_IFMT) != S_IFIFO) { 714 prmsg(1,"NAMEDOpenClient: Device %s is not a FIFO\n", server_path); 715 /* Is this really a failure? */ 716 (void) close(fd); 717 return -1; 718 } 719 720 721 if (isastream(fd) <= 0) { 722 prmsg(1,"NAMEDOpenClient: %s is not a streams device\n", server_path); 723 (void) close(fd); 724 return -1; 725 } 726 727 /* 728 * Everything looks good: fill in the XtransConnInfo structure. 729 */ 730 731 if (TRANS(FillAddrInfo) (ciptr, server_path, server_path) == 0) 732 { 733 prmsg(1,"NAMEDOpenClient: failed to fill in addr info\n"); 734 close(fd); 735 return -1; 736 } 737 738 return(fd); 739 740 #endif /* !NAMEDNODENAME */ 741 } 742 743 #endif /* TRANS_CLIENT */ 744 745 746 #ifdef TRANS_SERVER 747 748 749 #ifdef NAMEDNODENAME 750 static int 751 TRANS(NAMEDOpenPipe)(const char *server_path) 752 { 753 int fd, pipefd[2]; 754 struct stat sbuf; 755 int mode; 756 757 prmsg(2,"NAMEDOpenPipe(%s)\n", server_path); 758 759 #ifdef HAS_STICKY_DIR_BIT 760 mode = 01777; 761 #else 762 mode = 0777; 763 #endif 764 if (trans_mkdir(X_STREAMS_DIR, mode) == -1) { 765 prmsg (1, "NAMEDOpenPipe: mkdir(%s) failed, errno = %d\n", 766 X_STREAMS_DIR, errno); 767 return(-1); 768 } 769 770 if(stat(server_path, &sbuf) != 0) { 771 if (errno == ENOENT) { 772 if ((fd = creat(server_path, (mode_t)0666)) == -1) { 773 prmsg(1, "NAMEDOpenPipe: Can't open %s\n", server_path); 774 return(-1); 775 } 776 if (fchmod(fd, (mode_t)0666) < 0) { 777 prmsg(1, "NAMEDOpenPipe: Can't chmod %s\n", server_path); 778 close(fd); 779 return(-1); 780 } 781 close(fd); 782 } else { 783 prmsg(1, "NAMEDOpenPipe: stat on %s failed\n", server_path); 784 return(-1); 785 } 786 } 787 788 if( pipe(pipefd) != 0) { 789 prmsg(1, "NAMEDOpenPipe: pipe() failed, errno=%d\n",errno); 790 return(-1); 791 } 792 793 if( ioctl(pipefd[0], I_PUSH, "connld") != 0) { 794 prmsg(1, "NAMEDOpenPipe: ioctl(I_PUSH,\"connld\") failed, errno=%d\n",errno); 795 close(pipefd[0]); 796 close(pipefd[1]); 797 return(-1); 798 } 799 800 if( fattach(pipefd[0], server_path) != 0) { 801 prmsg(1, "NAMEDOpenPipe: fattach(%s) failed, errno=%d\n", server_path,errno); 802 close(pipefd[0]); 803 close(pipefd[1]); 804 return(-1); 805 } 806 807 return(pipefd[1]); 808 } 809 #endif 810 811 static int 812 TRANS(NAMEDOpenServer)(XtransConnInfo ciptr, const char *port) 813 { 814 #ifdef NAMEDNODENAME 815 int fd; 816 char server_path[64]; 817 #endif 818 819 prmsg(2,"NAMEDOpenServer(%s)\n", port); 820 821 #if !defined(NAMEDNODENAME) 822 prmsg(1,"NAMEDOpenServer: Protocol is not supported by a NAMED connection\n"); 823 return -1; 824 #else 825 if ( port && *port ) { 826 if( *port == '/' ) { /* A full pathname */ 827 (void) snprintf(server_path, sizeof(server_path), "%s", port); 828 } else { 829 (void) snprintf(server_path, sizeof(server_path), "%s%s", 830 NAMEDNODENAME, port); 831 } 832 } else { 833 (void) snprintf(server_path, sizeof(server_path), "%s%ld", 834 NAMEDNODENAME, (long)getpid()); 835 } 836 837 fd = TRANS(NAMEDOpenPipe)(server_path); 838 if (fd < 0) { 839 return -1; 840 } 841 842 /* 843 * Everything looks good: fill in the XtransConnInfo structure. 844 */ 845 846 if (TRANS(FillAddrInfo) (ciptr, server_path, server_path) == 0) 847 { 848 prmsg(1,"NAMEDOpenServer: failed to fill in addr info\n"); 849 TRANS(LocalClose)(ciptr); 850 return -1; 851 } 852 853 return fd; 854 855 #endif /* !NAMEDNODENAME */ 856 } 857 858 static int 859 TRANS(NAMEDResetListener) (XtransConnInfo ciptr) 860 861 { 862 struct sockaddr_un *sockname=(struct sockaddr_un *) ciptr->addr; 863 struct stat statb; 864 865 prmsg(2,"NAMEDResetListener(%p, %d)\n", ciptr, ciptr->fd); 866 867 if (ciptr->fd != -1) { 868 /* 869 * see if the pipe has disappeared 870 */ 871 872 if (stat (sockname->sun_path, &statb) == -1 || 873 (statb.st_mode & S_IFMT) != S_IFIFO) { 874 prmsg(3, "Pipe %s trashed, recreating\n", sockname->sun_path); 875 TRANS(LocalClose)(ciptr); 876 ciptr->fd = TRANS(NAMEDOpenPipe)(sockname->sun_path); 877 if (ciptr->fd >= 0) 878 return TRANS_RESET_NEW_FD; 879 else 880 return TRANS_CREATE_LISTENER_FAILED; 881 } 882 } 883 return TRANS_RESET_NOOP; 884 } 885 886 static int 887 TRANS(NAMEDAccept)(XtransConnInfo ciptr, XtransConnInfo newciptr, int *status) 888 889 { 890 struct strrecvfd str; 891 892 prmsg(2,"NAMEDAccept(%p->%d)\n", ciptr, ciptr->fd); 893 894 if( ioctl(ciptr->fd, I_RECVFD, &str ) < 0 ) { 895 prmsg(1, "NAMEDAccept: ioctl(I_RECVFD) failed, errno=%d\n", errno); 896 *status = TRANS_ACCEPT_MISC_ERROR; 897 return(-1); 898 } 899 900 /* 901 * Everything looks good: fill in the XtransConnInfo structure. 902 */ 903 newciptr->family=ciptr->family; 904 newciptr->addrlen=ciptr->addrlen; 905 if( (newciptr->addr = malloc(newciptr->addrlen)) == NULL ) { 906 prmsg(1, 907 "NAMEDAccept: failed to allocate memory for pipe addr\n"); 908 close(str.fd); 909 *status = TRANS_ACCEPT_BAD_MALLOC; 910 return -1; 911 } 912 913 memcpy(newciptr->addr,ciptr->addr,newciptr->addrlen); 914 915 newciptr->peeraddrlen=newciptr->addrlen; 916 if( (newciptr->peeraddr = malloc(newciptr->peeraddrlen)) == NULL ) { 917 prmsg(1, 918 "NAMEDAccept: failed to allocate memory for peer addr\n"); 919 free(newciptr->addr); 920 close(str.fd); 921 *status = TRANS_ACCEPT_BAD_MALLOC; 922 return -1; 923 } 924 925 memcpy(newciptr->peeraddr,newciptr->addr,newciptr->peeraddrlen); 926 927 *status = 0; 928 929 return str.fd; 930 } 931 932 #endif /* TRANS_SERVER */ 933 934 #endif /* LOCAL_TRANS_NAMED */ 935 936 937 938 #if defined(LOCAL_TRANS_SCO) 939 940 /* 941 * connect_spipe is used by the SCO connection type. 942 */ 943 static int 944 connect_spipe(int fd1, int fd2) 945 { 946 long temp; 947 struct strfdinsert sbuf; 948 949 sbuf.databuf.maxlen = -1; 950 sbuf.databuf.len = -1; 951 sbuf.databuf.buf = NULL; 952 sbuf.ctlbuf.maxlen = sizeof(long); 953 sbuf.ctlbuf.len = sizeof(long); 954 sbuf.ctlbuf.buf = (caddr_t)&temp; 955 sbuf.offset = 0; 956 sbuf.fildes = fd2; 957 sbuf.flags = 0; 958 959 if( ioctl(fd1, I_FDINSERT, &sbuf) < 0 ) 960 return(-1); 961 962 return(0); 963 } 964 965 /* 966 * named_spipe is used by the SCO connection type. 967 */ 968 969 static int 970 named_spipe(int fd, char *path) 971 972 { 973 int oldUmask, ret; 974 struct stat sbuf; 975 976 oldUmask = umask(0); 977 978 (void) fstat(fd, &sbuf); 979 ret = mknod(path, 0020666, sbuf.st_rdev); 980 981 umask(oldUmask); 982 983 if (ret < 0) { 984 ret = -1; 985 } else { 986 ret = fd; 987 } 988 989 return(ret); 990 } 991 992 #endif /* defined(LOCAL_TRANS_SCO) */ 993 994 995 996 997 #ifdef LOCAL_TRANS_SCO 998 /* SCO */ 999 1000 /* 1001 * 2002-11-09 (jkj@sco.com) 1002 * 1003 * This code has been modified to match what is in the actual SCO X server. 1004 * This greatly helps inter-operability between X11R6 and X11R5 (the native 1005 * SCO server). Mainly, it relies on streams nodes existing in /dev, not 1006 * creating them or unlinking them, which breaks the native X server. 1007 * 1008 * However, this is only for the X protocol. For all other protocols, we 1009 * do in fact create the nodes, as only X11R6 will use them, and this makes 1010 * it possible to have both types of clients running, otherwise we get all 1011 * kinds of nasty errors on startup for anything that doesnt use the X 1012 * protocol (like SM, when KDE starts up). 1013 */ 1014 1015 #ifdef TRANS_CLIENT 1016 1017 static int 1018 TRANS(SCOOpenClient)(XtransConnInfo ciptr, const char *port) 1019 { 1020 #ifdef SCORNODENAME 1021 int fd, server, fl, ret; 1022 char server_path[64]; 1023 struct strbuf ctlbuf; 1024 unsigned long alarm_time; 1025 void (*savef)(); 1026 long temp; 1027 extern int getmsg(), putmsg(); 1028 #endif 1029 1030 prmsg(2,"SCOOpenClient(%s)\n", port); 1031 if (!port || !port[0]) 1032 port = "0"; 1033 1034 #if !defined(SCORNODENAME) 1035 prmsg(2,"SCOOpenClient: Protocol is not supported by a SCO connection\n"); 1036 return -1; 1037 #else 1038 (void) sprintf(server_path, SCORNODENAME, port); 1039 1040 if ((server = open(server_path, O_RDWR)) < 0) { 1041 prmsg(1,"SCOOpenClient: failed to open %s\n", server_path); 1042 return -1; 1043 } 1044 1045 if ((fd = open(DEV_SPX, O_RDWR)) < 0) { 1046 prmsg(1,"SCOOpenClient: failed to open %s\n", DEV_SPX); 1047 close(server); 1048 return -1; 1049 } 1050 1051 (void) write(server, &server, 1); 1052 ctlbuf.len = 0; 1053 ctlbuf.maxlen = sizeof(long); 1054 ctlbuf.buf = (caddr_t)&temp; 1055 fl = 0; 1056 1057 savef = signal(SIGALRM, _dummy); 1058 alarm_time = alarm(10); 1059 1060 ret = getmsg(server, &ctlbuf, 0, &fl); 1061 1062 (void) alarm(alarm_time); 1063 (void) signal(SIGALRM, savef); 1064 1065 if (ret < 0) { 1066 prmsg(1,"SCOOpenClient: error from getmsg\n"); 1067 close(fd); 1068 close(server); 1069 return -1; 1070 } 1071 1072 /* The msg we got via getmsg is the result of an 1073 * I_FDINSERT, so if we do a putmsg with whatever 1074 * we recieved, we're doing another I_FDINSERT ... 1075 */ 1076 (void) putmsg(fd, &ctlbuf, 0, 0); 1077 (void) fcntl(fd,F_SETFL,fcntl(fd,F_GETFL,0)|O_NDELAY); 1078 1079 (void) close(server); 1080 1081 /* 1082 * Everything looks good: fill in the XtransConnInfo structure. 1083 */ 1084 1085 #if defined(X11_t) && defined(__SCO__) 1086 ciptr->flags |= TRANS_NOUNLINK; 1087 #endif 1088 if (TRANS(FillAddrInfo) (ciptr, server_path, server_path) == 0) 1089 { 1090 prmsg(1,"SCOOpenClient: failed to fill addr info\n"); 1091 close(fd); 1092 return -1; 1093 } 1094 1095 return(fd); 1096 1097 #endif /* !SCORNODENAME */ 1098 } 1099 1100 #endif /* TRANS_CLIENT */ 1101 1102 1103 #ifdef TRANS_SERVER 1104 1105 static int 1106 TRANS(SCOOpenServer)(XtransConnInfo ciptr, const char *port) 1107 { 1108 #ifdef SCORNODENAME 1109 char serverR_path[64]; 1110 char serverS_path[64]; 1111 struct flock mylock; 1112 int fdr = -1; 1113 int fds = -1; 1114 #endif 1115 1116 prmsg(2,"SCOOpenServer(%s)\n", port); 1117 if (!port || !port[0]) 1118 port = "0"; 1119 1120 #if !defined(SCORNODENAME) 1121 prmsg(1,"SCOOpenServer: Protocol is not supported by a SCO connection\n"); 1122 return -1; 1123 #else 1124 (void) sprintf(serverR_path, SCORNODENAME, port); 1125 (void) sprintf(serverS_path, SCOSNODENAME, port); 1126 1127 #if !defined(X11_t) || !defined(__SCO__) 1128 unlink(serverR_path); 1129 unlink(serverS_path); 1130 1131 if ((fds = open(DEV_SPX, O_RDWR)) < 0 || 1132 (fdr = open(DEV_SPX, O_RDWR)) < 0 ) { 1133 prmsg(1,"SCOOpenServer: failed to open %s\n", DEV_SPX); 1134 if (fds >= 0) 1135 close(fds); 1136 if (fdr >= 0) 1137 close(fdr); 1138 return -1; 1139 } 1140 1141 if (named_spipe (fds, serverS_path) == -1) { 1142 prmsg(1,"SCOOpenServer: failed to create %s\n", serverS_path); 1143 close (fdr); 1144 close (fds); 1145 return -1; 1146 } 1147 1148 if (named_spipe (fdr, serverR_path) == -1) { 1149 prmsg(1,"SCOOpenServer: failed to create %s\n", serverR_path); 1150 close (fdr); 1151 close (fds); 1152 return -1; 1153 } 1154 #else /* X11_t */ 1155 1156 fds = open (serverS_path, O_RDWR | O_NDELAY); 1157 if (fds < 0) { 1158 prmsg(1,"SCOOpenServer: failed to open %s\n", serverS_path); 1159 return -1; 1160 } 1161 1162 /* 1163 * Lock the connection device for the duration of the server. 1164 * This resolves multiple server starts especially on SMP machines. 1165 */ 1166 mylock.l_type = F_WRLCK; 1167 mylock.l_whence = 0; 1168 mylock.l_start = 0; 1169 mylock.l_len = 0; 1170 if (fcntl (fds, F_SETLK, &mylock) < 0) { 1171 prmsg(1,"SCOOpenServer: failed to lock %s\n", serverS_path); 1172 close (fds); 1173 return -1; 1174 } 1175 1176 fdr = open (serverR_path, O_RDWR | O_NDELAY); 1177 if (fdr < 0) { 1178 prmsg(1,"SCOOpenServer: failed to open %s\n", serverR_path); 1179 close (fds); 1180 return -1; 1181 } 1182 #endif /* X11_t */ 1183 1184 if (connect_spipe(fds, fdr)) { 1185 prmsg(1,"SCOOpenServer: ioctl(I_FDINSERT) failed on %s\n", 1186 serverS_path); 1187 close (fdr); 1188 close (fds); 1189 return -1; 1190 } 1191 1192 /* 1193 * Everything looks good: fill in the XtransConnInfo structure. 1194 */ 1195 1196 #if defined(X11_t) && defined(__SCO__) 1197 ciptr->flags |= TRANS_NOUNLINK; 1198 #endif 1199 if (TRANS(FillAddrInfo) (ciptr, serverS_path, serverR_path) == 0) { 1200 prmsg(1,"SCOOpenServer: failed to fill in addr info\n"); 1201 close(fds); 1202 close(fdr); 1203 return -1; 1204 } 1205 1206 return(fds); 1207 1208 #endif /* !SCORNODENAME */ 1209 } 1210 1211 static int 1212 TRANS(SCOAccept)(XtransConnInfo ciptr, XtransConnInfo newciptr, int *status) 1213 { 1214 char c; 1215 int fd; 1216 1217 prmsg(2,"SCOAccept(%d)\n", ciptr->fd); 1218 1219 if (read(ciptr->fd, &c, 1) < 0) { 1220 prmsg(1,"SCOAccept: can't read from client\n"); 1221 *status = TRANS_ACCEPT_MISC_ERROR; 1222 return(-1); 1223 } 1224 1225 if( (fd = open(DEV_SPX, O_RDWR)) < 0 ) { 1226 prmsg(1,"SCOAccept: can't open \"%s\"\n",DEV_SPX); 1227 *status = TRANS_ACCEPT_MISC_ERROR; 1228 return(-1); 1229 } 1230 1231 if (connect_spipe (ciptr->fd, fd) < 0) { 1232 prmsg(1,"SCOAccept: ioctl(I_FDINSERT) failed\n"); 1233 close (fd); 1234 *status = TRANS_ACCEPT_MISC_ERROR; 1235 return -1; 1236 } 1237 1238 /* 1239 * Everything looks good: fill in the XtransConnInfo structure. 1240 */ 1241 1242 newciptr->addrlen=ciptr->addrlen; 1243 if( (newciptr->addr = malloc(newciptr->addrlen)) == NULL ) { 1244 prmsg(1, 1245 "SCOAccept: failed to allocate memory for peer addr\n"); 1246 close(fd); 1247 *status = TRANS_ACCEPT_BAD_MALLOC; 1248 return -1; 1249 } 1250 1251 memcpy(newciptr->addr,ciptr->addr,newciptr->addrlen); 1252 #if defined(__SCO__) 1253 newciptr->flags |= TRANS_NOUNLINK; 1254 #endif 1255 1256 newciptr->peeraddrlen=newciptr->addrlen; 1257 if( (newciptr->peeraddr = malloc(newciptr->peeraddrlen)) == NULL ) { 1258 prmsg(1, 1259 "SCOAccept: failed to allocate memory for peer addr\n"); 1260 free(newciptr->addr); 1261 close(fd); 1262 *status = TRANS_ACCEPT_BAD_MALLOC; 1263 return -1; 1264 } 1265 1266 memcpy(newciptr->peeraddr,newciptr->addr,newciptr->peeraddrlen); 1267 1268 *status = 0; 1269 1270 return(fd); 1271 } 1272 1273 #endif /* TRANS_SERVER */ 1274 #endif /* LOCAL_TRANS_SCO */ 1275 1276 1277 1278 #ifdef TRANS_REOPEN 1279 #ifdef LOCAL_TRANS_PTS 1280 1281 static int 1282 TRANS(PTSReopenServer)(XtransConnInfo ciptr, int fd, const char *port) 1283 1284 { 1285 #ifdef PTSNODENAME 1286 char server_path[64]; 1287 #endif 1288 1289 prmsg(2,"PTSReopenServer(%d,%s)\n", fd, port); 1290 1291 #if !defined(PTSNODENAME) 1292 prmsg(1,"PTSReopenServer: Protocol is not supported by a pts connection\n"); 1293 return 0; 1294 #else 1295 if (port && *port ) { 1296 if( *port == '/' ) { /* A full pathname */ 1297 snprintf(server_path, sizeof(server_path), "%s", port); 1298 } else { 1299 snprintf(server_path, sizeof(server_path), "%s%s", 1300 PTSNODENAME, port); 1301 } 1302 } else { 1303 snprintf(server_path, sizeof(server_path), "%s%ld", 1304 PTSNODENAME, (long)getpid()); 1305 } 1306 1307 if (TRANS(FillAddrInfo) (ciptr, server_path, server_path) == 0) 1308 { 1309 prmsg(1,"PTSReopenServer: failed to fill in addr info\n"); 1310 return 0; 1311 } 1312 1313 return 1; 1314 1315 #endif /* !PTSNODENAME */ 1316 } 1317 1318 #endif /* LOCAL_TRANS_PTS */ 1319 1320 #ifdef LOCAL_TRANS_NAMED 1321 1322 static int 1323 TRANS(NAMEDReopenServer)(XtransConnInfo ciptr, int fd _X_UNUSED, const char *port) 1324 1325 { 1326 #ifdef NAMEDNODENAME 1327 char server_path[64]; 1328 #endif 1329 1330 prmsg(2,"NAMEDReopenServer(%s)\n", port); 1331 1332 #if !defined(NAMEDNODENAME) 1333 prmsg(1,"NAMEDReopenServer: Protocol is not supported by a NAMED connection\n"); 1334 return 0; 1335 #else 1336 if ( port && *port ) { 1337 if( *port == '/' ) { /* A full pathname */ 1338 snprintf(server_path, sizeof(server_path),"%s", port); 1339 } else { 1340 snprintf(server_path, sizeof(server_path), "%s%s", 1341 NAMEDNODENAME, port); 1342 } 1343 } else { 1344 snprintf(server_path, sizeof(server_path), "%s%ld", 1345 NAMEDNODENAME, (long)getpid()); 1346 } 1347 1348 if (TRANS(FillAddrInfo) (ciptr, server_path, server_path) == 0) 1349 { 1350 prmsg(1,"NAMEDReopenServer: failed to fill in addr info\n"); 1351 return 0; 1352 } 1353 1354 return 1; 1355 1356 #endif /* !NAMEDNODENAME */ 1357 } 1358 1359 #endif /* LOCAL_TRANS_NAMED */ 1360 1361 1362 #ifdef LOCAL_TRANS_SCO 1363 static int 1364 TRANS(SCOReopenServer)(XtransConnInfo ciptr, int fd, const char *port) 1365 1366 { 1367 #ifdef SCORNODENAME 1368 char serverR_path[64], serverS_path[64]; 1369 #endif 1370 1371 prmsg(2,"SCOReopenServer(%s)\n", port); 1372 if (!port || !port[0]) 1373 port = "0"; 1374 1375 #if !defined(SCORNODENAME) 1376 prmsg(2,"SCOReopenServer: Protocol is not supported by a SCO connection\n"); 1377 return 0; 1378 #else 1379 (void) sprintf(serverR_path, SCORNODENAME, port); 1380 (void) sprintf(serverS_path, SCOSNODENAME, port); 1381 1382 #if defined(X11_t) && defined(__SCO__) 1383 ciptr->flags |= TRANS_NOUNLINK; 1384 #endif 1385 if (TRANS(FillAddrInfo) (ciptr, serverS_path, serverR_path) == 0) 1386 { 1387 prmsg(1, "SCOReopenServer: failed to fill in addr info\n"); 1388 return 0; 1389 } 1390 1391 return 1; 1392 1393 #endif /* SCORNODENAME */ 1394 } 1395 1396 #endif /* LOCAL_TRANS_SCO */ 1397 1398 #endif /* TRANS_REOPEN */ 1399 1400 1401 1402 /* 1403 * This table contains all of the entry points for the different local 1404 * connection mechanisms. 1405 */ 1406 1407 typedef struct _LOCALtrans2dev { 1408 const char *transname; 1409 1410 #ifdef TRANS_CLIENT 1411 1412 int (*devcotsopenclient)( 1413 XtransConnInfo, const char * /*port*/ 1414 ); 1415 1416 #endif /* TRANS_CLIENT */ 1417 1418 #ifdef TRANS_SERVER 1419 1420 int (*devcotsopenserver)( 1421 XtransConnInfo, const char * /*port*/ 1422 ); 1423 1424 #endif /* TRANS_SERVER */ 1425 1426 #ifdef TRANS_CLIENT 1427 1428 int (*devcltsopenclient)( 1429 XtransConnInfo, const char * /*port*/ 1430 ); 1431 1432 #endif /* TRANS_CLIENT */ 1433 1434 #ifdef TRANS_SERVER 1435 1436 int (*devcltsopenserver)( 1437 XtransConnInfo, const char * /*port*/ 1438 ); 1439 1440 #endif /* TRANS_SERVER */ 1441 1442 #ifdef TRANS_REOPEN 1443 1444 int (*devcotsreopenserver)( 1445 XtransConnInfo, 1446 int, /* fd */ 1447 const char * /* port */ 1448 ); 1449 1450 int (*devcltsreopenserver)( 1451 XtransConnInfo, 1452 int, /* fd */ 1453 const char * /* port */ 1454 ); 1455 1456 #endif /* TRANS_REOPEN */ 1457 1458 #ifdef TRANS_SERVER 1459 1460 int (*devreset)( 1461 XtransConnInfo /* ciptr */ 1462 ); 1463 1464 int (*devaccept)( 1465 XtransConnInfo, XtransConnInfo, int * 1466 ); 1467 1468 #endif /* TRANS_SERVER */ 1469 1470 } LOCALtrans2dev; 1471 1472 static LOCALtrans2dev LOCALtrans2devtab[] = { 1473 #ifdef LOCAL_TRANS_PTS 1474 {"", 1475 #ifdef TRANS_CLIENT 1476 TRANS(PTSOpenClient), 1477 #endif /* TRANS_CLIENT */ 1478 #ifdef TRANS_SERVER 1479 TRANS(PTSOpenServer), 1480 #endif /* TRANS_SERVER */ 1481 #ifdef TRANS_CLIENT 1482 TRANS(OpenFail), 1483 #endif /* TRANS_CLIENT */ 1484 #ifdef TRANS_SERVER 1485 TRANS(OpenFail), 1486 #endif /* TRANS_SERVER */ 1487 #ifdef TRANS_REOPEN 1488 TRANS(PTSReopenServer), 1489 TRANS(ReopenFail), 1490 #endif 1491 #ifdef TRANS_SERVER 1492 NULL, /* ResetListener */ 1493 TRANS(PTSAccept) 1494 #endif /* TRANS_SERVER */ 1495 }, 1496 1497 {"local", 1498 #ifdef TRANS_CLIENT 1499 TRANS(PTSOpenClient), 1500 #endif /* TRANS_CLIENT */ 1501 #ifdef TRANS_SERVER 1502 TRANS(PTSOpenServer), 1503 #endif /* TRANS_SERVER */ 1504 #ifdef TRANS_CLIENT 1505 TRANS(OpenFail), 1506 #endif /* TRANS_CLIENT */ 1507 #ifdef TRANS_SERVER 1508 TRANS(OpenFail), 1509 #endif /* TRANS_SERVER */ 1510 #ifdef TRANS_REOPEN 1511 TRANS(PTSReopenServer), 1512 TRANS(ReopenFail), 1513 #endif 1514 #ifdef TRANS_SERVER 1515 NULL, /* ResetListener */ 1516 TRANS(PTSAccept) 1517 #endif /* TRANS_SERVER */ 1518 }, 1519 1520 {"pts", 1521 #ifdef TRANS_CLIENT 1522 TRANS(PTSOpenClient), 1523 #endif /* TRANS_CLIENT */ 1524 #ifdef TRANS_SERVER 1525 TRANS(PTSOpenServer), 1526 #endif /* TRANS_SERVER */ 1527 #ifdef TRANS_CLIENT 1528 TRANS(OpenFail), 1529 #endif /* TRANS_CLIENT */ 1530 #ifdef TRANS_SERVER 1531 TRANS(OpenFail), 1532 #endif /* TRANS_SERVER */ 1533 #ifdef TRANS_REOPEN 1534 TRANS(PTSReopenServer), 1535 TRANS(ReopenFail), 1536 #endif 1537 #ifdef TRANS_SERVER 1538 NULL, /* ResetListener */ 1539 TRANS(PTSAccept) 1540 #endif /* TRANS_SERVER */ 1541 }, 1542 #else /* !LOCAL_TRANS_PTS */ 1543 {"", 1544 #ifdef TRANS_CLIENT 1545 TRANS(NAMEDOpenClient), 1546 #endif /* TRANS_CLIENT */ 1547 #ifdef TRANS_SERVER 1548 TRANS(NAMEDOpenServer), 1549 #endif /* TRANS_SERVER */ 1550 #ifdef TRANS_CLIENT 1551 TRANS(OpenFail), 1552 #endif /* TRANS_CLIENT */ 1553 #ifdef TRANS_SERVER 1554 TRANS(OpenFail), 1555 #endif /* TRANS_SERVER */ 1556 #ifdef TRANS_REOPEN 1557 TRANS(NAMEDReopenServer), 1558 TRANS(ReopenFail), 1559 #endif 1560 #ifdef TRANS_SERVER 1561 TRANS(NAMEDResetListener), 1562 TRANS(NAMEDAccept) 1563 #endif /* TRANS_SERVER */ 1564 }, 1565 1566 {"local", 1567 #ifdef TRANS_CLIENT 1568 TRANS(NAMEDOpenClient), 1569 #endif /* TRANS_CLIENT */ 1570 #ifdef TRANS_SERVER 1571 TRANS(NAMEDOpenServer), 1572 #endif /* TRANS_SERVER */ 1573 #ifdef TRANS_CLIENT 1574 TRANS(OpenFail), 1575 #endif /* TRANS_CLIENT */ 1576 #ifdef TRANS_SERVER 1577 TRANS(OpenFail), 1578 #endif /* TRANS_SERVER */ 1579 #ifdef TRANS_REOPEN 1580 TRANS(NAMEDReopenServer), 1581 TRANS(ReopenFail), 1582 #endif 1583 #ifdef TRANS_SERVER 1584 TRANS(NAMEDResetListener), 1585 TRANS(NAMEDAccept) 1586 #endif /* TRANS_SERVER */ 1587 }, 1588 #endif /* !LOCAL_TRANS_PTS */ 1589 1590 #ifdef LOCAL_TRANS_NAMED 1591 {"named", 1592 #ifdef TRANS_CLIENT 1593 TRANS(NAMEDOpenClient), 1594 #endif /* TRANS_CLIENT */ 1595 #ifdef TRANS_SERVER 1596 TRANS(NAMEDOpenServer), 1597 #endif /* TRANS_SERVER */ 1598 #ifdef TRANS_CLIENT 1599 TRANS(OpenFail), 1600 #endif /* TRANS_CLIENT */ 1601 #ifdef TRANS_SERVER 1602 TRANS(OpenFail), 1603 #endif /* TRANS_SERVER */ 1604 #ifdef TRANS_REOPEN 1605 TRANS(NAMEDReopenServer), 1606 TRANS(ReopenFail), 1607 #endif 1608 #ifdef TRANS_SERVER 1609 TRANS(NAMEDResetListener), 1610 TRANS(NAMEDAccept) 1611 #endif /* TRANS_SERVER */ 1612 }, 1613 1614 #ifdef __sun /* Alias "pipe" to named, since that's what Solaris called it */ 1615 {"pipe", 1616 #ifdef TRANS_CLIENT 1617 TRANS(NAMEDOpenClient), 1618 #endif /* TRANS_CLIENT */ 1619 #ifdef TRANS_SERVER 1620 TRANS(NAMEDOpenServer), 1621 #endif /* TRANS_SERVER */ 1622 #ifdef TRANS_CLIENT 1623 TRANS(OpenFail), 1624 #endif /* TRANS_CLIENT */ 1625 #ifdef TRANS_SERVER 1626 TRANS(OpenFail), 1627 #endif /* TRANS_SERVER */ 1628 #ifdef TRANS_REOPEN 1629 TRANS(NAMEDReopenServer), 1630 TRANS(ReopenFail), 1631 #endif 1632 #ifdef TRANS_SERVER 1633 TRANS(NAMEDResetListener), 1634 TRANS(NAMEDAccept) 1635 #endif /* TRANS_SERVER */ 1636 }, 1637 #endif /* __sun */ 1638 #endif /* LOCAL_TRANS_NAMED */ 1639 1640 1641 #ifdef LOCAL_TRANS_SCO 1642 {"sco", 1643 #ifdef TRANS_CLIENT 1644 TRANS(SCOOpenClient), 1645 #endif /* TRANS_CLIENT */ 1646 #ifdef TRANS_SERVER 1647 TRANS(SCOOpenServer), 1648 #endif /* TRANS_SERVER */ 1649 #ifdef TRANS_CLIENT 1650 TRANS(OpenFail), 1651 #endif /* TRANS_CLIENT */ 1652 #ifdef TRANS_SERVER 1653 TRANS(OpenFail), 1654 #endif /* TRANS_SERVER */ 1655 #ifdef TRANS_REOPEN 1656 TRANS(SCOReopenServer), 1657 TRANS(ReopenFail), 1658 #endif 1659 #ifdef TRANS_SERVER 1660 NULL, /* ResetListener */ 1661 TRANS(SCOAccept) 1662 #endif /* TRANS_SERVER */ 1663 }, 1664 #endif /* LOCAL_TRANS_SCO */ 1665 }; 1666 1667 #define NUMTRANSPORTS (sizeof(LOCALtrans2devtab)/sizeof(LOCALtrans2dev)) 1668 1669 static const char *XLOCAL=NULL; 1670 static char *workingXLOCAL=NULL; 1671 static char *freeXLOCAL=NULL; 1672 1673 #if defined(__SCO__) 1674 #define DEF_XLOCAL "SCO:UNIX:PTS" 1675 #elif defined(__UNIXWARE__) 1676 #define DEF_XLOCAL "UNIX:PTS:NAMED:SCO" 1677 #elif defined(__sun) 1678 #define DEF_XLOCAL "UNIX:NAMED" 1679 #else 1680 #define DEF_XLOCAL "UNIX:PTS:NAMED:SCO" 1681 #endif 1682 1683 static void 1684 TRANS(LocalInitTransports)(const char *protocol) 1685 1686 { 1687 prmsg(3,"LocalInitTransports(%s)\n", protocol); 1688 1689 if( strcmp(protocol,"local") && strcmp(protocol,"LOCAL") ) 1690 { 1691 workingXLOCAL = freeXLOCAL = strdup (protocol); 1692 } 1693 else { 1694 XLOCAL=(char *)getenv("XLOCAL"); 1695 if(XLOCAL==NULL) 1696 XLOCAL=DEF_XLOCAL; 1697 workingXLOCAL = freeXLOCAL = strdup (XLOCAL); 1698 } 1699 } 1700 1701 static void 1702 TRANS(LocalEndTransports)(void) 1703 1704 { 1705 prmsg(3,"LocalEndTransports()\n"); 1706 free(freeXLOCAL); 1707 freeXLOCAL = NULL; 1708 } 1709 1710 #define TYPEBUFSIZE 32 1711 1712 #ifdef TRANS_CLIENT 1713 1714 static LOCALtrans2dev * 1715 TRANS(LocalGetNextTransport)(void) 1716 1717 { 1718 int i; 1719 char *typetocheck; 1720 prmsg(3,"LocalGetNextTransport()\n"); 1721 1722 while(1) 1723 { 1724 if( workingXLOCAL == NULL || *workingXLOCAL == '\0' ) 1725 return NULL; 1726 1727 typetocheck=workingXLOCAL; 1728 workingXLOCAL=strchr(workingXLOCAL,':'); 1729 if(workingXLOCAL && *workingXLOCAL) 1730 *workingXLOCAL++='\0'; 1731 1732 for(i=0;i
1762 #endif 1763 1764 /* 1765 * Make sure 'host' is really local. 1766 */ 1767 1768 static int 1769 HostReallyLocal (const char *host) 1770 1771 { 1772 /* 1773 * The 'host' passed to this function may have been generated 1774 * by either uname() or gethostname(). We try both if possible. 1775 */ 1776 1777 #ifdef NEED_UTSNAME 1778 struct utsname name; 1779 #endif 1780 char buf[256]; 1781 1782 #ifdef NEED_UTSNAME 1783 if (uname (&name) >= 0 && strcmp (host, name.nodename) == 0) 1784 return (1); 1785 #endif 1786 1787 buf[0] = '\0'; 1788 (void) gethostname (buf, 256); 1789 buf[255] = '\0'; 1790 1791 if (strcmp (host, buf) == 0) 1792 return (1); 1793 1794 return (0); 1795 } 1796 1797 1798 static XtransConnInfo 1799 TRANS(LocalOpenClient)(int type, const char *protocol, 1800 const char *host, const char *port) 1801 1802 { 1803 LOCALtrans2dev *transptr; 1804 XtransConnInfo ciptr; 1805 int index; 1806 1807 prmsg(3,"LocalOpenClient()\n"); 1808 1809 /* 1810 * Make sure 'host' is really local. If not, we return failure. 1811 * The reason we make this check is because a process may advertise 1812 * a "local" address for which it can accept connections, but if a 1813 * process on a remote machine tries to connect to this address, 1814 * we know for sure it will fail. 1815 */ 1816 1817 if (strcmp (host, "unix") != 0 && !HostReallyLocal (host)) 1818 { 1819 prmsg (1, 1820 "LocalOpenClient: Cannot connect to non-local host %s\n", 1821 host); 1822 return NULL; 1823 } 1824 1825 1826 #if defined(X11_t) 1827 /* 1828 * X has a well known port, that is transport dependant. It is easier 1829 * to handle it here, than try and come up with a transport independent 1830 * representation that can be passed in and resolved the usual way. 1831 * 1832 * The port that is passed here is really a string containing the idisplay 1833 * from ConnectDisplay(). Since that is what we want for the local transports, 1834 * we don't have to do anything special. 1835 */ 1836 #endif /* X11_t */ 1837 1838 if( (ciptr = calloc(1,sizeof(struct _XtransConnInfo))) == NULL ) 1839 { 1840 prmsg(1,"LocalOpenClient: calloc(1,%lu) failed\n", 1841 sizeof(struct _XtransConnInfo)); 1842 return NULL; 1843 } 1844 1845 ciptr->fd = -1; 1846 1847 TRANS(LocalInitTransports)(protocol); 1848 1849 index = 0; 1850 for(transptr=TRANS(LocalGetNextTransport)(); 1851 transptr!=NULL;transptr=TRANS(LocalGetNextTransport)(), index++) 1852 { 1853 switch( type ) 1854 { 1855 case XTRANS_OPEN_COTS_CLIENT: 1856 ciptr->fd=transptr->devcotsopenclient(ciptr,port); 1857 break; 1858 case XTRANS_OPEN_COTS_SERVER: 1859 prmsg(1, 1860 "LocalOpenClient: Should not be opening a server with this function\n"); 1861 break; 1862 default: 1863 prmsg(1, 1864 "LocalOpenClient: Unknown Open type %d\n", 1865 type); 1866 } 1867 if( ciptr->fd >= 0 ) 1868 break; 1869 } 1870 1871 TRANS(LocalEndTransports)(); 1872 1873 if( ciptr->fd < 0 ) 1874 { 1875 free(ciptr); 1876 return NULL; 1877 } 1878 1879 ciptr->priv=(char *)transptr; 1880 ciptr->index = index; 1881 1882 return ciptr; 1883 } 1884 1885 #endif /* TRANS_CLIENT */ 1886 1887 1888 #ifdef TRANS_SERVER 1889 1890 static XtransConnInfo 1891 TRANS(LocalOpenServer)(int type, const char *protocol, 1892 const char *host _X_UNUSED, const char *port) 1893 1894 { 1895 int i; 1896 XtransConnInfo ciptr; 1897 1898 prmsg(2,"LocalOpenServer(%d,%s,%s)\n", type, protocol, port); 1899 1900 #if defined(X11_t) 1901 /* 1902 * For X11, the port will be in the format xserverN where N is the 1903 * display number. All of the local connections just need to know 1904 * the display number because they don't do any name resolution on 1905 * the port. This just truncates port to the display portion. 1906 */ 1907 #endif /* X11_t */ 1908 1909 if( (ciptr = calloc(1,sizeof(struct _XtransConnInfo))) == NULL ) 1910 { 1911 prmsg(1,"LocalOpenServer: calloc(1,%lu) failed\n", 1912 sizeof(struct _XtransConnInfo)); 1913 return NULL; 1914 } 1915 1916 for(i=1;i
fd=LOCALtrans2devtab[i].devcotsopenserver(ciptr,port); 1928 break; 1929 default: 1930 prmsg(1,"LocalOpenServer: Unknown Open type %d\n", 1931 type ); 1932 } 1933 if( ciptr->fd >= 0 ) { 1934 ciptr->priv=(char *)&LOCALtrans2devtab[i]; 1935 ciptr->index=i; 1936 ciptr->flags = 1 | (ciptr->flags & TRANS_KEEPFLAGS); 1937 return ciptr; 1938 } 1939 } 1940 1941 free(ciptr); 1942 return NULL; 1943 } 1944 1945 #endif /* TRANS_SERVER */ 1946 1947 1948 #ifdef TRANS_REOPEN 1949 1950 static XtransConnInfo 1951 TRANS(LocalReopenServer)(int type, int index, int fd, const char *port) 1952 1953 { 1954 XtransConnInfo ciptr; 1955 int stat = 0; 1956 1957 prmsg(2,"LocalReopenServer(%d,%d,%d)\n", type, index, fd); 1958 1959 if( (ciptr = calloc(1,sizeof(struct _XtransConnInfo))) == NULL ) 1960 { 1961 prmsg(1,"LocalReopenServer: calloc(1,%lu) failed\n", 1962 sizeof(struct _XtransConnInfo)); 1963 return NULL; 1964 } 1965 1966 ciptr->fd = fd; 1967 1968 switch( type ) 1969 { 1970 case XTRANS_OPEN_COTS_SERVER: 1971 stat = LOCALtrans2devtab[index].devcotsreopenserver(ciptr,fd,port); 1972 break; 1973 default: 1974 prmsg(1,"LocalReopenServer: Unknown Open type %d\n", 1975 type ); 1976 } 1977 1978 if( stat > 0 ) { 1979 ciptr->priv=(char *)&LOCALtrans2devtab[index]; 1980 ciptr->index=index; 1981 ciptr->flags = 1 | (ciptr->flags & TRANS_KEEPFLAGS); 1982 return ciptr; 1983 } 1984 1985 free(ciptr); 1986 return NULL; 1987 } 1988 1989 #endif /* TRANS_REOPEN */ 1990 1991 1992 1993 /* 1994 * This is the Local implementation of the X Transport service layer 1995 */ 1996 1997 #ifdef TRANS_CLIENT 1998 1999 static XtransConnInfo 2000 TRANS(LocalOpenCOTSClient)(Xtransport *thistrans _X_UNUSED, const char *protocol, 2001 const char *host, const char *port) 2002 2003 { 2004 prmsg(2,"LocalOpenCOTSClient(%s,%s,%s)\n",protocol,host,port); 2005 2006 return TRANS(LocalOpenClient)(XTRANS_OPEN_COTS_CLIENT, protocol, host, port); 2007 } 2008 2009 #endif /* TRANS_CLIENT */ 2010 2011 2012 #ifdef TRANS_SERVER 2013 2014 static XtransConnInfo 2015 TRANS(LocalOpenCOTSServer)(Xtransport *thistrans, const char *protocol, 2016 const char *host, const char *port) 2017 2018 { 2019 char *typetocheck = NULL; 2020 int found = 0; 2021 2022 prmsg(2,"LocalOpenCOTSServer(%s,%s,%s)\n",protocol,host,port); 2023 2024 /* Check if this local type is in the XLOCAL list */ 2025 TRANS(LocalInitTransports)("local"); 2026 typetocheck = workingXLOCAL; 2027 while (typetocheck && !found) { 2028 #ifndef HAVE_STRCASECMP 2029 int j; 2030 char typebuf[TYPEBUFSIZE]; 2031 #endif 2032 2033 workingXLOCAL = strchr(workingXLOCAL, ':'); 2034 if (workingXLOCAL && *workingXLOCAL) 2035 *workingXLOCAL++ = '\0'; 2036 #ifndef HAVE_STRCASECMP 2037 strncpy(typebuf, typetocheck, TYPEBUFSIZE); 2038 for (j = 0; j < TYPEBUFSIZE; j++) 2039 if (isupper(typebuf[j])) 2040 typebuf[j] = tolower(typebuf[j]); 2041 if (!strcmp(thistrans->TransName, typebuf)) 2042 #else 2043 if (!strcasecmp(thistrans->TransName, typetocheck)) 2044 #endif 2045 found = 1; 2046 typetocheck = workingXLOCAL; 2047 } 2048 TRANS(LocalEndTransports)(); 2049 2050 if (!found) { 2051 prmsg(3,"LocalOpenCOTSServer: disabling %s\n",thistrans->TransName); 2052 thistrans->flags |= TRANS_DISABLED; 2053 return NULL; 2054 } 2055 2056 return TRANS(LocalOpenServer)(XTRANS_OPEN_COTS_SERVER, protocol, host, port); 2057 } 2058 2059 #endif /* TRANS_SERVER */ 2060 2061 #ifdef TRANS_REOPEN 2062 2063 static XtransConnInfo 2064 TRANS(LocalReopenCOTSServer)(Xtransport *thistrans, int fd, const char *port) 2065 2066 { 2067 int index; 2068 2069 prmsg(2,"LocalReopenCOTSServer(%d,%s)\n", fd, port); 2070 2071 for(index=1;index
TransName, 2074 LOCALtrans2devtab[index].transname) == 0 ) 2075 break; 2076 } 2077 2078 if (index >= NUMTRANSPORTS) 2079 { 2080 return (NULL); 2081 } 2082 2083 return TRANS(LocalReopenServer)(XTRANS_OPEN_COTS_SERVER, 2084 index, fd, port); 2085 } 2086 2087 #endif /* TRANS_REOPEN */ 2088 2089 2090 2091 static int 2092 TRANS(LocalSetOption)(XtransConnInfo ciptr, int option, int arg) 2093 2094 { 2095 prmsg(2,"LocalSetOption(%d,%d,%d)\n",ciptr->fd,option,arg); 2096 2097 return -1; 2098 } 2099 2100 2101 #ifdef TRANS_SERVER 2102 2103 static int 2104 TRANS(LocalCreateListener)(XtransConnInfo ciptr, const char *port, 2105 unsigned int flags _X_UNUSED) 2106 2107 { 2108 prmsg(2,"LocalCreateListener(%p->%d,%s)\n",ciptr,ciptr->fd,port); 2109 2110 return 0; 2111 } 2112 2113 static int 2114 TRANS(LocalResetListener)(XtransConnInfo ciptr) 2115 2116 { 2117 LOCALtrans2dev *transptr; 2118 2119 prmsg(2,"LocalResetListener(%p)\n",ciptr); 2120 2121 transptr=(LOCALtrans2dev *)ciptr->priv; 2122 if (transptr->devreset != NULL) { 2123 return transptr->devreset(ciptr); 2124 } 2125 return TRANS_RESET_NOOP; 2126 } 2127 2128 2129 static XtransConnInfo 2130 TRANS(LocalAccept)(XtransConnInfo ciptr, int *status) 2131 2132 { 2133 XtransConnInfo newciptr; 2134 LOCALtrans2dev *transptr; 2135 2136 prmsg(2,"LocalAccept(%p->%d)\n", ciptr, ciptr->fd); 2137 2138 transptr=(LOCALtrans2dev *)ciptr->priv; 2139 2140 if( (newciptr = calloc(1,sizeof(struct _XtransConnInfo)))==NULL ) 2141 { 2142 prmsg(1,"LocalAccept: calloc(1,%lu) failed\n", 2143 sizeof(struct _XtransConnInfo)); 2144 *status = TRANS_ACCEPT_BAD_MALLOC; 2145 return NULL; 2146 } 2147 2148 newciptr->fd=transptr->devaccept(ciptr,newciptr,status); 2149 2150 if( newciptr->fd < 0 ) 2151 { 2152 free(newciptr); 2153 return NULL; 2154 } 2155 2156 newciptr->priv=(char *)transptr; 2157 newciptr->index = ciptr->index; 2158 2159 *status = 0; 2160 2161 return newciptr; 2162 } 2163 2164 #endif /* TRANS_SERVER */ 2165 2166 2167 #ifdef TRANS_CLIENT 2168 2169 static int 2170 TRANS(LocalConnect)(XtransConnInfo ciptr, 2171 const char *host _X_UNUSED, const char *port) 2172 2173 { 2174 prmsg(2,"LocalConnect(%p->%d,%s)\n", ciptr, ciptr->fd, port); 2175 2176 return 0; 2177 } 2178 2179 #endif /* TRANS_CLIENT */ 2180 2181 2182 static int 2183 TRANS(LocalBytesReadable)(XtransConnInfo ciptr, BytesReadable_t *pend ) 2184 2185 { 2186 prmsg(2,"LocalBytesReadable(%p->%d,%p)\n", ciptr, ciptr->fd, pend); 2187 2188 #if defined(SCO325) 2189 return ioctl(ciptr->fd, I_NREAD, (char *)pend); 2190 #else 2191 return ioctl(ciptr->fd, FIONREAD, (char *)pend); 2192 #endif 2193 } 2194 2195 static int 2196 TRANS(LocalRead)(XtransConnInfo ciptr, char *buf, int size) 2197 2198 { 2199 prmsg(2,"LocalRead(%d,%p,%d)\n", ciptr->fd, buf, size ); 2200 2201 return read(ciptr->fd,buf,size); 2202 } 2203 2204 static int 2205 TRANS(LocalWrite)(XtransConnInfo ciptr, char *buf, int size) 2206 2207 { 2208 prmsg(2,"LocalWrite(%d,%p,%d)\n", ciptr->fd, buf, size ); 2209 2210 return write(ciptr->fd,buf,size); 2211 } 2212 2213 static int 2214 TRANS(LocalReadv)(XtransConnInfo ciptr, struct iovec *buf, int size) 2215 2216 { 2217 prmsg(2,"LocalReadv(%d,%p,%d)\n", ciptr->fd, buf, size ); 2218 2219 return READV(ciptr,buf,size); 2220 } 2221 2222 static int 2223 TRANS(LocalWritev)(XtransConnInfo ciptr, struct iovec *buf, int size) 2224 2225 { 2226 prmsg(2,"LocalWritev(%d,%p,%d)\n", ciptr->fd, buf, size ); 2227 2228 return WRITEV(ciptr,buf,size); 2229 } 2230 2231 static int 2232 TRANS(LocalDisconnect)(XtransConnInfo ciptr) 2233 2234 { 2235 prmsg(2,"LocalDisconnect(%p->%d)\n", ciptr, ciptr->fd); 2236 2237 return 0; 2238 } 2239 2240 static int 2241 TRANS(LocalClose)(XtransConnInfo ciptr) 2242 2243 { 2244 struct sockaddr_un *sockname=(struct sockaddr_un *) ciptr->addr; 2245 int ret; 2246 2247 prmsg(2,"LocalClose(%p->%d)\n", ciptr, ciptr->fd ); 2248 2249 ret=close(ciptr->fd); 2250 2251 if(ciptr->flags 2252 && sockname 2253 && sockname->sun_family == AF_UNIX 2254 && sockname->sun_path[0] ) 2255 { 2256 if (!(ciptr->flags & TRANS_NOUNLINK)) 2257 unlink(sockname->sun_path); 2258 } 2259 2260 return ret; 2261 } 2262 2263 static int 2264 TRANS(LocalCloseForCloning)(XtransConnInfo ciptr) 2265 2266 { 2267 int ret; 2268 2269 prmsg(2,"LocalCloseForCloning(%p->%d)\n", ciptr, ciptr->fd ); 2270 2271 /* Don't unlink path */ 2272 2273 ret=close(ciptr->fd); 2274 2275 return ret; 2276 } 2277 2278 2279 /* 2280 * MakeAllCOTSServerListeners() will go through the entire Xtransports[] 2281 * array defined in Xtrans.c and try to OpenCOTSServer() for each entry. 2282 * We will add duplicate entries to that table so that the OpenCOTSServer() 2283 * function will get called once for each type of local transport. 2284 * 2285 * The TransName is in lowercase, so it will never match during a normal 2286 * call to SelectTransport() in Xtrans.c. 2287 */ 2288 2289 #ifdef TRANS_SERVER 2290 static const char * local_aliases[] = { 2291 # ifdef LOCAL_TRANS_PTS 2292 "pts", 2293 # endif 2294 "named", 2295 # ifdef __sun 2296 "pipe", /* compatibility with Solaris Xlib */ 2297 # endif 2298 # ifdef LOCAL_TRANS_SCO 2299 "sco", 2300 # endif 2301 NULL }; 2302 #endif 2303 2304 Xtransport TRANS(LocalFuncs) = { 2305 /* Local Interface */ 2306 "local", 2307 TRANS_ALIAS | TRANS_LOCAL, 2308 #ifdef TRANS_CLIENT 2309 TRANS(LocalOpenCOTSClient), 2310 #endif /* TRANS_CLIENT */ 2311 #ifdef TRANS_SERVER 2312 local_aliases, 2313 TRANS(LocalOpenCOTSServer), 2314 #endif /* TRANS_SERVER */ 2315 #ifdef TRANS_REOPEN 2316 TRANS(LocalReopenCOTSServer), 2317 #endif 2318 TRANS(LocalSetOption), 2319 #ifdef TRANS_SERVER 2320 TRANS(LocalCreateListener), 2321 TRANS(LocalResetListener), 2322 TRANS(LocalAccept), 2323 #endif /* TRANS_SERVER */ 2324 #ifdef TRANS_CLIENT 2325 TRANS(LocalConnect), 2326 #endif /* TRANS_CLIENT */ 2327 TRANS(LocalBytesReadable), 2328 TRANS(LocalRead), 2329 TRANS(LocalWrite), 2330 TRANS(LocalReadv), 2331 TRANS(LocalWritev), 2332 #if XTRANS_SEND_FDS 2333 TRANS(LocalSendFdInvalid), 2334 TRANS(LocalRecvFdInvalid), 2335 #endif 2336 TRANS(LocalDisconnect), 2337 TRANS(LocalClose), 2338 TRANS(LocalCloseForCloning), 2339 }; 2340 2341 #ifdef LOCAL_TRANS_PTS 2342 2343 Xtransport TRANS(PTSFuncs) = { 2344 /* Local Interface */ 2345 "pts", 2346 TRANS_LOCAL, 2347 #ifdef TRANS_CLIENT 2348 TRANS(LocalOpenCOTSClient), 2349 #endif /* TRANS_CLIENT */ 2350 #ifdef TRANS_SERVER 2351 NULL, 2352 TRANS(LocalOpenCOTSServer), 2353 #endif /* TRANS_SERVER */ 2354 #ifdef TRANS_REOPEN 2355 TRANS(LocalReopenCOTSServer), 2356 #endif 2357 TRANS(LocalSetOption), 2358 #ifdef TRANS_SERVER 2359 TRANS(LocalCreateListener), 2360 TRANS(LocalResetListener), 2361 TRANS(LocalAccept), 2362 #endif /* TRANS_SERVER */ 2363 #ifdef TRANS_CLIENT 2364 TRANS(LocalConnect), 2365 #endif /* TRANS_CLIENT */ 2366 TRANS(LocalBytesReadable), 2367 TRANS(LocalRead), 2368 TRANS(LocalWrite), 2369 TRANS(LocalReadv), 2370 TRANS(LocalWritev), 2371 #if XTRANS_SEND_FDS 2372 TRANS(LocalSendFdInvalid), 2373 TRANS(LocalRecvFdInvalid), 2374 #endif 2375 TRANS(LocalDisconnect), 2376 TRANS(LocalClose), 2377 TRANS(LocalCloseForCloning), 2378 }; 2379 2380 #endif /* LOCAL_TRANS_PTS */ 2381 2382 #ifdef LOCAL_TRANS_NAMED 2383 2384 Xtransport TRANS(NAMEDFuncs) = { 2385 /* Local Interface */ 2386 "named", 2387 TRANS_LOCAL, 2388 #ifdef TRANS_CLIENT 2389 TRANS(LocalOpenCOTSClient), 2390 #endif /* TRANS_CLIENT */ 2391 #ifdef TRANS_SERVER 2392 NULL, 2393 TRANS(LocalOpenCOTSServer), 2394 #endif /* TRANS_SERVER */ 2395 #ifdef TRANS_REOPEN 2396 TRANS(LocalReopenCOTSServer), 2397 #endif 2398 TRANS(LocalSetOption), 2399 #ifdef TRANS_SERVER 2400 TRANS(LocalCreateListener), 2401 TRANS(LocalResetListener), 2402 TRANS(LocalAccept), 2403 #endif /* TRANS_SERVER */ 2404 #ifdef TRANS_CLIENT 2405 TRANS(LocalConnect), 2406 #endif /* TRANS_CLIENT */ 2407 TRANS(LocalBytesReadable), 2408 TRANS(LocalRead), 2409 TRANS(LocalWrite), 2410 TRANS(LocalReadv), 2411 TRANS(LocalWritev), 2412 #if XTRANS_SEND_FDS 2413 TRANS(LocalSendFdInvalid), 2414 TRANS(LocalRecvFdInvalid), 2415 #endif 2416 TRANS(LocalDisconnect), 2417 TRANS(LocalClose), 2418 TRANS(LocalCloseForCloning), 2419 }; 2420 2421 #ifdef __sun 2422 Xtransport TRANS(PIPEFuncs) = { 2423 /* Local Interface */ 2424 "pipe", 2425 TRANS_ALIAS | TRANS_LOCAL, 2426 #ifdef TRANS_CLIENT 2427 TRANS(LocalOpenCOTSClient), 2428 #endif /* TRANS_CLIENT */ 2429 #ifdef TRANS_SERVER 2430 NULL, 2431 TRANS(LocalOpenCOTSServer), 2432 #endif /* TRANS_SERVER */ 2433 #ifdef TRANS_REOPEN 2434 TRANS(LocalReopenCOTSServer), 2435 #endif 2436 TRANS(LocalSetOption), 2437 #ifdef TRANS_SERVER 2438 TRANS(LocalCreateListener), 2439 TRANS(LocalResetListener), 2440 TRANS(LocalAccept), 2441 #endif /* TRANS_SERVER */ 2442 #ifdef TRANS_CLIENT 2443 TRANS(LocalConnect), 2444 #endif /* TRANS_CLIENT */ 2445 TRANS(LocalBytesReadable), 2446 TRANS(LocalRead), 2447 TRANS(LocalWrite), 2448 TRANS(LocalReadv), 2449 TRANS(LocalWritev), 2450 #if XTRANS_SEND_FDS 2451 TRANS(LocalSendFdInvalid), 2452 TRANS(LocalRecvFdInvalid), 2453 #endif 2454 TRANS(LocalDisconnect), 2455 TRANS(LocalClose), 2456 TRANS(LocalCloseForCloning), 2457 }; 2458 #endif /* __sun */ 2459 #endif /* LOCAL_TRANS_NAMED */ 2460 2461 2462 #ifdef LOCAL_TRANS_SCO 2463 Xtransport TRANS(SCOFuncs) = { 2464 /* Local Interface */ 2465 "sco", 2466 TRANS_LOCAL, 2467 #ifdef TRANS_CLIENT 2468 TRANS(LocalOpenCOTSClient), 2469 #endif /* TRANS_CLIENT */ 2470 #ifdef TRANS_SERVER 2471 NULL, 2472 TRANS(LocalOpenCOTSServer), 2473 #endif /* TRANS_SERVER */ 2474 #ifdef TRANS_REOPEN 2475 TRANS(LocalReopenCOTSServer), 2476 #endif 2477 TRANS(LocalSetOption), 2478 #ifdef TRANS_SERVER 2479 TRANS(LocalCreateListener), 2480 TRANS(LocalResetListener), 2481 TRANS(LocalAccept), 2482 #endif /* TRANS_SERVER */ 2483 #ifdef TRANS_CLIENT 2484 TRANS(LocalConnect), 2485 #endif /* TRANS_CLIENT */ 2486 TRANS(LocalBytesReadable), 2487 TRANS(LocalRead), 2488 TRANS(LocalWrite), 2489 TRANS(LocalReadv), 2490 TRANS(LocalWritev), 2491 #if XTRANS_SEND_FDS 2492 TRANS(LocalSendFdInvalid), 2493 TRANS(LocalRecvFdInvalid), 2494 #endif 2495 TRANS(LocalDisconnect), 2496 TRANS(LocalClose), 2497 TRANS(LocalCloseForCloning), 2498 }; 2499 #endif /* LOCAL_TRANS_SCO */
Contact us
|
About us
|
Term of use
|
Copyright © 2000-2025 MyWebUniversity.com ™