Annotation of Gnu-Mach/device/cirbuf.c, revision 1.1

1.1     ! root        1: /* 
        !             2:  * Mach Operating System
        !             3:  * Copyright (c) 1992,1991,1990 Carnegie Mellon University
        !             4:  * All Rights Reserved.
        !             5:  * 
        !             6:  * Permission to use, copy, modify and distribute this software and its
        !             7:  * documentation is hereby granted, provided that both the copyright
        !             8:  * notice and this permission notice appear in all copies of the
        !             9:  * software, derivative works or modified versions, and any portions
        !            10:  * thereof, and that both notices appear in supporting documentation.
        !            11:  * 
        !            12:  * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS"
        !            13:  * CONDITION.  CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR
        !            14:  * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
        !            15:  * 
        !            16:  * Carnegie Mellon requests users of this software to return to
        !            17:  * 
        !            18:  *  Software Distribution Coordinator  or  [email protected]
        !            19:  *  School of Computer Science
        !            20:  *  Carnegie Mellon University
        !            21:  *  Pittsburgh PA 15213-3890
        !            22:  * 
        !            23:  * any improvements or extensions that they make and grant Carnegie Mellon
        !            24:  * the rights to redistribute these changes.
        !            25:  */
        !            26: /*
        !            27:  *     Author: David B. Golub, Carnegie Mellon University
        !            28:  *     Date:   7/90
        !            29:  *
        !            30:  *     Circular buffers for TTY
        !            31:  */
        !            32: 
        !            33: #include <device/cirbuf.h>
        !            34: #include <kern/kalloc.h>
        !            35: 
        !            36: 
        !            37: 
        !            38: /* read at c_cf, write at c_cl */
        !            39: /* if c_cf == c_cl, buffer is empty */
        !            40: /* if c_cl == c_cf - 1, buffer is full */
        !            41: 
        !            42: #if    DEBUG
        !            43: int cb_check_enable = 0;
        !            44: #define        CB_CHECK(cb) if (cb_check_enable) cb_check(cb)
        !            45: 
        !            46: void
        !            47: cb_check(register struct cirbuf *cb)
        !            48: {
        !            49:        if (!(cb->c_cf >= cb->c_start && cb->c_cf < cb->c_end))
        !            50:            panic("cf %x out of range [%x..%x)",
        !            51:                cb->c_cf, cb->c_start, cb->c_end);
        !            52:        if (!(cb->c_cl >= cb->c_start && cb->c_cl < cb->c_end))
        !            53:            panic("cl %x out of range [%x..%x)",
        !            54:                cb->c_cl, cb->c_start, cb->c_end);
        !            55:        if (cb->c_cf <= cb->c_cl) {
        !            56:            if (!(cb->c_cc == cb->c_cl - cb->c_cf))
        !            57:                panic("cc %x should be %x",
        !            58:                        cb->c_cc,
        !            59:                        cb->c_cl - cb->c_cf);
        !            60:        }
        !            61:        else {
        !            62:            if (!(cb->c_cc == cb->c_end - cb->c_cf
        !            63:                            + cb->c_cl - cb->c_start))
        !            64:                panic("cc %x should be %x",
        !            65:                        cb->c_cc,
        !            66:                        cb->c_end - cb->c_cf +
        !            67:                        cb->c_cl - cb->c_start);
        !            68:        }
        !            69: }
        !            70: #else  /* DEBUG */
        !            71: #define        CB_CHECK(cb)
        !            72: #endif /* DEBUG */
        !            73: 
        !            74: /*
        !            75:  * Put one character in circular buffer.
        !            76:  */
        !            77: int putc(
        !            78:        int     c,
        !            79:        register struct cirbuf *cb)
        !            80: {
        !            81:        register char *ow, *nw;
        !            82: 
        !            83:        ow = cb->c_cl;
        !            84:        nw = ow+1;
        !            85:        if (nw == cb->c_end)
        !            86:            nw = cb->c_start;
        !            87:        if (nw == cb->c_cf)
        !            88:            return 1;           /* not entered */
        !            89:        *ow = c;
        !            90:        cb->c_cl = nw;
        !            91: 
        !            92:        cb->c_cc++;
        !            93: 
        !            94:        CB_CHECK(cb);
        !            95: 
        !            96:        return 0;
        !            97: }
        !            98: 
        !            99: /*
        !           100:  * Get one character from circular buffer.
        !           101:  */
        !           102: int getc(register struct cirbuf *cb)
        !           103: {
        !           104:        register unsigned char *nr;
        !           105:        register int    c;
        !           106: 
        !           107:        nr = (unsigned char *)cb->c_cf;
        !           108:        if (nr == (unsigned char *)cb->c_cl) {
        !           109:            CB_CHECK(cb);
        !           110:            return -1;          /* empty */
        !           111:        }
        !           112:        c = *nr;
        !           113:        nr++;
        !           114:        if (nr == (unsigned char *)cb->c_end)
        !           115:            nr = (unsigned char *)cb->c_start;
        !           116:        cb->c_cf = (char *)nr;
        !           117: 
        !           118:        cb->c_cc--;
        !           119: 
        !           120:        CB_CHECK(cb);
        !           121: 
        !           122:        return c;
        !           123: }
        !           124: 
        !           125: /*
        !           126:  * Get lots of characters.
        !           127:  * Return number moved.
        !           128:  */
        !           129: int
        !           130: q_to_b( register struct cirbuf *cb,
        !           131:        register char   *cp,
        !           132:        register int    count)
        !           133: {
        !           134:        char *          ocp = cp;
        !           135:        register int    i;
        !           136: 
        !           137:        while (count != 0) {
        !           138:            if (cb->c_cl == cb->c_cf)
        !           139:                break;          /* empty */
        !           140:            if (cb->c_cl < cb->c_cf)
        !           141:                i = cb->c_end - cb->c_cf;
        !           142:            else
        !           143:                i = cb->c_cl - cb->c_cf;
        !           144:            if (i > count)
        !           145:                i = count;
        !           146:            bcopy(cb->c_cf, cp, i);
        !           147:            cp += i;
        !           148:            count -= i;
        !           149:            cb->c_cf += i;
        !           150:            cb->c_cc -= i;
        !           151:            if (cb->c_cf == cb->c_end)
        !           152:                cb->c_cf = cb->c_start;
        !           153: 
        !           154:            CB_CHECK(cb);
        !           155:        }
        !           156:        CB_CHECK(cb);
        !           157: 
        !           158:        return cp - ocp;
        !           159: }
        !           160: 
        !           161: /*
        !           162:  * Add character array to buffer and return number of characters
        !           163:  * NOT entered.
        !           164:  */
        !           165: int
        !           166: b_to_q( register char *        cp,
        !           167:        int     count,
        !           168:        register struct cirbuf *cb)
        !           169: {
        !           170:        register int    i;
        !           171:        register char   *lim;
        !           172: 
        !           173:        while (count != 0) {
        !           174:            lim = cb->c_cf - 1;
        !           175:            if (lim < cb->c_start)
        !           176:                lim = cb->c_end - 1;
        !           177: 
        !           178:            if (cb->c_cl == lim)
        !           179:                break;
        !           180:            if (cb->c_cl < lim)
        !           181:                i = lim - cb->c_cl;
        !           182:            else
        !           183:                i = cb->c_end - cb->c_cl;
        !           184: 
        !           185:            if (i > count)
        !           186:                i = count;
        !           187:            bcopy(cp, cb->c_cl, i);
        !           188:            cp += i;
        !           189:            count -= i;
        !           190:            cb->c_cc += i;
        !           191:            cb->c_cl += i;
        !           192:            if (cb->c_cl == cb->c_end)
        !           193:                cb->c_cl = cb->c_start;
        !           194: 
        !           195:            CB_CHECK(cb);
        !           196:        }
        !           197:        CB_CHECK(cb);
        !           198:        return count;
        !           199: }
        !           200: 
        !           201: /*
        !           202:  * Return number of contiguous characters up to a character
        !           203:  * that matches the mask.
        !           204:  */
        !           205: int
        !           206: ndqb(  register struct cirbuf *cb,
        !           207:        register int    mask)
        !           208: {
        !           209:        register char *cp, *lim;
        !           210: 
        !           211:        if (cb->c_cl < cb->c_cf)
        !           212:            lim = cb->c_end;
        !           213:        else
        !           214:            lim = cb->c_cl;
        !           215:        if (mask == 0)
        !           216:            return (lim - cb->c_cf);
        !           217:        cp = cb->c_cf;
        !           218:        while (cp < lim) {
        !           219:            if (*cp & mask)
        !           220:                break;
        !           221:            cp++;
        !           222:        }
        !           223:        return (cp - cb->c_cf);
        !           224: }
        !           225: 
        !           226: /*
        !           227:  * Flush characters from circular buffer.
        !           228:  */
        !           229: void
        !           230: ndflush(register struct cirbuf *cb,
        !           231:        register int    count)
        !           232: {
        !           233:        register int    i;
        !           234: 
        !           235:        while (count != 0) {
        !           236:            if (cb->c_cl == cb->c_cf)
        !           237:                break;          /* empty */
        !           238:            if (cb->c_cl < cb->c_cf)
        !           239:                i = cb->c_end - cb->c_cf;
        !           240:            else
        !           241:                i = cb->c_cl - cb->c_cf;
        !           242:            if (i > count)
        !           243:                i = count;
        !           244:            count -= i;
        !           245:            cb->c_cf += i;
        !           246:            cb->c_cc -= i;
        !           247:            if (cb->c_cf == cb->c_end)
        !           248:                cb->c_cf = cb->c_start;
        !           249:            CB_CHECK(cb);
        !           250:        }
        !           251: 
        !           252:        CB_CHECK(cb);
        !           253: }
        !           254: 
        !           255: /*
        !           256:  * Empty a circular buffer.
        !           257:  */
        !           258: void cb_clear(struct cirbuf *cb)
        !           259: {
        !           260:        cb->c_cf = cb->c_start;
        !           261:        cb->c_cl = cb->c_start;
        !           262:        cb->c_cc = 0;
        !           263: }
        !           264: 
        !           265: /*
        !           266:  * Allocate character space for a circular buffer.
        !           267:  */
        !           268: void
        !           269: cb_alloc(
        !           270:        register struct cirbuf *cb,
        !           271:        int             buf_size)
        !           272: {
        !           273:        register char *buf;
        !           274: 
        !           275:        buf = (char *)kalloc(buf_size);
        !           276: 
        !           277:        cb->c_start = buf;
        !           278:        cb->c_end = buf + buf_size;
        !           279:        cb->c_cf = buf;
        !           280:        cb->c_cl = buf;
        !           281:        cb->c_cc = 0;
        !           282:        cb->c_hog = buf_size - 1;
        !           283: 
        !           284:        CB_CHECK(cb);
        !           285: }
        !           286: 
        !           287: /*
        !           288:  * Free character space for a circular buffer.
        !           289:  */
        !           290: void
        !           291: cb_free(register struct cirbuf *cb)
        !           292: {
        !           293:        int             size;
        !           294: 
        !           295:        size = cb->c_end - cb->c_start;
        !           296:        kfree((vm_offset_t)cb->c_start, size);
        !           297: }
        !           298: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.