[BACK]Return to svr4_socket.c CVS log [TXT][DIR] Up to [local] / sys / compat / svr4

Annotation of sys/compat/svr4/svr4_socket.c, Revision 1.1.1.1

1.1       nbrk        1: /*     $OpenBSD: svr4_socket.c,v 1.5 2006/03/05 21:48:56 miod Exp $    */
                      2: /*     $NetBSD: svr4_socket.c,v 1.4 1997/07/21 23:02:37 christos Exp $ */
                      3:
                      4: /*
                      5:  * Copyright (c) 1996 Christos Zoulas.  All rights reserved.
                      6:  *
                      7:  * Redistribution and use in source and binary forms, with or without
                      8:  * modification, are permitted provided that the following conditions
                      9:  * are met:
                     10:  * 1. Redistributions of source code must retain the above copyright
                     11:  *    notice, this list of conditions and the following disclaimer.
                     12:  * 2. Redistributions in binary form must reproduce the above copyright
                     13:  *    notice, this list of conditions and the following disclaimer in the
                     14:  *    documentation and/or other materials provided with the distribution.
                     15:  * 3. All advertising materials mentioning features or use of this software
                     16:  *    must display the following acknowledgement:
                     17:  *     This product includes software developed by Christos Zoulas.
                     18:  * 4. The name of the author may not be used to endorse or promote products
                     19:  *    derived from this software without specific prior written permission.
                     20:  *
                     21:  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
                     22:  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
                     23:  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
                     24:  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
                     25:  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
                     26:  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
                     27:  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
                     28:  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
                     29:  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
                     30:  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
                     31:  */
                     32:
                     33: /*
                     34:  * In SVR4 unix domain sockets are referenced sometimes
                     35:  * (in putmsg(2) for example) as a [device, inode] pair instead of a pathname.
                     36:  * Since there is no iname() routine in the kernel, and we need access to
                     37:  * a mapping from inode to pathname, we keep our own table. This is a simple
                     38:  * linked list that contains the pathname, the [device, inode] pair, the
                     39:  * file corresponding to that socket and the process. When the
                     40:  * socket gets closed we remove the item from the list. The list gets loaded
                     41:  * every time a stat(2) call finds a socket.
                     42:  */
                     43:
                     44: #include <sys/param.h>
                     45: #include <sys/kernel.h>
                     46: #include <sys/systm.h>
                     47: #include <sys/queue.h>
                     48: #include <sys/mbuf.h>
                     49: #include <sys/file.h>
                     50: #include <sys/mount.h>
                     51: #include <sys/socket.h>
                     52: #include <sys/socketvar.h>
                     53: #include <sys/syscallargs.h>
                     54: #include <sys/un.h>
                     55: #include <sys/stat.h>
                     56:
                     57: #include <compat/svr4/svr4_types.h>
                     58: #include <compat/svr4/svr4_util.h>
                     59: #include <compat/svr4/svr4_socket.h>
                     60: #include <compat/svr4/svr4_signal.h>
                     61: #include <compat/svr4/svr4_sockmod.h>
                     62: #include <compat/svr4/svr4_syscallargs.h>
                     63:
                     64: struct svr4_sockcache_entry {
                     65:        struct proc *p;         /* Process for the socket               */
                     66:        void *cookie;           /* Internal cookie used for matching    */
                     67:        struct sockaddr_un sock;/* Pathname for the socket              */
                     68:        dev_t dev;              /* Device where the socket lives on     */
                     69:        ino_t ino;              /* Inode where the socket lives on      */
                     70:        TAILQ_ENTRY(svr4_sockcache_entry) entries;
                     71: };
                     72:
                     73: static TAILQ_HEAD(svr4_sockcache_head, svr4_sockcache_entry) svr4_head;
                     74: static int initialized = 0;
                     75:
                     76: struct sockaddr_un *
                     77: svr4_find_socket(p, fp, dev, ino)
                     78:        struct proc *p;
                     79:        struct file *fp;
                     80:        dev_t dev;
                     81:        ino_t ino;
                     82: {
                     83:        struct svr4_sockcache_entry *e;
                     84:        void *cookie = ((struct socket *) fp->f_data)->so_internal;
                     85:
                     86:        if (!initialized) {
                     87:                DPRINTF(("svr4_find_socket: uninitialized [%p,%d,%d]\n",
                     88:                    p, dev, ino));
                     89:                TAILQ_INIT(&svr4_head);
                     90:                initialized = 1;
                     91:                return NULL;
                     92:        }
                     93:
                     94:
                     95:        DPRINTF(("svr4_find_socket: [%p,%d,%d]: ", p, dev, ino));
                     96:        TAILQ_FOREACH(e, &svr4_head, entries)
                     97:                if (e->p == p && e->dev == dev && e->ino == ino) {
                     98: #ifdef DIAGNOSTIC
                     99:                        if (e->cookie != NULL && e->cookie != cookie)
                    100:                                panic("svr4 socket cookie mismatch");
                    101: #endif
                    102:                        e->cookie = cookie;
                    103:                        DPRINTF(("%s\n", e->sock.sun_path));
                    104:                        return &e->sock;
                    105:                }
                    106:
                    107:        DPRINTF(("not found\n"));
                    108:        return NULL;
                    109: }
                    110:
                    111:
                    112: void
                    113: svr4_delete_socket(p, fp)
                    114:        struct proc *p;
                    115:        struct file *fp;
                    116: {
                    117:        struct svr4_sockcache_entry *e;
                    118:        void *cookie = ((struct socket *) fp->f_data)->so_internal;
                    119:
                    120:        if (!initialized) {
                    121:                TAILQ_INIT(&svr4_head);
                    122:                initialized = 1;
                    123:                return;
                    124:        }
                    125:
                    126:        TAILQ_FOREACH(e, &svr4_head, entries)
                    127:                if (e->p == p && e->cookie == cookie) {
                    128:                        TAILQ_REMOVE(&svr4_head, e, entries);
                    129:                        DPRINTF(("svr4_delete_socket: %s [%p,%d,%d]\n",
                    130:                                 e->sock.sun_path, p, e->dev, e->ino));
                    131:                        free(e, M_TEMP);
                    132:                        return;
                    133:                }
                    134: }
                    135:
                    136:
                    137: int
                    138: svr4_add_socket(p, path, st)
                    139:        struct proc *p;
                    140:        const char *path;
                    141:        struct stat *st;
                    142: {
                    143:        struct svr4_sockcache_entry *e;
                    144:        size_t len;
                    145:        int error;
                    146:
                    147:        if (!initialized) {
                    148:                TAILQ_INIT(&svr4_head);
                    149:                initialized = 1;
                    150:        }
                    151:
                    152:        e = malloc(sizeof(*e), M_TEMP, M_WAITOK);
                    153:        e->cookie = NULL;
                    154:        e->dev = st->st_dev;
                    155:        e->ino = st->st_ino;
                    156:        e->p = p;
                    157:
                    158:        if ((error = copyinstr(path, e->sock.sun_path,
                    159:            sizeof(e->sock.sun_path), &len)) != 0) {
                    160:                DPRINTF(("svr4_add_socket: copyinstr failed %d\n", error));
                    161:                free(e, M_TEMP);
                    162:                return error;
                    163:        }
                    164:
                    165:        e->sock.sun_family = AF_UNIX;
                    166:        e->sock.sun_len = len;
                    167:
                    168:        TAILQ_INSERT_HEAD(&svr4_head, e, entries);
                    169:        DPRINTF(("svr4_add_socket: %s [%p,%d,%d]\n", e->sock.sun_path,
                    170:                 p, e->dev, e->ino));
                    171:        return 0;
                    172: }
                    173:
                    174:
                    175: int
                    176: svr4_sys_socket(p, v, retval)
                    177:        struct proc *p;
                    178:        void *v;
                    179:        register_t *retval;
                    180: {
                    181:        struct svr4_sys_socket_args *uap = v;
                    182:
                    183:        switch (SCARG(uap, type)) {
                    184:        case SVR4_SOCK_DGRAM:
                    185:                SCARG(uap, type) = SOCK_DGRAM;
                    186:                break;
                    187:
                    188:        case SVR4_SOCK_STREAM:
                    189:                SCARG(uap, type) = SOCK_STREAM;
                    190:                break;
                    191:
                    192:        case SVR4_SOCK_RAW:
                    193:                SCARG(uap, type) = SOCK_RAW;
                    194:                break;
                    195:
                    196:        case SVR4_SOCK_RDM:
                    197:                SCARG(uap, type) = SOCK_RDM;
                    198:                break;
                    199:
                    200:        case SVR4_SOCK_SEQPACKET:
                    201:                SCARG(uap, type) = SOCK_SEQPACKET;
                    202:                break;
                    203:        default:
                    204:                return EINVAL;
                    205:        }
                    206:        return sys_socket(p, uap, retval);
                    207: }

CVSweb