Index: Makefile
===================================================================
RCS file: /home/ncvs/src/usr.bin/tee/Makefile,v
retrieving revision 1.4
diff -U2 -r1.4 Makefile
--- Makefile    12 Dec 2001 00:06:51 -0000      1.4
+++ Makefile    1 Nov 2007 01:41:54 -0000
@@ -3,4 +3,5 @@
 
 PROG=  tee
+WARNS= 5
 
 .include <bsd.prog.mk>
Index: tee.1
===================================================================
RCS file: /home/ncvs/src/usr.bin/tee/tee.1,v
retrieving revision 1.7
diff -U2 -r1.7 tee.1
--- tee.1       17 Jan 2005 07:44:30 -0000      1.7
+++ tee.1       1 Nov 2007 01:41:54 -0000
@@ -45,4 +45,6 @@
 .Nm
 .Op Fl ai
+.Op Ar -t|u host port
+.Op Ar -d descriptor
 .Op Ar
 .Sh DESCRIPTION
@@ -58,8 +60,19 @@
 Append the output to the files rather than
 overwriting them.
+.It Fl d Ar descriptor
+Output into the already opened file-descriptor, such as 2 (stderr).
+This option can be specified multiple times.
 .It Fl i
 Ignore the
 .Dv SIGINT
 signal.
+.It Fl u|t Ar host port
+Connect to the specified host and port combination and send the
+data into the UDP
+.Pf ( Fl u )
+or TCP
+.Pf ( Fl t )
+socket. Be careful with UDP -- the sending might fail silently.
+These options can be specified multiple times.
 .El
 .Pp
@@ -77,4 +90,7 @@
 .Fl i
 option.
+.Sh SEE ALSO
+.Xr cat 1 ,
+.Xr getaddrinfo 3
 .Sh EXIT STATUS
 .Ex -std
Index: tee.c
===================================================================
RCS file: /home/ncvs/src/usr.bin/tee/tee.c,v
retrieving revision 1.10
diff -U2 -r1.10 tee.c
--- tee.c       4 Sep 2002 23:29:07 -0000       1.10
+++ tee.c       1 Nov 2007 01:41:54 -0000
@@ -54,4 +54,7 @@
 #include <stdlib.h>
 #include <string.h>
+#include <sysexits.h>
+#include <sys/socket.h>
+#include <netdb.h>
 #include <unistd.h>
 
@@ -63,6 +66,7 @@
 LIST *head;
 
-void add(int, const char *);
-static void usage(void);
+static void add(int, const char *);
+static int opensocket(int udportcp, const char *host, const char *port);
+static void usage(int code);
 
 int
@@ -77,5 +81,7 @@
 
        append = 0;
-       while ((ch = getopt(argc, argv, "ai")) != -1)
+
+       add(STDOUT_FILENO, "stdout");
+       while ((ch = getopt(argc, argv, "hd:t:u:ai")) != -1)
                switch((char)ch) {
                case 'a':
@@ -85,7 +91,23 @@
                        (void)signal(SIGINT, SIG_IGN);
                        break;
-               case '?':
+               case 'd':
+                       fd = (int)strtol(optarg, &bp, 0);
+                       if (bp[0] != '\0' || fd == STDIN_FILENO) {
+                               warnx("%s is not a valid file descriptor",
+                                   optarg);
+                               exitval = 1;
+                       } else
+                               add(fd, optarg);
+                       break;
+               case 'u':
+               case 't':
+                       fd = opensocket(ch, optarg, argv[optind++]);
+                       if (fd < 0)
+                               exitval = 1;
+                       else
+                               add(fd, optarg);
+                       break;
                default:
-                       usage();
+                       usage((char)ch == 'h' ? EX_OK : EX_USAGE);
                }
        argv += optind;
@@ -95,6 +117,4 @@
                err(1, "malloc");
 
-       add(STDOUT_FILENO, "stdout");
-
        for (exitval = 0; *argv; ++argv)
                if ((fd = open(*argv, append ? O_WRONLY|O_CREAT|O_APPEND :
@@ -124,11 +144,12 @@
 
 static void
-usage(void)
+usage(int code)
 {
-       (void)fprintf(stderr, "usage: tee [-ai] [file ...]\n");
-       exit(1);
+       (void)fprintf(stderr, "usage: tee [-ai] [-d fd] "
+           "[-{u|t} host port] [file ...]\n");
+       exit(code);
 }
 
-void
+static void
 add(int fd, const char *name)
 {
@@ -142,2 +163,38 @@
        head = p;
 }
+
+static int
+opensocket(int type, const char *host, const char *port)
+{
+       int error, s = -1;
+       struct addrinfo *res0, *res, hints = {
+               .ai_socktype = (char)type == 'u' ?
+                   SOCK_DGRAM : SOCK_STREAM,
+               .ai_family = PF_UNSPEC
+       };
+
+       error = getaddrinfo(host, port, &hints, &res0);
+       if (error) {
+               warnx("resolving %s %s: %s", host, port,
+                   gai_strerror(error));
+               return -1;
+       }
+
+       for (res = res0; res; res = res->ai_next) {
+               s = socket(res->ai_family, res->ai_socktype,
+                   res->ai_protocol);
+               if (s < 0)
+                       continue;
+
+               if (connect(s, res->ai_addr, res->ai_addrlen) < 0) {
+                       s = -1;
+                       continue;
+               }
+               break;
+       }
+
+       freeaddrinfo(res0);
+       if (s < 0)
+               warn("connecting to %s %s failed. Last error", host, port);
+       return s;
+}