Annotation of embedaddon/tmux/osdep-openbsd.c, revision 1.1.1.1

1.1       misho       1: /* $OpenBSD$ */
                      2: 
                      3: /*
                      4:  * Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
                      5:  *
                      6:  * Permission to use, copy, modify, and distribute this software for any
                      7:  * purpose with or without fee is hereby granted, provided that the above
                      8:  * copyright notice and this permission notice appear in all copies.
                      9:  *
                     10:  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
                     11:  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
                     12:  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
                     13:  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
                     14:  * WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
                     15:  * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
                     16:  * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
                     17:  */
                     18: 
                     19: #include <sys/param.h> /* MAXCOMLEN */
                     20: #include <sys/types.h>
                     21: #include <sys/proc.h>
                     22: #include <sys/sysctl.h>
                     23: #include <sys/stat.h>
                     24: 
                     25: #include <errno.h>
                     26: #include <event.h>
                     27: #include <stdlib.h>
                     28: #include <string.h>
                     29: #include <unistd.h>
                     30: 
                     31: #ifndef nitems
                     32: #define nitems(_a) (sizeof((_a)) / sizeof((_a)[0]))
                     33: #endif
                     34: 
                     35: #define is_runnable(p) \
                     36:        ((p)->p_stat == SRUN || (p)->p_stat == SIDL || (p)->p_stat == SONPROC)
                     37: #define is_stopped(p) \
                     38:        ((p)->p_stat == SSTOP || (p)->p_stat == SDEAD)
                     39: 
                     40: static struct kinfo_proc *cmp_procs(struct kinfo_proc *, struct kinfo_proc *);
                     41: char                    *osdep_get_name(int, char *);
                     42: char                    *osdep_get_cwd(int);
                     43: struct event_base       *osdep_event_init(void);
                     44: 
                     45: static struct kinfo_proc *
                     46: cmp_procs(struct kinfo_proc *p1, struct kinfo_proc *p2)
                     47: {
                     48:        if (is_runnable(p1) && !is_runnable(p2))
                     49:                return (p1);
                     50:        if (!is_runnable(p1) && is_runnable(p2))
                     51:                return (p2);
                     52: 
                     53:        if (is_stopped(p1) && !is_stopped(p2))
                     54:                return (p1);
                     55:        if (!is_stopped(p1) && is_stopped(p2))
                     56:                return (p2);
                     57: 
                     58:        if (p1->p_estcpu > p2->p_estcpu)
                     59:                return (p1);
                     60:        if (p1->p_estcpu < p2->p_estcpu)
                     61:                return (p2);
                     62: 
                     63:        if (p1->p_slptime < p2->p_slptime)
                     64:                return (p1);
                     65:        if (p1->p_slptime > p2->p_slptime)
                     66:                return (p2);
                     67: 
                     68:        if ((p1->p_flag & P_SINTR) && !(p2->p_flag & P_SINTR))
                     69:                return (p1);
                     70:        if (!(p1->p_flag & P_SINTR) && (p2->p_flag & P_SINTR))
                     71:                return (p2);
                     72: 
                     73:        if (strcmp(p1->p_comm, p2->p_comm) < 0)
                     74:                return (p1);
                     75:        if (strcmp(p1->p_comm, p2->p_comm) > 0)
                     76:                return (p2);
                     77: 
                     78:        if (p1->p_pid > p2->p_pid)
                     79:                return (p1);
                     80:        return (p2);
                     81: }
                     82: 
                     83: char *
                     84: osdep_get_name(int fd, char *tty)
                     85: {
                     86:        int              mib[6] = { CTL_KERN, KERN_PROC, KERN_PROC_PGRP, 0,
                     87:                                    sizeof(struct kinfo_proc), 0 };
                     88:        struct stat      sb;
                     89:        size_t           len;
                     90:        struct kinfo_proc *buf, *newbuf, *bestp;
                     91:        u_int            i;
                     92:        char            *name;
                     93: 
                     94:        buf = NULL;
                     95: 
                     96:        if (stat(tty, &sb) == -1)
                     97:                return (NULL);
                     98:        if ((mib[3] = tcgetpgrp(fd)) == -1)
                     99:                return (NULL);
                    100: 
                    101: retry:
                    102:        if (sysctl(mib, nitems(mib), NULL, &len, NULL, 0) == -1)
                    103:                goto error;
                    104:        len = (len * 5) / 4;
                    105: 
                    106:        if ((newbuf = realloc(buf, len)) == NULL)
                    107:                goto error;
                    108:        buf = newbuf;
                    109: 
                    110:        mib[5] = (int)(len / sizeof(struct kinfo_proc));
                    111:        if (sysctl(mib, nitems(mib), buf, &len, NULL, 0) == -1) {
                    112:                if (errno == ENOMEM)
                    113:                        goto retry;
                    114:                goto error;
                    115:        }
                    116: 
                    117:        bestp = NULL;
                    118:        for (i = 0; i < len / sizeof (struct kinfo_proc); i++) {
                    119:                if ((dev_t)buf[i].p_tdev != sb.st_rdev)
                    120:                        continue;
                    121:                if (bestp == NULL)
                    122:                        bestp = &buf[i];
                    123:                else
                    124:                        bestp = cmp_procs(&buf[i], bestp);
                    125:        }
                    126: 
                    127:        name = NULL;
                    128:        if (bestp != NULL)
                    129:                name = strdup(bestp->p_comm);
                    130: 
                    131:        free(buf);
                    132:        return (name);
                    133: 
                    134: error:
                    135:        free(buf);
                    136:        return (NULL);
                    137: }
                    138: 
                    139: char *
                    140: osdep_get_cwd(int fd)
                    141: {
                    142:        int             name[] = { CTL_KERN, KERN_PROC_CWD, 0 };
                    143:        static char     path[MAXPATHLEN];
                    144:        size_t          pathlen = sizeof path;
                    145: 
                    146:        if ((name[2] = tcgetpgrp(fd)) == -1)
                    147:                return (NULL);
                    148:        if (sysctl(name, 3, path, &pathlen, NULL, 0) != 0)
                    149:                return (NULL);
                    150:        return (path);
                    151: }
                    152: 
                    153: struct event_base *
                    154: osdep_event_init(void)
                    155: {
                    156:        return (event_init());
                    157: }

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>