);
close(DETAILS);
return ($ip, $pid, $sect);
}
# get_wvdial_pid()
# Returns the PID of a running wvdial process
sub get_wvdial_pid
{
local $p;
&foreign_require("proc", "proc-lib.pl");
foreach $p (&proc::list_processes()) {
if ($p->{'args'} =~ /^\S*wvdial($|\s)/ && $p->{'args'} !~ /\[/) {
return $p->{'pid'};
}
}
return undef;
}
sub dialer_name
{
return $_[0] =~ /^Dialer Defaults$/i ?
$text{'index_defaults'} :
$_[0] =~ /^Dialer\s+(.*)$/i ?
&text('index_dialer', "$1") : $_[0];
}
# ppp_connect(section-name, textmode)
sub ppp_connect
{
# Get this dialer's configuration
local $conf = &get_config();
local ($dialer) = grep { lc($_->{'name'}) eq lc($_[0]) } @$conf;
local ($ddialer) = grep { lc($_->{'name'}) eq 'dialer defaults' } @$conf;
local ($inherits, $parent, $autodns);
if ($inherits = $dialer->{'values'}->{'inherits'}) {
($parent) = grep { lc($_->{'name'}) eq lc($inherits) } @$conf;
}
$autodns = $dialer->{'values'}->{'auto dns'} ?
($dialer->{'values'}->{'auto dns'} =~ /on|yes|1/ ? 1 : 0) :
$parent->{'values'}->{'auto dns'} ?
($parent->{'values'}->{'auto dns'} =~ /on|yes|1/ ? 1 : 0) :
$ddialer->{'values'}->{'auto dns'} ?
($ddialer->{'values'}->{'auto dns'} =~ /on|yes|1/ ? 1 : 0) :
1;
# Run wvdial, writing to a temp file in the background
local $stime = time();
local $sect = $_[0];
$sect =~ s/^Dialer\s+//;
local $temp = &tempname();
if (!($pid = fork())) {
untie(*STDIN);
untie(*STDOUT);
untie(*STDERR);
open(STDOUT, ">$temp");
open(STDERR, ">&STDOUT");
open(STDIN, "/dev/null");
exec($config{'wvdial'}, $sect);
exit(1);
}
while (!open(TEMP, "<".$temp)) { }
&additional_log("exec", undef, "$config{'wvdial'} $sect");
unlink($temp);
# Read output until success or failure
if ($_[1] == 1) {
print &text('connect_cmd', "$config{'wvdial'} $sect"),"\n\n";
}
elsif ($_[1] == 0) {
print "",&text('connect_cmd',
"$config{'wvdial'} $sect"),"
\n";
print "";
}
local ($connected, $failed);
while(1) {
local $line = &wait_for_line();
if ($_[1] == 1) {
print $line;
}
elsif ($_[1] == 0) {
print &html_escape($line);
}
if ($line =~ /IP\s+address\s+is\s+(\d+\.\d+\.\d+\.\d+)/i) {
# Connected OK!
$connected = $1 eq "0.0.0.0" ? "*" : $1;
last;
}
elsif ($line =~ /starting\s+ppp/i) {
# Connected in stupid mode
$connected = "*";
last;
}
elsif (!$line) {
# Program terminated .. must have failed!
$failed++;
last;
}
}
print "\n" if ($_[1] == 0);
# If OK, save the PID for later
if ($connected) {
if ($_[1] == 0) {
print "",$connected eq '*' ? $text{'connect_noip'} :
&text('connect_ip', "$connected"),"\n";
}
elsif ($_[1] == 1) {
print $connected eq '*' ? $text{'connect_noip'} :
&text('connect_ip', $connected),"\n";
}
&save_connect_details($connected, $pid, $_[0]);
}
else {
if ($_[1] == 0) {
print "$text{'connect_failed'}
\n";
}
elsif ($_[1] == 1) {
print "$text{'connect_failed'}\n\n";
}
}
$config{'dialer'} = $_[0];
&lock_file("$module_config_directory/config");
&write_file("$module_config_directory/config", \%config);
&unlock_file("$module_config_directory/config");
if ($connected && $autodns) {
# If the resolv.conf file has not been modified, and the PPP
# resolv.conf has, copy it into place
while(1) {
sleep(3);
local ($ip, $pid, $sect) = &get_connect_details();
if (!$pid || !kill(0, $pid)) {
# Connection is down .. DNS will never be updated
if ($_[1] == 0) {
print "$text{'connect_dnsdown'}
\n";
}
elsif ($_[1] == 1) {
print "$text{'connect_dnsdown'}\n\n";
}
last;
}
$now = time();
if ($now > $stime+60) {
# Took too long to update DNS
if ($_[1] == 0) {
print "$text{'connect_dnsto'}
\n";
}
elsif ($_[1] == 1) {
print "$text{'connect_dnsto'}\n\n";
}
last;
}
local @pst = stat($ppp_resolv_conf);
local @ost = stat($resolv_conf);
if ($ost[9] >= $stime) {
# Something else has update the DNS config ..
if ($_[1] == 0) {
print "$text{'connect_dns2'}
\n";
}
elsif ($_[1] == 1) {
print "$text{'connect_dns2'}\n\n";
}
last;
}
if ($pst[9] >= $stime) {
# A PPP DNS config has been created .. use it
&system_logged("cp $resolv_conf $save_resolv_conf")
if (!-l $resolv_conf);
unlink($resolv_conf);
&system_logged("cp $ppp_resolv_conf $resolv_conf");
if ($_[1] == 0) {
print "$text{'connect_dns'}
\n";
}
elsif ($_[1] == 1) {
print "$text{'connect_dns'}\n\n";
}
last;
}
}
}
return $connected;
}
# wait_for_line()
# Reads a line from the temp file, or waits if there is no more to read. Only
# returns undef if the process has died
sub wait_for_line
{
local $line = ;
return $line if ($line);
waitpid($pid, 1);
return undef if (!kill(0, $pid));
sleep(1);
return &wait_for_line();
}
# ppp_disconnect(mode, text-mode)
# Shuts down the active PPP connection
sub ppp_disconnect
{
local ($ip, $pid, $sect);
if ($_[0] == 0) {
($ip, $pid, $sect) = &get_connect_details();
}
else {
$pid = &get_wvdial_pid();
}
if ($pid && &kill_logged('TERM', $pid)) {
# Tell the user that the connection is now down
if ($ip) {
if ($_[1] == 0) {
print &text('disc_ok1', "$ip", &dialer_name($sect)),"\n";
}
elsif ($_[1] == 1) {
print &text('disc_ok1', $ip, &dialer_name($sect)),"\n\n";
}
}
else {
if ($_[1] == 0) {
print $text{'disc_ok2'},"
\n";
}
elsif ($_[1] == 1) {
print $text{'disc_ok2'},"\n\n";
}
}
# Restore the saved DNS config file, if it hasn't been done
sleep(3);
local @ost = stat($resolv_conf);
if (!-l $resolv_conf && $ost[9] < time()-5 && -r $save_resolv_conf) {
&system_logged("mv $save_resolv_conf $resolv_conf");
if ($_[1] == 0) {
print "$text{'disc_dns'}
\n";
}
elsif ($_[1] == 1) {
print "$text{'disc_dns'}\n\n";
}
}
&system_logged("rm -f $ppp_resolv_conf");
return 1;
}
else {
# Wasn't even active .. tell the user
if ($_[1] == 0) {
print "$text{'disc_edown'}
\n";
}
elsif ($_[1] == 1) {
print "$text{'disc_edown'}\n\n";
}
return 0;
}
}
1;