v04i036: ringback getty for sharing a phone line

Jon Zeeff zeeff at b-tech.UUCP
Fri Aug 26 04:19:00 AEST 1988


Posting-number: Volume 4, Issue 36
Submitted-by: "Jon Zeeff" <zeeff at b-tech.UUCP>
Archive-name: ringback

[People, *please* "shar" your submissions!!!!!

Apologies for the delay; "jetroff" was clogging the pipes.  It will probably
start going out on September 6.  ++bsa]

#! /bin/sh
echo x - ringback.c
sed 's/^X//' << \EOF > ringback.c
X/*
X
XRingback.c V1.3
X
XThis program implements a ring-back system that allows a phone line 
Xthat is normally used as a voice line and a dial-out data line to be 
Xused as a limited dial-in data and voice line.  It does not interfere 
Xwith the use of the line for an answering machine.  
X
XIt solves a problem for my situation:
X
X1) I am normally in my office.  The phone line is used for dial-out via
Xmodem and dial-in/dial-out voice traffic.
X
X2) I sometimes travel, at which time I connect an answering machine to
Xthe line.  
X
X3) I'd like to be able to call in to my system via modem when I am 
Xtravelling, without interfering with others use of my answering 
Xmachine.  
X
X4) I don't want to pay for another phone line.
X
XThis program functions by watching a tty port for an incoming call on 
Xa smart modem.  Forty seconds after an incoming call, it will spawn a 
Xgetty on the line.  If no one calls and logs in, the getty will be 
Xkilled by an uncaught alarm and the line will be set back to a no 
Xanswer state.  
X
XThis implements a ringback dialin system.  Just call, wait a minute,
Xand call again. 
X
XIf the program notices that a user (uucp or kermit) is using the line 
Xfor an outgoing call, it will back off until that call is completed.  
X(Note: the first modem response char will be eaten.  Uucp dialing scripts 
Xshould be set up to tolerate this.) 
X
XWritten for Sys V.3 and HDB uucp (but easily modified for others)
X
XTwo arguments must be present - tty and type
X
XSample lines from /etc/inittab:
X     rb:1234:respawn:/etc/ringback tty1 1200
X
XMake sure that you trust the people who are allowed to login on this 
Xline.  It is possible for them to dial-out on the line.  
X
XTo install:
X
X1) Edit TTYID and TTYGID and UUGETTY.
X2) Compile and install as /etc/ringback
X3) Create an initab line like the above one.
X
X 				- Jon Zeeff (umix!b-tech!zeeff)
X
XThis program is in the public domain.
X
X*/
X
X#include <stdio.h>
X#include <sys/types.h>
X#include <sys/stat.h>
X#include <signal.h>
X#include <fcntl.h>
X#include <termio.h>
X
Xchar *strcpy();
Xchar *strcat();
Xunsigned sleep();
Xunsigned alarm();
Xvoid exit();
X
X/* the id and gid for normal ownership of tty lines (usually uucp) */
X
X#define TTYID		5	/* uucp */
X#define TTYGID		11	/* staff */
X
X/* if you have a getty/tty/modem combination that doesn't get in a babbling
X   getty loop, then there is no need to define this.  If you do, make sure
X   that /etc/uugetty exists.
X*/ 
X#define UUGETTY		/* #define UUGETTY */
X
Xmain(argc,argv)
Xint argc;
Xchar **argv;
X{
X
Xchar c;
XFILE *tty0,*tty1,*tty2;
X#ifdef DEBUG
XFILE *console;
X#endif
XFILE *tty;
XFILE *lock;
Xstruct termio ttymodes;
Xstruct stat buf;
Xchar tty_lock[100];
Xchar tty_name[100];
Xint i;
X
X/* name and location of tty locks - change this as needed */
X
Xstrcpy(tty_lock,"/usr/spool/locks/LCK.."); 
Xstrcat(tty_lock,argv[1]);
X
Xstrcpy(tty_name,"/dev/");
Xstrcat(tty_name,argv[1]);
X
Xif (argc != 3) exit(2);
X
Xunlink(tty_lock);
Xumask(022);
X
Xsignal(SIGHUP,SIG_IGN);
Xsignal(SIGINT,SIG_IGN);
Xsignal(SIGQUIT,SIG_IGN);
Xsignal(SIGTERM,SIG_IGN);
X
Xfor (;;) {
X   
X      /* Set the line permissions, owner, and group for dial-out use */
X   
X      chown(tty_name,TTYID,TTYGID);
X      chmod(tty_name,0660);
X   
X      /* Open line - getty will close the first 3, so make sure we are #4 */
X      /* so that the modem doesn't get reset on dtr drop and our autoanswer */
X      /* setting don't get undone. */
X
X      tty0 = fopen(tty_name,"r+");
X      tty1 = fopen(tty_name,"r+");
X      tty2 = fopen(tty_name,"r+");
X      tty = fopen(tty_name,"r+");
X
X      fclose(tty0); fclose(tty1); fclose(tty2);
X
X#ifdef DEBUG
Xconsole = fopen("/dev/console","w");
Xfprintf(console,"check 1\n"); fflush(console);
X#endif
X
X      ttymodes.c_iflag = 0;
X      ttymodes.c_oflag = NL1 | CR3;
X      ttymodes.c_cflag = 0; 
X      ttymodes.c_lflag = 0;
X      ttymodes.c_line = 0;
X      for (i = 0; i < NCC; ++i) ttymodes.c_cc[i] = 0; 
X      ttymodes.c_cc[VMIN] = 1;		/* min number of characters */
X      ttymodes.c_cc[VTIME] = 0;     	/* no max time before return */
X      ioctl(fileno(tty),TCSETA,&ttymodes);  /* hang up the line */
X      sleep(1);
X      ttymodes.c_cflag = B1200 | CS8 | CREAD | HUPCL; 
X      ioctl(fileno(tty),TCSETA,&ttymodes);
X      sleep(1);
X#ifdef DEBUG
Xfprintf(console,"check 1.3\n"); fflush(console);
X#endif
X   
X      /* setup the modem */
X   
X      fputs("AT\r",tty); fflush(tty); sleep(1);  
X      fputs("ATZ\r",tty); fflush(tty); sleep(2);  
X      fputs("ATS0=0\r",tty); fflush(tty); sleep(1);  /* Don't answer phone */
X      fputs("ATE0\r",tty); fflush(tty); sleep(1);
X      fputs("ATV0\r",tty); fflush(tty); sleep(1);
X      fputs("ATQ0\r",tty); fflush(tty); sleep(1);
X   
X#ifdef DEBUG
Xfprintf(console,"check 2\n"); fflush(console);
X#endif
X      fcntl(fileno(tty),F_SETFL,O_NDELAY);    /* Set to nonblocking reads */
X      while (read(fileno(tty),&c,(unsigned)1) == 1);   /* Flush input */
X      fcntl(fileno(tty),F_SETFL,O_RDWR);      /* Set to blocking reads */
X   
X      /* Wait for incoming call ('2') or other usage (uucp or user) */
X   
X      /* Get char from tty port */
X
X      while (read(fileno(tty),&c,(unsigned)1) != 1);
X
X      /* 
X         If we receive a '2' and no lock file is present, we can be sure
X         that it is not someone calling out.
X      */   
X
X#ifdef DEBUG
Xfprintf(console,"check 2.5 %d\n",c); fflush(console);
X#endif
X
X      if ((c&0x7f) == '2' && stat(tty_lock,&buf) == -1) {	
X
X	      /* create a hdb style lock file */
X
X              lock = fopen(tty_lock,"w");
X      	      if (lock) {
X      	         fprintf(lock,"%10.10d\n",(int)getpid());
X      	         fclose(lock);
X   	      }
X
X	      /* wait for this call to end */
X     
X              sleep(32);    /* should be long enough for answering machine
X			       to answer if they let it ring. */
X  
X	      /* Setup modem for incoming call */
X 
X              fputs("AT\r",tty);fflush(tty);sleep(1);
X              fputs("ATZ\r",tty);fflush(tty);sleep(1);
X              fputs("ATQ1\r",tty);fflush(tty);sleep(1); 
X              fputs("ATS0=1\r",tty);fflush(tty);sleep(5);
X
X#ifdef DEBUG
Xfprintf(console,"check 4\n"); fflush(console);
X#endif
X
X      	      /* set things up so the getty will live a short life */
X 
X              alarm(120);
X 
X#ifndef UUGETTY  
X              execl("/etc/getty","getty","-t","90","-h",
X                   argv[1],argv[2],(char *)0);
X#else
X              unlink(tty_lock);
X              execl("/etc/uugetty","uugetty","-r","-h","-t","90",
X                   argv[1],argv[2],(char *)0);
X#endif
X
X#ifdef DEBUG
Xfprintf(console,"check 5\n"); fflush(console);
X#endif
X   	} else {                         /* Must be someone using line */
X   
X              fclose(tty);                 /* Release line */
X   
X              /* Loop until lock file goes away (uucp or user done) */
X    
X              do {
X                 while (stat(tty_lock,&buf) == 0) sleep(40);
X   	         sleep(40);
X   	      }  while (stat(tty_lock,&buf) == 0);
X   
X   	} /* end_if */
X   
X   } /* next */
X   
X}
EOF
exit 0
-- 
Jon Zeeff           		Branch Technology,
uunet!umix!b-tech!zeeff  	zeeff%b-tech.uucp at umix.cc.umich.edu



More information about the Comp.sources.misc mailing list