1 /* 2 * Copyright (c) 1989, 1993 3 * The Regents of the University of California. All rights reserved. 4 * 5 * This code is derived from software contributed to Berkeley by 6 * Tony Nardo of the Johns Hopkins University/Applied Physics Lab. 7 * 8 * %sccs.include.redist.c% 9 */ 10 11 #ifndef lint 12 static char sccsid[] = "@(#)net.c 8.3 (Berkeley) 01/02/94"; 13 #endif /* not lint */ 14 15 #include <sys/types.h> 16 #include <sys/socket.h> 17 #include <netinet/in.h> 18 #include <arpa/inet.h> 19 #include <netdb.h> 20 #include <db.h> 21 #include <unistd.h> 22 #include <pwd.h> 23 #include <utmp.h> 24 #include <stdio.h> 25 #include <ctype.h> 26 #include <string.h> 27 #include "finger.h" 28 29 void 30 netfinger(name) 31 char *name; 32 { 33 extern int lflag; 34 register FILE *fp; 35 register int c, lastc; 36 struct in_addr defaddr; 37 struct hostent *hp, def; 38 struct servent *sp; 39 struct sockaddr_in sin; 40 int s; 41 char *alist[1], *host; 42 43 if (!(host = rindex(name, '@'))) 44 return; 45 *host++ = NULL; 46 if (isdigit(*host) && (defaddr.s_addr = inet_addr(host)) != -1) { 47 def.h_name = host; 48 def.h_addr_list = alist; 49 def.h_addr = (char *)&defaddr; 50 def.h_length = sizeof(struct in_addr); 51 def.h_addrtype = AF_INET; 52 def.h_aliases = 0; 53 hp = &def; 54 } else if (!(hp = gethostbyname(host))) { 55 (void)fprintf(stderr, 56 "finger: unknown host: %s\n", host); 57 return; 58 } 59 if (!(sp = getservbyname("finger", "tcp"))) { 60 (void)fprintf(stderr, "finger: tcp/finger: unknown service\n"); 61 return; 62 } 63 sin.sin_family = hp->h_addrtype; 64 bcopy(hp->h_addr, (char *)&sin.sin_addr, hp->h_length); 65 sin.sin_port = sp->s_port; 66 if ((s = socket(hp->h_addrtype, SOCK_STREAM, 0)) < 0) { 67 perror("finger: socket"); 68 return; 69 } 70 71 /* have network connection; identify the host connected with */ 72 (void)printf("[%s]\n", hp->h_name); 73 if (connect(s, (struct sockaddr *)&sin, sizeof(sin)) < 0) { 74 perror("finger: connect"); 75 (void)close(s); 76 return; 77 } 78 79 /* -l flag for remote fingerd */ 80 if (lflag) 81 write(s, "/W ", 3); 82 /* send the name followed by <CR><LF> */ 83 (void)write(s, name, strlen(name)); 84 (void)write(s, "\r\n", 2); 85 86 /* 87 * Read from the remote system; once we're connected, we assume some 88 * data. If none arrives, we hang until the user interrupts. 89 * 90 * If we see a <CR> or a <CR> with the high bit set, treat it as 91 * a newline; if followed by a newline character, only output one 92 * newline. 93 * 94 * Otherwise, all high bits are stripped; if it isn't printable and 95 * it isn't a space, we can simply set the 7th bit. Every ASCII 96 * character with bit 7 set is printable. 97 */ 98 if (fp = fdopen(s, "r")) 99 while ((c = getc(fp)) != EOF) { 100 c &= 0x7f; 101 if (c == 0x0d) { 102 if (lastc == '\r') /* ^M^M - skip dupes */ 103 continue; 104 c = '\n'; 105 lastc = '\r'; 106 } else { 107 if (!isprint(c) && !isspace(c)) 108 c |= 0x40; 109 if (lastc != '\r' || c != '\n') 110 lastc = c; 111 else { 112 lastc = '\n'; 113 continue; 114 } 115 } 116 putchar(c); 117 } 118 if (lastc != '\n') 119 putchar('\n'); 120 putchar('\n'); 121 (void)fclose(fp); 122 } 123