home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Usenet 1994 October
/
usenetsourcesnewsgroupsinfomagicoctober1994disk2.iso
/
unix
/
volume26
/
modempool
/
part01
/
dialup.c
< prev
next >
Wrap
C/C++ Source or Header
|
1993-04-05
|
6KB
|
267 lines
/*******************************************************************
*
* Module: @(#)dialup.c 4.2 92/04/16
*
* Description:
* Dialup routines.
*
* Revision:
* Date By Reason
* ---- -- ------
* 920309 Lars Berntzon Created
*
*******************************************************************/
static char SccsId[] = "@(#)dialup.c 4.2 92/04/16";
#include <stdio.h>
#ifndef NOSTDLIB
#include <stdlib.h>
#endif
#include <unistd.h>
#include <string.h>
#include <signal.h>
#include <fcntl.h>
#include <termios.h>
#include <ctype.h>
#include "modempool.h"
#ifdef RLOGIN
#include <pwd.h>
#endif
/*******************************************************************
*
* callback
* --------
*
* Description:
* Does the actual calling.
*
*******************************************************************/
callback(slot_t *sp)
{
struct slot free_slot;
int main_port = 0;
int fd;
int id;
int rc;
/*
* Find free available line.
*/
slot_lock();
slot_open();
while((rc = slot_traverse(&free_slot)) == E_OK) {
/* I will only use myself in last resort */
if (free_slot.pid == getpid()) {
continue;
}
/* Of cause don't use a busy server */
if (free_slot.status != SLOT_FREE) {
continue;
}
/* Maybe the port us taken by someone else, dont use it then */
if (lock_line(free_slot.line, free_slot.pid) != E_OK) {
continue;
}
/* Now a free server is found */
break;
}
/*
* Use myself if no other servers was found.
*/
if (rc != E_OK) {
debug("callback: using myself");
memcpy(&free_slot, &slot, sizeof free_slot);
}
mod_put(MSG_CALLING);
/*
* Write command to slot e.i. tell server to dial.
*/
free_slot.status = SLOT_BUSY;
strncpy(free_slot.phone, sp->phone, sizeof free_slot.phone);
strncpy(free_slot.name, sp->name, sizeof free_slot.name);
#ifdef RLOGIN
strncpy(free_slot.host, sp->host, sizeof free_slot.host);
#endif
free_slot.baud = sp->baud;
debug("calling: slotid: %d, phone: %s, name: %s, baud: %d",
free_slot.id, free_slot.phone, free_slot.name, free_slot.baud);
/*
* Write the data and unlock server database.
*/
slot_write(&free_slot);
slot_unlock();
/* Send signal to server to read its database (dont signal myself) */
if (free_slot.pid != getpid()) {
kill(free_slot.pid, SIG_SERVER);
}
else {
if ( dialup() != E_OK) {
log("dialup failed");
return E_FAIL;
}
}
return E_OK;
}
/*******************************************************************
*
* DIALUP
* ------
*
* Description:
* Dials a number for this server.
*
*******************************************************************/
dialup()
{
#ifdef RLOGIN
char name[NAME_SIZE]; /* Temporary name */
struct passwd *pw; /* Pointer to passwd struct */
#endif
int retry; /* Retry counter */
int baud = 0; /* Connected baudrate */
int rc;
/* Turn of signalled flag */
signalled = 0;
/* Hangup line before dialing */
tty_hangup();
tty_close();
/* Wait some before dialing */
sleep(DIALUP_DELAY);
/* Read baudrate and phone number to dial */
if (slot_read(&slot) != E_OK) {
logerr("dialup: failed to read slot");
return E_FAIL;
}
/* log dialing */
log("dialup: dialing #%s baud %d", slot.phone, slot.baud);
/* Open port again */
if (tty_open(portname, slot.baud, O_NDELAY) != E_OK) {
logerr("dialup: failed to open port");
return E_FAIL;
}
/* Try three times to dialup */
for(retry = 0; retry < 3; retry++)
{
/* Send modem command */
mod_put("ATDT");
mod_put(prefix);
mod_put(slot.phone);
mod_put("\r");
/* Expect connection in 20 sec */
rc = mod_exp(MOD_ANY, DIALUP_TMOUT);
debug("dial: got %d\n", rc);
switch(rc)
{
case MOD_CONNECT:
case MOD_CONNECT_300:
baud = 300;
case MOD_CONNECT_1200:
if (baud == 0) baud = 1200;
case MOD_CONNECT_2400:
if (baud == 0) baud = 2400;
case MOD_CONNECT_4800:
if (baud == 0) baud = 4800;
case MOD_CONNECT_9600:
if (baud == 0) baud = 9600;
sleep(2); /* Let modem settle */
tty_flush();
tty_local(0);
tty_baud(baud);
tty_sane();
log("dialup: connected");
mod_put("\r\n\r\n");
/*
* Mark current baudrate in the server database.
*/
slot.baud = baud;
slot_write(&slot);
#ifdef RLOGIN
/*
* Get login name.
*/
retry = 0;
do {
rc = prompt(MSG_LOGIN, name, NAME_SIZE, LOGIN_TMOUT);
} while(rc == E_OK && strlen(name) == 0);
if ((pw = getpwnam(name)) == NULL) {
mod_put(MSG_LOGINFAIL);
return E_FAIL;
}
/*
* Don't even try to login as same uid as this process.
*/
if (pw->pw_uid < 10 || pw->pw_uid == getuid()) {
log("pseudouser '%s' tried to log in as '%s'", slot.name, name);
mod_put(MSG_LOGINFAIL);
return E_FAIL;
}
#endif
/*
* Redirect port to stdin, stdout and stderr.
*/
if (tty_redirect() != E_OK) {
logerr("redirection failed");
return E_FAIL;
}
#ifdef RLOGIN
execl("/usr/ucb/rlogin", "rlogin", "-l", name, slot.host, NULL);
logerr("dialup: failed to exec rlogin");
#else
execl("/bin/login", "login", NULL);
logerr("dialup: failed to exec login");
#endif
return E_FAIL;
case MOD_NO_CARRIER:
logerr("dialup: got no carrier for number '%s'", slot.phone);
break; /* Retry */
case MOD_BUSY:
sleep(7);
break; /* Retry */
case MOD_OK:
default:
logerr("dialup: got %d from modem", rc);
break; /* Retry */
}
sleep(5);
}
/*
* Failed to dialup.
*/
return E_FAIL;
}