1: /*
   2:  * Cary 118c Spectrophotometer Driver
   3:  *
   4:  * WFJ 19-AUG-78
   5:  * wfj 8 mar 80 (rewritten for version 7)
   6:  */
   7: 
   8: /*
   9:  *	SCCS id	@(#)cary.c	2.1 (Berkeley)	8/5/83
  10:  */
  11: 
  12: /* #define debug */
  13: 
  14: #include "param.h"
  15: #include <sys/conf.h>
  16: #include <sys/dir.h>
  17: #include <sys/user.h>
  18: #include <sys/tty.h>
  19: 
  20: #define PRI (PZERO+1)           /*user's wait priority */
  21: #define NELEMENTS   32      /* depth of internal buffer q */
  22: 
  23: /* states */
  24: #define OPEN    1
  25: #define DATAQ   2
  26: #define DATAZ   4
  27: #define OVERRUN 010
  28: 
  29: /* device bits */
  30: #define DATAINTS 1
  31: #define SWINTS   2
  32: #define LITE     4
  33: #define MODE_MSK 0400
  34: #define TENK_MSK 0200
  35: #define START_MSK 01000
  36: #define OVERANGE 02000
  37: #define READY    04000
  38: #define SIGN_MSK 0100000
  39: 
  40: #define DEFAULT 200L        /* default sample freq. */
  41: 
  42: struct cary118
  43: {
  44:     int state;
  45:     union {
  46:         long    freq;
  47:         int w[2];
  48:     }   frun;
  49:     long    count;
  50:     int head,tail;  /* ring buffer pointers */
  51:     int buffer[NELEMENTS];
  52: #ifdef debug
  53:     unsigned notready;
  54:     unsigned ovflow;
  55: #endif
  56: }   cary;
  57: 
  58: struct device
  59: {
  60:     int data;       /* read-only */
  61:     int csr;        /* no read-modify-write instructions (rmw)*/
  62: };
  63: 
  64: struct device *CARYADDR = ((struct device*)0160040);
  65: /* note: the carlock board has data & switch interrupts at 270 & 274 */
  66: 
  67: caryattach(addr, unit)
  68: struct device *addr;
  69: {
  70:     if (unit != 0)
  71:         return(0);
  72:     CARYADDR = addr;
  73:     return(1);
  74: }
  75: 
  76: caryopen()
  77: {
  78:     if ((CARYADDR == (struct device *) NULL) || cary.state)
  79:     {
  80:         u.u_error = ENXIO;
  81:         return;
  82:     }
  83:     cary.state = OPEN;
  84:     CARYADDR->csr = SWINTS;
  85:     cary.count = 0L;
  86:     cary.frun.freq = DEFAULT;
  87:     cary.head = cary.tail = 0;
  88: }
  89: 
  90: caryclose()
  91: {
  92:     CARYADDR->csr = 0;
  93:     cary.state = 0;
  94: }
  95: 
  96: caryioctl(dev,cmd,addr,flag)
  97: dev_t   dev;
  98: int cmd;
  99: register caddr_t addr;
 100: int flag;
 101: {
 102:     register x,y;
 103: 
 104:     switch(cmd)
 105:     {
 106: 
 107:     /* get status */
 108:     case ('c'<<8)+0:
 109:         suword(addr, CARYADDR->csr);
 110:         addr += 2;
 111:         suword(addr,cary.frun.w[0]);
 112:         addr += 2;
 113:         suword(addr,cary.frun.w[1]);
 114:         addr += 2;
 115:         suword(addr,cary.state);
 116:         return;
 117: 
 118:     /* set sample frequency/rate */
 119:     case ('c'<<8)+1:
 120:         addr += 2;
 121:         x = fuword(addr);
 122:         addr += 2;
 123:         y = fuword(addr);
 124:         if (x == -1 || y == -1)
 125:         {
 126:             u.u_error = EFAULT;
 127:             return;
 128:         }
 129:         cary.frun.w[0] = x; cary.frun.w[1] = y;
 130:         return;
 131: 
 132:     default:
 133:         u.u_error = ENOTTY;
 134:         return;
 135:     }
 136: }
 137: 
 138: caryread()
 139: {
 140:     union
 141:     {
 142:         int w;
 143:         char b[2];
 144:     }   w;
 145: 
 146:     do
 147:     {
 148:         while (cary.head == cary.tail)
 149:         {
 150:             if ((cary.state & OPEN) == 0)
 151:                 return;
 152:             sleep((caddr_t)&cary, PRI);
 153:         }
 154:         w.w = cary.buffer[cary.tail];
 155:         cary.tail = ++cary.tail % NELEMENTS;
 156:     } while ( (passc(w.b[0])>=0) && (passc(w.b[1])>=0));
 157: 
 158: }
 159: 
 160: caryswint()
 161: {
 162:     register m;
 163: 
 164:     if(!cary.state)
 165:     {
 166:         CARYADDR->csr = 0;
 167:         return;
 168:     }
 169:     m = CARYADDR->csr & START_MSK;
 170:     if( m && (cary.state & DATAQ) == 0)
 171:     {   /* allow data accquisition (interrupts) */
 172:         cary.state |= DATAQ;
 173:         CARYADDR->csr = DATAINTS | SWINTS | LITE;
 174:         return;
 175:     }
 176:     if( m == 0 && (cary.state & DATAQ))
 177:     {   /* disable accquisition */
 178:         cary.state &= ~OPEN;
 179:         CARYADDR->csr = 0;
 180:         wakeup((caddr_t)&cary);
 181:         return;
 182:     }
 183: }
 184: 
 185: carydataint()
 186: {
 187:     register int data, val, x;
 188:     if(--cary.count <= 0)
 189:     { /* take data */
 190:         if( (cary.state & OPEN) == 0)
 191:         {
 192:             CARYADDR->csr = 0;
 193:             return;
 194:         }
 195:         cary.count = cary.frun.freq;
 196:         data = CARYADDR->data;
 197:         val = 0;
 198:         /*
 199: 		 * Convert bcd to binary
 200: 		 */
 201: 
 202:         for(x = 12;x >= 0; x -= 4)
 203:             val = 10 * val + (017 & (data >> x));
 204:         data = CARYADDR->csr;
 205: #ifdef debug
 206:         if (!data&READY)
 207:             cary.notready++;
 208: #endif
 209:         if (data & TENK_MSK)
 210:             val += 10000;
 211:         if(!(data & SIGN_MSK))val = -val;
 212:         cary.buffer[cary.head] = val;
 213:         cary.head = ++cary.head % NELEMENTS;
 214:         if (cary.head == cary.tail) {
 215:             printf("Ring buffer overflow!\n");
 216:             cary.state |= OVERRUN;
 217: #ifdef debug
 218:             cary.ovflow++;
 219: #endif
 220:         }
 221: 
 222:         /*
 223: 		 * This blinks the indicator lamp at the data rate.
 224: 		 * (its this complicated cause csr can't do rmw cycles.
 225: 		 *  thus no csr ^= LITE...)
 226: 		 */
 227: 
 228:         if (cary.state & DATAZ)
 229:             CARYADDR->csr = SWINTS|DATAINTS|LITE;
 230:         else
 231:             CARYADDR->csr = SWINTS|DATAINTS;
 232:         cary.state ^= DATAZ;
 233:         wakeup((caddr_t)&cary);
 234:     }
 235: }

Defined functions

caryattach defined in line 67; never used
caryclose defined in line 90; never used
carydataint defined in line 185; never used
caryioctl defined in line 96; never used
caryopen defined in line 76; never used
caryread defined in line 138; never used
caryswint defined in line 160; never used

Defined variables

CARYADDR defined in line 64; used 14 times
cary defined in line 56; used 42 times

Defined struct's

cary118 defined in line 42; never used
device defined in line 58; used 8 times

Defined macros

DATAINTS defined in line 30; used 3 times
DATAQ defined in line 25; used 3 times
DATAZ defined in line 26; used 2 times
DEFAULT defined in line 40; used 1 times
  • in line 86
LITE defined in line 32; used 2 times
MODE_MSK defined in line 33; never used
NELEMENTS defined in line 21; used 3 times
OPEN defined in line 24; used 4 times
OVERANGE defined in line 36; never used
OVERRUN defined in line 27; used 1 times
PRI defined in line 20; used 1 times
READY defined in line 37; used 1 times
SIGN_MSK defined in line 38; used 1 times
START_MSK defined in line 35; used 1 times
SWINTS defined in line 31; used 4 times
TENK_MSK defined in line 34; used 1 times
Last modified: 1984-02-18
Generated: 2016-12-26
Generated by src2html V0.67
page hit count: 1182
Valid CSS Valid XHTML 1.0 Strict