1: /*
   2:  * Copyright (c) 1983 Regents of the University of California.
   3:  * All rights reserved.  The Berkeley software License Agreement
   4:  * specifies the terms and conditions for redistribution.
   5:  */
   6: 
   7: #ifndef lint
   8: static char sccsid[] = "@(#)penril.c	5.1 (Berkeley) 4/30/85";
   9: #endif not lint
  10: 
  11: /*
  12:  * Routines for calling up on a Penril Modem
  13:  * The Penril is expected to be strapped for local echo (just like uucp)
  14:  */
  15: #include "tip.h"
  16: 
  17: #define MAXRETRY    5
  18: 
  19: static  int sigALRM();
  20: static  int timeout = 0;
  21: static  jmp_buf buftimeout;
  22: 
  23: /*
  24:  * some sleep calls have been replaced by this macro
  25:  * because some penril modems require two <cr>s in less than
  26:  * a second in order to 'wake up'... yes, it is dirty...
  27:  */
  28: #define delay(num,denom) busyloop(CPUSPEED*num/denom)
  29: #define CPUSPEED 1000000    /* VAX 780 is 1MIPS */
  30: #define DELAY(n)    { register long N = (n); while (--N > 0); }
  31: busyloop(n) { DELAY(n); }
  32: 
  33: pen_dialer(num, acu)
  34:     register char *num;
  35:     char *acu;
  36: {
  37:     register char *cp;
  38:     register int connected = 0;
  39:     char *msg, *index(), line[80];
  40: 
  41:     /*
  42: 	 * Get in synch with a couple of carriage returns
  43: 	 */
  44:     if (!pensync(FD)) {
  45:         printf("can't synchronize with penril\n");
  46: #ifdef ACULOG
  47:         logent(value(HOST), num, "penril", "can't synch up");
  48: #endif
  49:         return (0);
  50:     }
  51:     if (boolean(value(VERBOSE)))
  52:         printf("\ndialing...");
  53:     fflush(stdout);
  54:     ioctl(FD, TIOCHPCL, 0);
  55:     echo("#k$\r$\n$D$I$A$L$:$ ");
  56:     for (cp = num; *cp; cp++) {
  57:         delay(1, 10);
  58:         write(FD, cp, 1);
  59:     }
  60:     delay(1, 10);
  61:     write(FD, "\r", 1);
  62:     gobble('\n', line);
  63:     if (gobble('\n', line))
  64:         connected = gobble('O', line) && gobble('K', line);
  65:     ioctl(FD, TIOCFLUSH);
  66: #ifdef ACULOG
  67:     if (timeout) {
  68:         sprintf(line, "%d second dial timeout",
  69:             number(value(DIALTIMEOUT)));
  70:         logent(value(HOST), num, "penril", line);
  71:     }
  72: #endif
  73:     if (timeout)
  74:         pen_disconnect();   /* insurance */
  75:     if (connected || timeout || !boolean(value(VERBOSE)))
  76:         return (connected);
  77:     /* call failed, parse response for user */
  78:     cp = index(line, '\r');
  79:     if (cp)
  80:         *cp = '\0';
  81:     for (cp = line; cp = index(cp, ' '); cp++)
  82:         if (cp[1] == ' ')
  83:             break;
  84:     if (cp) {
  85:         while (*cp == ' ')
  86:             cp++;
  87:         msg = cp;
  88:         while (*cp) {
  89:             if (isupper(*cp))
  90:                 *cp = tolower(*cp);
  91:             cp++;
  92:         }
  93:         printf("%s...", msg);
  94:     }
  95:     return (connected);
  96: }
  97: 
  98: pen_disconnect()
  99: {
 100: 
 101:     close(FD);
 102: }
 103: 
 104: pen_abort()
 105: {
 106: 
 107:     write(FD, "\03", 1);
 108:     close(FD);
 109: }
 110: 
 111: static int
 112: echo(s)
 113:     register char *s;
 114: {
 115:     char c;
 116: 
 117:     while (c = *s++) switch (c) {
 118: 
 119:     case '$':
 120:         read(FD, &c, 1);
 121:         s++;
 122:         break;
 123: 
 124:     case '#':
 125:         c = *s++;
 126:         write(FD, &c, 1);
 127:         break;
 128: 
 129:     default:
 130:         write(FD, &c, 1);
 131:         read(FD, &c, 1);
 132:     }
 133: }
 134: 
 135: static int
 136: sigALRM()
 137: {
 138: 
 139:     printf("\07timeout waiting for reply\n");
 140:     timeout = 1;
 141:     longjmp(buftimeout, 1);
 142: }
 143: 
 144: static int
 145: gobble(match, response)
 146:     register char match;
 147:     char response[];
 148: {
 149:     register char *cp = response;
 150:     char c;
 151:     int (*f)();
 152: 
 153:     signal(SIGALRM, sigALRM);
 154:     timeout = 0;
 155:     do {
 156:         if (setjmp(buftimeout)) {
 157:             signal(SIGALRM, f);
 158:             *cp = '\0';
 159:             return (0);
 160:         }
 161:         alarm(number(value(DIALTIMEOUT)));
 162:         read(FD, cp, 1);
 163:         alarm(0);
 164:         c = (*cp++ &= 0177);
 165: #ifdef notdef
 166:         if (boolean(value(VERBOSE)))
 167:             putchar(c);
 168: #endif
 169:     } while (c != '\n' && c != match);
 170:     signal(SIGALRM, SIG_DFL);
 171:     *cp = '\0';
 172:     return (c == match);
 173: }
 174: 
 175: #define min(a,b)    ((a)>(b)?(b):(a))
 176: /*
 177:  * This convoluted piece of code attempts to get
 178:  * the penril in sync.  If you don't have FIONREAD
 179:  * there are gory ways to simulate this.
 180:  */
 181: static int
 182: pensync(fd)
 183: {
 184:     int already = 0, nread;
 185:     long temp;
 186:     char buf[60];
 187: 
 188:     /*
 189: 	 * Toggle DTR to force anyone off that might have left
 190: 	 * the modem connected, and insure a consistent state
 191: 	 * to start from.
 192: 	 *
 193: 	 * If you don't have the ioctl calls to diddle directly
 194: 	 * with DTR, you can always try setting the baud rate to 0.
 195: 	 */
 196:     ioctl(FD, TIOCCDTR, 0);
 197:     sleep(1);
 198:     ioctl(FD, TIOCSDTR, 0);
 199:     while (already < MAXRETRY) {
 200:         /*
 201: 		 * After reseting the modem, send it two \r's to
 202: 		 * autobaud on. Make sure to delay between them
 203: 		 * so the modem can frame the incoming characters.
 204: 		 */
 205:         write(fd, "\r", 1);
 206:         sleep(2);
 207:         if (ioctl(fd, FIONREAD, &temp) < 0) {
 208:             perror("tip: ioctl");
 209:             continue;
 210:         }
 211:         nread = temp;
 212:         while (nread > 0) {
 213:             read(fd, buf, min(nread, 70));
 214:             if (((buf[nread - 6] & 0177) == 'B') &&
 215:                 ((buf[nread - 5] & 0177) == 'P') &&
 216:                 ((buf[nread - 4] & 0177) == 'S') &&
 217:                 ((buf[nread - 1] & 0177) == '>'))
 218:                 return (1);
 219:             nread -= min(nread, 70);
 220:         }
 221:         sleep(1);
 222:         already++;
 223:     }
 224:     return (0);
 225: }

Defined functions

busyloop defined in line 31; used 1 times
  • in line 28
echo defined in line 111; used 1 times
  • in line 55
gobble defined in line 144; used 4 times
pen_abort defined in line 104; never used
pen_dialer defined in line 33; never used
pen_disconnect defined in line 98; used 1 times
  • in line 74
pensync defined in line 181; used 1 times
  • in line 44
sigALRM defined in line 135; used 2 times

Defined variables

sccsid defined in line 8; never used
timeout defined in line 20; used 5 times

Defined macros

CPUSPEED defined in line 29; used 1 times
  • in line 28
DELAY defined in line 30; used 1 times
  • in line 31
MAXRETRY defined in line 17; used 1 times
delay defined in line 28; used 2 times
min defined in line 175; used 2 times
Last modified: 1987-07-11
Generated: 2016-12-26
Generated by src2html V0.67
page hit count: 3622
Valid CSS Valid XHTML 1.0 Strict