📄 dialer.c
字号:
ppp_close(mppp, LCP_STATE);
#endif /* USE_PPP */
modemp->upperline->ln_state = D_IDLE; /* go back to idle state */
modemp->modem_in[0] = 0;
modemp->lastdial = cticks; /* reset last activity time */
break;
}
tmo = modemp->lastdial + (60*TPS); /* last dial activity plus some seconds... */
if(tmo < cticks) /* dial timeout? */
{
modem_linedown(modemp); /* tell upper line modem is down */
modem_reset(modemp);
ConPrintf("timeout waiting for modem connect...\n");
modemp->modem_in[0] = 0;
modemp->upperline->ln_state = D_IDLE;
modemp->lastdial = cticks; /* reset last activity time */
break;
}
break; /* no connect or timeout; keep waiting */
case D_CONNECTED:
/* see if bytes have come in the UART, give to line prot if so: */
while((c = uart_getc(modemp->unit)) != -1)
{
#ifdef MDM_CHECK_NO_CARRIER
if (modem_no_carrier(modemp, c))
{
ConPrintf("NO CARRIER available on line. Reseting...\n");
no_carrier = TRUE ;
break;
}
#endif
modemp->upperline->ln_getc(modemp->upperline, c);
modemp->lastchar = cticks;
}
/* see if other guy hung up */
if(modem_DCD(modemp) || no_carrier == TRUE )
{
ConPrintf("lost carrier, cleaning up...\n");
modemp->upperline->ln_state = D_IDLE;
modemp->lastdial = cticks; /* reset last activity time */
modem_linedown(modemp); /* tell upper line modem is down */
}
/* See if we have not done any IO in a long time: */
if(modemp->IdleDialTmo != 0) /* If timeout specified... */
{
/* caclulate last character activity timeout */
tmo = modemp->lastchar + ((unsigned long)(modemp->IdleDialTmo) * TPS);
if(tmo < cticks) /* timeout? */
{
ConPrintf("Disconnecting idle modem connection\n");
modem_hangup(modemp->upperline);
}
}
break;
case D_HANGINGUP:
/* see if Data Carrier Detect line has gone down. */
if(modem_DCD(modemp)) /* See if hangup is complete */
{
modemp->upperline->ln_state = D_IDLE;
ConPrintf("hung up\n");
/* resend the init string after each hangup */
modem_cmd(modemp, mdm_init_string);
modemp->lastdial = cticks; /* reset last activity time */
break;
}
tmo = modemp->lastdial + (30*TPS); /* last dial activity plus some seconds... */
if(tmo < cticks) /* timeout? */
{
ConPrintf("timeout waiting for modem hangup.\n");
modemp->modem_in[0] = 0;
modemp->upperline->ln_state = D_BROKEN;
break;
}
break;
case D_IDLE: /* try to set phone to auto-answer */
sprintf((char*)(modemp->modem_out), "ATS0=%u", answer_rings);
if(modem_cmd(modemp, (char*)(modemp->modem_out)) == 0)
{
modemp->upperline->ln_state = D_AUTOANS;
modemp->lastdial = cticks; /* reset last activity time */
}
else
modemp->upperline->ln_state = D_BROKEN;
break;
case D_BROKEN:
modem_hangup(modemp->upperline); /* try to reset modem/dialer */
break; /* will try forever */
case D_RESETTING:
break;
default:
ConPrintf("ERROR: Bad dialer state\n");
dtrap("dialer 4\n");
modemp->upperline->ln_state = D_BROKEN;
break;
}
in_dialcheck--;
#endif /* #if 0 */
}
/* FUNCTION: modem_putc()
*
* Send a char out the modem connection.
*
* This is called by the protocol code to send single bytes.
*
* PARAM1: LINEP line
* PARAM2: int bByte
*
* RETURNS: 0 if OK, else -1, usually because of a timeout.
*/
static int mp_reenter = 0; /* re-entry flag */
int
modem_putc(LINEP line, int bByte)
{
MODEMP modemp;
unsigned long timeout;
modemp = ModemByLine(line);
if(modemp == NULL)
{
dtrap("dialer 5\n");
return -1;
}
if(mp_reenter) /* we should never reenter this routine! */
{
//ConPrintf("ERROR: reentered modem_putc\n");
dtrap("dialer 6\n");
return -1;
}
if(modemp->upperline->ln_state != D_CONNECTED) /* another serious coding problem */
{
//ConPrintf("ERROR: entered modem_putc when not connected\n");
dtrap("dialer 7\n");
return -1;
}
mp_reenter++; /* set reentry protect flag */
modemp->lastchar = cticks; /* reset idle timeout on all sent bytes */
timeout = cticks + TPS; /* for timeout on uart_ready */
while(uart_ready(modemp->unit) == FALSE) /* wait for uart send buffer to clear */
{
if(timeout <= cticks) /* timeout waiting for UART? */
{
#ifdef SUPERLOOP
/* this is pretty serious; should we reset connection? later... */
dtrap("dialer 8\n"); /* tell programmer */
// ConPrintf("modem_putc: UART Timeout\n");
#endif
mp_reenter--;
return -1;
}
#ifndef SUPERLOOP
tk_yield();
#endif
}
/* finally, send byte out uart */
uart_putc(modemp->unit, (u_char)bByte);
mp_reenter--;
return 0; /* good return */
}
#ifdef NET_STATS
/* FUNCTION: dialer_status()
*
* dialer_status() - dump stats to display. This routine is desinged for
* use by the demo package menu system & similar consoles.
*
* PARAM1: void * pio
*
* RETURNS: 0
*/
int
dialer_status(void * pio)
{
/* default to 1st modem */
int modem_unit = 0;
LINEP line = modems[modem_unit].upperline;
ns_printf(pio, "unit %d, dialer state: %s\n", modem_unit,
modem_state(&modems[modem_unit]));
ns_printf(pio, "last baud rate: %ld\n", line->ln_speed);
uart_stats(pio, modem_unit); /* dump UART stats */
return 0;
}
#endif /* NET_STATS */
/* FUNCTION: modem_connect()
*
* modem_connect() - Called from the PPP or SLIP send() code when a
* PPP packet is to be sent for this device. This checks
* that the modem and Uart are ready, and attempts to dial if they are
* not.
*
* PARAM1: LINEP mdm_line
*
* RETURNS: modem D_state after dialing attempt.
*/
static int amc_reenter; /* reentry protect flag */
int
modem_connect(LINEP mdm_line)
{
MODEMP modemp;
/* for states other than idle & autoanswer just return the state */
switch(mdm_line->ln_state)
{
case D_CONNECTED:
case D_DIALING:
case D_BROKEN:
case D_HANGINGUP:
return mdm_line->ln_state;
case D_AUTOANS:
case D_IDLE:
break;
default: /* bogus state value? */
dtrap("dialer 9\n");
return D_BROKEN;
}
modemp = ModemByLine(mdm_line);
if(modemp == NULL)
{
dtrap("dialer 10\n");
return -1;
}
if(amc_reenter) /* we should never reenter this routine! */
{
dtrap("dialer 11\n");
//ConPrintf("ERROR: reentered modem_connect\n");
return mdm_line->ln_state;
}
amc_reenter++; /* set reentry protect flag */
dial(modemp, mdm_dial_string);
amc_reenter--;
return D_DIALING;
}
/* (yaxon del) */
#if 0 /* #if 0 */
/* FUNCTION: modem_reset()
*
* modem_reset() - Do the best we can to reset the modem.
*
* PARAM1: MODEMP modemp
*
* RETURNS:
*/
static int in_modem_reset = 0;
void
modem_reset(MODEMP modemp)
{
int unit = modemp->unit;
if(in_modem_reset) /* guard against re-entry */
return;
in_modem_reset++;
/* set up the modem configuration's data strings */
#ifdef INCLUDE_NVPARMS
strncpy(mdm_dial_string, modem_nvparms.dial_phone, TELNUM_SIZE);
strncpy(mdm_init_string, modem_nvparms.modem_init, MODEM_STRING_SIZE);
#endif /* INCLUDE_NVPARMS */
/* (yaxon add) */
strcpy(mdm_dial_string, "*99#");
strcpy(mdm_init_string, "AT+CGDCONT=1,IP");
/* Following is the decription of "+++" command from VivaModem24 manual
that we have.
"+++ is the Escape Code that changes the modem form the On-Line
state to the command state. This code must be entered within the
time guard (default 1 sec)."
Hence we will use 1 sec guard band.
*/
/* (yaxon del) */
#if 0
dial_delay(TPS); /* wait 1 second */
uart_putc(unit, '+');
uart_putc(unit, '+');
uart_putc(unit, '+');
dial_delay(TPS); /* wait 1 second */
#endif
#ifdef MDM_DTRRESET
/* and just in case, toggle DTR line oif we have it... */
modem_clr_dtr(modemp);
dial_delay(TPS); /* hold down 1 second */
modem_set_dtr(modemp);
USE_ARG(unit);
#endif /* hard/soft reset */
if((modemp->upperline->ln_state != D_IDLE) &&
(modemp->upperline->ln_state != D_AUTOANS))
{
modem_cmd(modemp, "ATH"); /* AT hangup command */
}
in_modem_reset--; /* clear re-entry flag */
return;
}
#endif /* #if 0 */
/* FUNCTION: modem_no_carrier()
*
* modem_no_carrier() checks if we have recieved the "NO CARRIER"
* string from the modem. As characters are received, we keep them
* in a ring buffer. Return TRUE when we find "NO CARRIER" in the
* buffer.
*
* To keep the logic simple, we will start putting chars in
* buffer only after we receive 'N' or 'n'.
*
* PARAM1: MODEMP modemp
* PARAM2: int c
*
* RETURNS: TRUE if we got NO CARRIER string, else FALSE
*/
#ifdef MDM_CHECK_NO_CARRIER
#define NC_TMO 1 /* Timeout value in seconds. */
static char no_carrier[] = "NO CARRIER" ;
static u_long prevchar = 0; /* ctick of last character */
int
modem_no_carrier(MODEMP modemp, int c)
{
/* We only want to flag the NO CARRIER message if there has been a
* Time delay of 1 second or more since the last character. If last
* char was recent and not a match for the next expected char in NO
* CARRIER, then we restart the matching.
*/
if (cticks > (prevchar + (NC_TMO * TPS)) )
{
/* Been a long delay. Restart the count and check the first char */
modemp->carrier_match = 0; /* restart match count */
/* force c to uppercase for test */
if((c & ~0x20) == no_carrier[0])
{
modemp->carrier_match = 1;
}
}
else /* last char was recent */
{
/* see if received char matches next expected char in NO CARRIER */
if(c > 'Z')
c &= ~0x20; /* force to uppercase */
if(c == no_carrier[modemp->carrier_match])
{
modemp->carrier_match++;
if(modemp->carrier_match >= (int)strlen(no_carrier))
{
return TRUE;
}
}
else
modemp->carrier_match = 0;
}
prevchar = cticks;
return FALSE;
}
#endif /* MDM_CHECK_NO_CARRIER */
#endif /* USE_MODEM */
/* end of file dialer.c */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -