# Global Lib ...
# 
# STTA Rev. 1.3 Copyright (c) 2001-2004 Jesús Pérez Lorenzo  --- license GNU GPL 
# stta: (@#) 1.31051043346- [2004_01_29_102036]

# Read Config File -
# since 1.3 serveral files at /etc/webmin/stta/dataconf/*.cfg 
# this is more easy to manage and to split vars for each theme
# ... it needs more cpu as it has to open several files ...
sub load_dataconf() {
   local %listfcfgs=();
   local @orderfcfgs=();
   local $d="";
   local ($listfcfgs) = $_[0] || "ordercfgs";

   if (! (-d "$config_directory/$module_name/dataconf" )) { $config{tta_dir}="" };
   &read_file("$root_directory/$module_name/dataconf/$listfcfgs", \%listfcfgs, \@orderfcfgs);
   foreach $d (@orderfcfgs) {
         &read_file("$config_directory/$module_name/dataconf/$d", \%config);
   }
   &set_interface_colors();
   &read_file("$root_directory/$module_name/dataconf/form_vars", \%text);
   $config{check_brand}=`cat $root_directory/$module_name/install/.brandchk 2>/dev/null`;
   $config{check_brand}=~ s/\r|\n//g;
}

sub set_interface_colors
{
    if (!defined($ENV{'WEBMIN_CONFIG'})) { return };  # not running under Webmin Server
    if ( defined($config{'cs_header'}) && $config{'cs_header'} ne "" ) {
           $tb="bgcolor=#$config{'cs_header'}"; 
	   $tconfig{'cs_header'}=$config{'cs_header'};
    }
    if ( defined($config{'cs_table'}) && $config{'cs_table'} ne "" ) {
           $cb="bgcolor=#$config{'cs_table'}"; 
    }
    if ( defined($config{'cs_page'}) && $config{'cs_page'} ne "" ) {
           $bgcolor="$config{'cs_page'}"; 
	   $tconfig{'cs_page'}=$config{'cs_page'};
    }
    if ( defined($config{'cs_link'}) && $config{'cs_link'} ne "" ) {
           $link="$config{'cs_link'}"; 
	   $tconfig{'cs_link'}=$config{'cs_link'};
    }
    if ( defined($config{'cs_text'}) && $config{'cs_text'} ne "" ) {
           $text="$config{'cs_text'}"; 
	   $tconfig{'cs_text'}=$config{'cs_text'};
    }
    if ( defined($config{'cs_revtext'}) && $config{'cs_revtext'} ne "" ) {
           $revtext="#$config{'cs_revtext'}"; 
    } else { $revtext="#ffffff"; }
    if ( defined($config{'bgimage'}) && $config{'bgimage'} ne "" ) {
	 $bgimage="background=\"$config{'bgimage'}\"";
	 $tconfig{'bgimage'}=$config{'bgimage'};
    }
}
sub load_minfo
{
   local $pathModInfo = $_[0] ||  '';
   $pathModInfo .= "module.info";

   local %minfo;
   &read_file( "$pathModInfo",\%minfo) ;
   return %minfo;
}

sub set_datetime_str
{
    local ($wkstr) = $_[0];
    local ($outStr) = "";
    local ($fday, $fmon, $fyea, $fhou, $fmin, $fsec, $fwday);

    # format should be: `date "+%d-%m-%Y %H:%M:%S %w"`;

    $fday=substr($wkstr,0,2); 
    $fmon=substr($wkstr,3,2); 
    $fyea=substr($wkstr,6,4); 
    $fhou=substr($wkstr,11,2); 
    $fmin=substr($wkstr,14,2); 
    $fsec=substr($wkstr,17,2); 
    $fwday=substr($wkstr,20,1); 

    # format for order criteria

    $outStr=$fyea.$fmon.$fday.$fhou.$fmin.$fsec.$wday ;
  return $outStr;
}

sub get_datetime_str
{
    local ($wkstr) = $_[0];
    local ($outStr) = "";
    local ($fday, $fmon, $fyea, $fhou, $fmin, $fsec, $fwday);

    # format should be: `date "+%d-%m-%Y %H:%M:%S $w"`;

    $fday=substr($wkstr,6,2); 
    $fmon=substr($wkstr,4,2); 
    $fyea=substr($wkstr,0,4); 
    $fhou=substr($wkstr,8,2); 
    $fmin=substr($wkstr,10,2); 
    $fsec=substr($wkstr,12,2); 
    $fsec=substr($wkstr,14,1); 

    # format for order criteria

    $outStr=$fday."-".$fmon."-".$fyea." ".$fhou.":".$fmin.":".$fsec." ".$fwday ;

  return $outStr;
}
sub set_now
{
    local ($now);
    if ( !$_[0] ) { 
         $now = time();
    } else {
         $now=$_[0];
    }     
    local @tm = localtime($now);
    local ($t_day, $t_mon, $t_yea, $t_hou, $t_min, $t_sec, $t_wday);
    
     # format should be: `date "+%d-%m-%Y %H:%M:%S $w"`;
     $t_sec=$tm[0];
     if ($t_sec < 10 ) { $t_sec="0".$t_sec;}
     $t_min=$tm[1];
     if ($t_min < 10 ) { $t_min="0".$t_min;}
     $t_hou=$tm[2];
     if ($t_hou < 10 ) { $t_hou="0".$t_hou;}
     $t_day=$tm[3];
     if ($t_day < 10 ) { $t_day="0".$t_day;}
     $t_mon=($tm[4]+1);
     if ($t_mon < 10 ) { $t_mon="0".$t_mon;}
     $t_yea=($tm[5]+1900);
     $t_wday=($tm[6]);
     $t_yead=$tm[7];
     if ($t_yead < 100 ) { $t_yead="0".$t_yead;}
     if ($t_yead < 10 ) { $t_yead="0".$t_yead;}
     $t_isdst=$tm[8];
        

    return "$t_day-$t_mon-$t_yea $t_hou:$t_min:$t_sec $t_wday $t_yead";

}

# cipher( text, length(text), key, length(key),result)
sub cipher
{
	local $i,$pos;
        local @buffer;
        local @string_arr;

        &seed_random();
	for ( $pos = 0; $pos < $_[3]; $pos++ ) {
                $i=int(rand($_[3]));
                $string_arr[$pos]=${$_[2]}[$i];
	}
	if (($_[1] + 2) >= $_[3]) {
		$pos = 1;
	} else {
		$pos = int(rand($_[3] - ($_[1] + 2)));
	}
        if ( $pos < 1 ) { $pos=1; }
	$string_arr[$pos - 1] = '\\';
        for ( $i=0 ; $i < ($_[1]+1) ; $i++ ) {
        	$string_arr[$pos+$i]=${$_[0]}[$i];
        }
	$string_arr[$pos + $_[1]+1] = '\\';

	for ( $i = 0; $i < $_[3]; $i++) {
		$buffer[$i]= $string_arr[$i] ^ ${$_[2]}[$i];
                ${$_[4]}.=$buffer[$i];
        }
       return; 
}

# decipher( text, key, length(key),result)
sub decipher
{
	local $i,$tobuff;
        local @buffer;

	for ( $i = 0; $i < $_[2]; $i++) {
		$buffer[$i] = ${$_[0]}[$i] ^ ${$_[1]}[$i];
        }

        $tobuff="0";
	for ( $i = 0; $i < $_[2]; $i++)  {
		if ($buffer[$i] eq '\\' )  {
                    if ( $tobuff eq "1" ) { 
                         $tobuff="0";
                    } elsif ( $tobuff eq "0" ) {
                         $tobuff="1";
                         next;
                    }
		}
                if ( $tobuff eq "1" ) { ${$_[3]}.=$buffer[$i]; }
        }
	return;
}

# cipher_text ( $task (code|decode), $text, &vartoreturn)
sub cipher_text
{
    local $longclave=12;
    local @clave=("0","1","2","3","4","5","6","7","0","1","2","3","4","5","6","7","0","1","2","3","4");
    local @texto =();
    local $lon=length($_[1]); 
    local $i;

    if ( $_[0] eq "code" ) {
         for ( $i = 0; $i < $lon;$i++) { $texto[$i]=substr($_[1],$i,1); }
	 &cipher(\@texto, $#texto, \@clave, $longclave,\${$_[2]});
    } elsif ( $_[0] eq "decode" ) { 
        $lon=length($_[1]); 
	for ( $i = 0; $i < $lon;$i++) { $texto[$i]=substr($_[1],$i,1); }
	&decipher(\@texto, \@clave, $lon,\${$_[2]});
    }
    if ( $debug eq "4" ) { &webmin_log("cipher_text",$_[0], "$_[1] -- ${$_[2]}"); }
}


# show_hash( %has-to-scan,$father-brach-if-hash-tree, $separator, $dev-to-output,&vartoout
sub show_hash
{
 local ($item,$v,$r);
  if ( $_[3] ) { select($_[3]);}
  return if (!%{$_[0]});
  local %h_lst=%{$_[0]};
  local @data;
  local @hlst=(), @hLst=();
  local $lnum=0;
  local $lchar=62;
  local $sep;

  if ( "$_[1]" eq "" && !$_[4] ) {
           print "___________________________________________________________\n"; 
  }

  foreach $item (keys (%h_lst)) {
#         if ( ! $h_lst{$item} ) { next ;}
         local $v=$h_lst{$item};
         $r=ref($v);
         if ( $r eq 'HASH') { 
               if ( $_[4] ) {
#                  ${$_[4]}.=$item."\n";
                   &show_hash(\%{$h_lst{$item}},$item,$_[2],$_[3],\${$_[4]});
               } else {
#                  print "$item\n";
                   &show_hash(\%{$h_lst{$item}},$item,$_[2],$_[3]);
               }
        } elsif ( $r eq 'ARRAY') {
               local @data=@{$v};
               for($i=1; $i <= $#data; $i++) {
                     if ( $_[4] ) {
                        ${$_[4]}.=$data[$i]."\n";
                     } else {
                        print $data[$i]."\n";
                     }
               }
        } else {
               push (@hlst,{'name' => $item, 'value' => $v } );
        }
        $lnum++;
  }
  @hLst = sort {$a->{name} cmp $b->{name}} @hlst;
  foreach $hitem (@hLst) {
       $item=$hitem->{'name'};
       $v=$hitem->{'value'};
       if ( $_[2] ) { 
                     if ( $_[4] ) {
                          ${$_[4]}.="$item$_[2]=$_[2]$v\n" ;
                     } else {
                        print $item.$_[2]."=".$_[2].$v."\n" ;
                     }
       } else  { 
                     if ( $_[4] ) {
                        ${$_[4]}.=$item."=".$v."\n" ;
                     } else {
                        print $item."=".$v."\n" ;
                     }
       }
  }
  if ( "$_[1]" ne "" ) {
     $item="_($lnum)_$_[1]________________________________________________________";
     if ( $_[4] ) {
          ${$_[4]}.="_($lnum)__$_[1]_____\n";
     } else {
          print substr($item,0,$lchar)."\n";
     }
  }
  if ( $_[3] ) { $| =1; select(STDOUT);}
#  if ( $_[4] ) { print "4** $_[4]";}
  
}

# lookup in hash %{$_[0]} for key $_[1]  and return value
sub search_in_hash
{
  local ($k,$v,$,);
  return if (!%{$_[0]});
  local %h_lst=%{$_[0]};
  local $lnum=1;
  local $key_value;

  foreach $item (keys (%h_lst)) {
         local $v=$h_lst{$item};
         $r=ref($v);
         if ( $r eq 'HASH') { 
               local %h_cp=%{$v};          
              $key_value=&search_in_hash(\%h_cp,$_[1]);
              if ( $key_value.length gt 0 ) { return $key_value; }
        } else { 
              if ($item eq $_[1] ) { return $h_lst{$item}; }
        }
        $lnum++;
  }
}

# To show each item from Rec in a list (hash-list: key + hash ) 
sub showrec_list
{
  &show_hash(\%{$_[0]},"","\t");
}

# check_socket(host, port, handle, [&error])
sub check_socket
{
local($addr, $h); $h = $_[2];
        if (!socket($h, PF_INET, SOCK_STREAM, getprotobyname("tcp"))) {
	     if ($_[3]) { ${$_[3]} = &text(sckerr_no, $!); return false; }
	     else { &error("&text(sckerr_no, $!)"); }
	}
        if (!($addr = inet_aton($_[0]))) {
	     if ($_[3]) { ${$_[3]} = &text(sckerr_noip, $_[0]); return false; }
	     else { &error("&text(sckerr_noip, $_[0])"); }
	}
        if (!connect($h, sockaddr_in($_[1], $addr))) {
	     if ($_[3]) { ${$_[3]} = &text(sckerr_noconn, $_[0],$_[1],$!); return false; }
	     else { &error("&text(sckerr_noconn, $_[0],$_[1],$!)"); }
	}
        # select($h); $| =1; select(STDOUT);
        shutdown($h,2);
        if ($_[3]) { ${$_[3]} = &text('responding_on',$_[1]); }  
        return true;
}

# Loading Hash with file and properties %ttaprops (with @data in)  and @ttahosts
# get_ttaprops(has_toset,$dir_path,$extension,$names_toexclude) 
sub get_ttaprops 
{
     local @list_names=glob($_[0]."*".$_[1]);
     local $list_exclude=$_[2];
     local $nhost=0;
     local $target=0;
     local $k,$kname,$v;
     local $ttaproperties=$text{tta_properties};

     foreach $f_name (@list_names) {
         $FileName=$f_name;
         $FileName=~s/$dir_path//g;  
         if ( $FileName )  { $FileName=~s/$_[1]//g; }
         if ( $list_exclude =~ /$FileName/ ) { next; }
         local %configtta=();
         &read_file($f_name, \%configtta);
         $target="array";
         if ( $configtta{'tarantella.config.name'} =~ /host/  ) { 
#              if ( $ttaproperties =~ /$FileName/ ) {
#                      $target="array";
#              } else {
          	    $target="host";
	            $ttahosts[$nhost] = { 'name' => $FileName  };
#              }
         }
         $ttaprops{$FileName} = { 
                           'name' => $FileName,
                           'target' => $target,
                           'path' => $f_name,
                           'config' => \%configtta
                          };
        if ( $target eq "host" ) { $nhost++; }
    }
}


sub load_ttaprops
{
     local $dir_path=$config{tta_dir}.$text{tta_global_dir};
     if ( $_[0] ) { $dir_path=$_[0] };
     local @data;
     local %configtta;
     local %h_cp;
     local ($array_port, $array_extport, $array_secureport, $cdm_enabled);
     local ($cdm_extlnbport, $billingservice, $searchldapLA, $ldap_url, $host_master, $h_license);
     local $lnum=0,$masthost;
     local ($h_secure, $h_dns_ext, $h_dns_peer, $h_acceptconn,$item);

     &get_ttaprops($dir_path,$text{tta_ext_cfgfiles},"");

    $array_port	=
      &search_in_hash(\%{$ttaprops{bootstrap}{config}},"tarantella.config.array.port");
    $array_extport=
      &search_in_hash(\%{$ttaprops{bootstrap}{config}},"tarantella.config.array.externalport");
    $array_secureport=
      &search_in_hash(\%{$ttaprops{bootstrap}{config}},"tarantella.config.array.secureport");
    $cdm_enabled=
      &search_in_hash(\%{$ttaprops{cdm}{config}},"tarantella.config.cdm.enabled");
    $cdm_extlnbport=
      &search_in_hash(\%{$ttaprops{cdm}{config}},"tarantella.config.cdm.externalnbtport");
    $billingservice=
      &search_in_hash(\%{$ttaprops{components}{config}},"tarantella.config.components.billingservice");
    $searchldapLA=
      &search_in_hash(\%{$ttaprops{components}{config}},"tarantella.config.components.searchldaploginauthority");
    $ldap_url=
      &search_in_hash(\%{$ttaprops{ldap}{config}},"tarantella.config.ldap.url");
    $host_master=
    &search_in_hash(\%ttaprops,"tarantella.config.host.master");

    $dir_path=$config{tta_dir}.$text{tta_local_dir}.$text{tta_bootstrap};
    &read_file($dir_path,\%configtta);

    $lnum=0;
    @data=@ttahosts;
    foreach $item (@data) {
            %h_cp=%{$ttaprops{$item->{name}}};
            $h_license= &search_in_hash(\%h_cp,"tarantella.config.host.license.keys");
            $h_secure= &search_in_hash(\%h_cp,"tarantella.config.host.security.active");
            $h_dns_ext= &search_in_hash(\%h_cp,"tarantella.config.host.dns.external");
            $h_dns_peer= &search_in_hash(\%h_cp,"tarantella.config.host.dns.peer");
            $h_acceptconn= &search_in_hash(\%h_cp,"tarantella.config.host.acceptnewconnections");
            $ttahosts[$lnum]={'name' => $item->{name},
                              'secure' => $h_secure,
                              'dns_ext' => $h_dns_ext,
                              'dns_peer' => $h_dns_peer,
                              'acceptconn' => $h_acceptconn,
                              'license' => $h_license,
  			      'ttaarray_status' => '',
  			      'ttastd_status' => '',
  			      'ttassl_status' => '',
  			      'ttacdm_status' => '',
  			      'http_status' => '',
  			      'https_status' => '',
                              'ipalive' => "" };
            if ( "$item->{name}" eq "$configtta{'tarantella.config.server.dns.peer'}" ){
                 $masthost=$lnum;
            }
            $lnum++;
    }
 
    $sttaparams{'tta'}= { 'ttalocal_dns_ext' => 
                                       $configtta{'tarantella.config.server.dns.external'},
                          'ttalocal_dns_peer' => 
                                       $configtta{'tarantella.config.server.dns.peer'},
                          'nhost'	 => $lnum,
                          'masthost'	 => $masthost,
                          'array_port'	 => $array_port,
                          'array_extport' => $array_extport,
                          'array_secureport' => $array_secureport,
                          'cdm_enabled' => $cdm_enabled,
                          'cdm_extlnbport' => $cdm_extlnbport,
                          'billingservice' => $billingservice,
                          'searchldapLA' => $searchldapLA,
                          'ldap_url' => $ldap_url,
                          'host_master' => $host_master };
    $sttaparams{'ldap'}= { 'ldap_status' => "",
  			  'ldap2_status' => "",
  			  'ldapcache_status' => "",
  			  'ldapcache2_status' => "" };
}

# Args can be "local"  (localhost and array services) or "remote" ( no local services)
# any other even nothing will be the whole array services !
sub scanSTTA_services
{
  local $title="";
  local $host,$port,$masthost;
  local $rv = { 'fh' => time().$$ };
  local %h_prop;
  local @data;
  local $is_ttamaster=false;
  local %h_hosts=&list_hosts(5);   

  local $thishost_name;
  $masthost=$sttaparams{'tta'}{'masthost'};

        # to look-up for master ...
        #  if ( $sttaparams{tta}{host_master} eq $sttaparams{tta}{ttalocal_dns_peer}){
        # Can be equal in Primary Array Server
        # if ( $sttaparams{'tta'}{'host_master'} eq $ttahosts[$masthost]->{'dns_peer'}){
 $lnum=0;
 foreach $item (@ttahosts) {
         $thishost_name="";
         %h_prop=%{$ttaprops{$item->{name}}};
         if ( $sttaparams{'tta'}{'host_master'} eq $item->{'dns_peer'} ) {
              $is_ttamaster=true;
              $thishost_name="TTA MASTER->";
         }
         next if  ( $_[0] eq "local" && 
              $item->{'dns_peer'} ne $sttaparams{tta}{ttalocal_dns_peer} &&
              $is_ttamaster ne true  );
         next if  ( $_[0] eq "remote" && 
              $item->{'dns_peer'} eq $sttaparams{tta}{ttalocal_dns_peer} );
       
       # Is TTA Alive on this host ??
         $host=$item->{'dns_peer'};
         $thishost_name.=$item->{'name'};

         if ( $item->{'name'} ne $host ) { $thishost_name.=$item->{'name'}." ($host)"; }

       # Try Array 5427
         $title="$text{srvTTA_Array} $thishost_name:";
         $port=$sttaparams{tta}{array_port};
         if ( $port) { 
              &check_socket($host, $port, $rv->{'fh'}, \$item->{'ttaarray_status'});
              if ( $debug eq 4 ) {
                   &additional_log('tta array socket', "socket", "$title $port");
                   &webmin_log("tta array socket","socket",$item->{'ttaarray_status'});
              }
         }
       # Try STD   
         $title="$text{srvTTA_STD} $thishost_name:";
         $port=$sttaparams{tta}{array_extport};
         if ( $port && $item->{acceptconn} eq "enabled" ) { 
              &check_socket($host, $port, $rv->{'fh'}, \$item->{'ttastd_status'});
              if ( $debug eq 4 ) {
                   &additional_log('ttaSTD socket', "socket", "$title $port");
                   &webmin_log("ttaSTD socket","socket",$item->{'ttastd_status'});
              }
         }; 
       # Try SSL
         $title="$text{srvTTA_SSL} $thishost_name:";
         $port=$sttaparams{tta}{array_secureport};
         if ( $port && $ttahosts[$masthost]->{acceptconn} eq "enabled" &&
              $item->{secure}  =~ /ssl/ ) { 
              &check_socket($host, $port, $rv->{'fh'}, \$item->{'ttassl_status'});
              if ( $debug eq 4 ) {
                   &additional_log('ttaSSL socket', "socket", "$title $port");
                   &webmin_log("ttaSSL socket","socket",$item->{'ttassl_status'});
              }
         };
       # Test CDM
         if ( $sttaparams{tta}{cdm_enabled} eq "1"  && 
             $item->{acceptconn} eq "enabled" ) {
             $title="$text{srvTTA_CDM} $thishost_name:";
             $port=$sttaparams{tta}{cdm_extlnbport};
             &check_socket($host, $port, $rv->{'fh'}, \$item->{'ttacdm_status'});
             if ( $debug eq 4 ) {
                  &additional_log('ttaCDM socket', "socket", "$title $port");
                  &webmin_log("ttaCDM socket","socket",$item->{'ttacdm_status'});
             }
         };
       # Assuming same ports in all the array ....
       # IS HTTP
         $port=$config{http_port};
         if ( $port ) {
             $title="$text{srvHTTP} $thishost_name:";
             &check_socket($host, $port, $rv->{'fh'}, \$item->{'http_status'}); 
             if ( $debug eq 4 ) {
                  &additional_log('http socket', "socket", "$title $port");
                  &webmin_log("http socket","socket",$item->{'http_status'});
             }
         };
       # IS HTTPS
         $port=$config{https_port};
#         if ( $port && $ttahosts[$masthost]->{secure} eq "1" ) { 
         if ( $port ) { 
             $title="$text{srvHTTPS} $thishost_name:";
             &check_socket($host, $port, $rv->{'fh'}, \$item->{'https_status'});
             if ( $debug eq 4 ) {
                  &additional_log('https socket', "socket", "$title $port");
                  &webmin_log("https socket","socket",$item->{'https_status'});
             }
         };
         # Alive Port
         $port="";
         if  ( $h_hosts{$host}->{'ipname'} eq $host ) {
            $port=$h_hosts{$host}->{'portalive'};
            $thishost_name=$h_hosts{$host}->{'name'};
            $host=$h_hosts{$host}->{'ipname'};
         }
         $title="$text{f_portalive} $thishost_name:";
         if ( $port ) {
             &check_socket($host, $port, $rv->{'fh'}, \$item->{'ipalive'});
             if ( $debug eq 4 ) {
                  &additional_log('ipalive socket', "socket", "$title $port");
                  &webmin_log("ipalive socket","socket",$item->{'ipalive'});
             }
         }
         $lnum++;
 }
   # IS LDAP up
         $host=$config{ldap_server};
         if ( $host ) {
              $port=$config {ldap_port};
              $thishost_name="$config{ldap_servertitle} $host";
              $title="$text{srvLDAP} $thishost_name:";
              &check_socket($host, $port, $rv->{'fh'}, \$sttaparams{'ldap'}{'ldap_status'});
              if ( $debug eq 4 ) {
                   &additional_log('ldap socket', "socket", "$title $port");
                   &webmin_log("ldap socket","socket",$sttaparams{'ldap'}{'ldap_status'});
              }
         };

  # IS LDAP2 up
         $host=$config{ldap2_server};
         if ( $host ) {
              $port=$config {ldap2_port};
              $thishost_name="$config{ldap2_servertitle} $host";
              $title="$text{srvLDAP} $thishost_name:";
              &check_socket($host, $port, $rv->{'fh'},\$sttaparams{'ldap'}{'ldap2_status'});
              if ( $debug eq 4 ) {
                   &additional_log('ldap2 socket', "socket", "$title $port");
                   &webmin_log("ldap2 socket","socket",$sttaparams{'ldap'}{'ldap2_status'});
              }
         };

  if ( $config{'is_ldapcache'} eq "true" ) {
         # IS LDAP CACHE up
         $host=$config{ldapcache_server};
         if ( $host ) {
              $port=$config {ldapcache_port};
              $thishost_name="$config{ldapcache_servertitle} $host";
              $title="$text{srvLDAPCACHE} $thishost_name:";
              &check_socket($host, $port, $rv->{'fh'}, \$sttaparams{'ldap'}{'ldapcache_status'});
              if ( $debug eq 4 ) {
                   &additional_log('ldapcache socket', "socket", "$title $port");
                   &webmin_log("ldapcache socket","socket",$sttaparams{'ldap'}{'ldapcache_status'});
              }
         };
     
         # IS LDAP2 CACHE up
         $host=$config{ldapcache2_server};
         if ( $host ) {
              $port=$config {ldapcache2_port};
              $thishost_name="$config{ldapcache2_servertitle} $host";
              $title="$text{srvLDAPCACHE} $thishost_name:";
              &check_socket($host, $port, $rv->{'fh'}, \$sttaparams{'ldap'}{'ldapcache2_status'});
              if ( $debug eq 4 ) {
                   &additional_log('ldapcache2 socket', "socket", "$title $port");
                   &webmin_log("ldapcache2 socket","socket",$sttaparams{'ldap'}{'ldapcache2_status'});
              }
         }; 
  } 
  $ldap_ok=true;
  $ldapcache_ok=true;
  $tta_ok=true;
  if ( $config{is_ldapcache} eq "true" && $sttaparams{'ldap'}{'ldapcache_status'} ne &text('responding_on',$config{ldapcache_port}) ) {
         $ldapcache_ok=false;
  }
  if ( $config{has_ldapusers} eq "true" && $sttaparams{'ldap'}{'ldap_status'} ne &text('responding_on',$config{ldap_port})) {
         $ldap_ok=false;
  }
#  if  ($ttahosts[$mhost]->{ttaarray_status} ne &text('responding_on',$sttaparams{tta}{array_port})) {
#         $tta_ok=false;
#  }
  foreach $item (@ttahosts) {
     if  ( $item->{'ttaarray_status'} ne &text('responding_on',$sttaparams{tta}{array_port})) {
           $tta_ok=false;
     }
  }
}
  
# checkSTTA_services($which,$how_handle,&var_out)
# $which can be "local"  (localhost and array services) or "remote" ( no local services)
# any other even nothing will be the whole array services !
# $how_handle means $config{iferror_services} options: stop, warn, browse
# ${$_[2]} is var to keep
sub checkSTTA_services
{
 local $title="";
 local $lnum=0;
 local %h_prop;
 local %h_hosts=&list_hosts(5);
 foreach $item (@ttahosts) {
         next if  ( $_[0] eq "local" && 
              $item->{'dns_peer'} ne $sttaparams{tta}{ttalocal_dns_peer} &&
              $is_ttamaster ne true  );
         next if  ( $_[0] eq "remote" && 
              $item->{'dns_peer'} eq $sttaparams{tta}{ttalocal_dns_peer} );
         $thishost_name="";
         %h_prop=%{$ttaprops{$item->{name}}};
         if ( $sttaparams{'tta'}{'host_master'} eq $item->{'dns_peer'} ) {
              $is_ttamaster=true;
              $thishost_name="TTA MASTER->";
         }
       # Is TTA Alive on this host ??
         $host=$item->{'dns_peer'};
         $thishost_name.=$item->{'name'};

         if ( $item->{'name'} ne $host ) { $thishost_name.=$item-{'name'}." ($host)"; }

       # Try Array 5427
         $port=$sttaparams{tta}{array_port};
         $title="$text{srvTTA_Array} $thishost_name";
         if ( $port) { 
              &chkout_service($_[1],$title,$item->{'ttaarray_status'},\${$_[2]});
         } else {
              &chkout_service($_[1],$title,"unknown",\${$_[2]});
         }
       # Try STD   
         $port=$sttaparams{tta}{array_extport};
         $title="$text{srvTTA_STD} $thishost_name:";
         if ( $port && $item->{acceptconn} eq "enabled" ) { 
              &chkout_service($_[1],$title,$item->{'ttastd_status'},\${$_[2]});
         } else {
              &chkout_service($_[1],$title,"unknown",\${$_[2]});
         }; 
       # Try SSL
         $port=$sttaparams{tta}{array_secureport};
         $title="$text{srvTTA_SSL} $thishost_name:";
         if ( $port && $ttahosts[$masthost]->{acceptconn} eq "enabled" &&
              $item->{secure}  =~ /ssl/ ) { 
               &chkout_service($_[0],$title,$item->{'ttassl_status'},\${$_[2]});
         } else {
              &chkout_service($_[1],$title,"unknown",\${$_[2]});
         };
       # Test CDM
         $title="$text{srvTTA_CDM} $thishost_name:";
         if ( $sttaparams{tta}{cdm_enabled} eq "1"  && 
             $item->{acceptconn} eq "enabled" ) {
             $port=$sttaparams{tta}{cdm_extlnbport};
              &chkout_service($_[1],$title,$item->{'ttacdm_status'},\${$_[2]});
         } else {
              &chkout_service($_[1],$title,"unknown",\${$_[2]});
         };
       # Assuming same ports in all the array ....
       # IS HTTP
         $port=$config {http_port};
         $title="$text{srvHTTP} $thishost_name:";
         if ( $port ) {
              &chkout_service($_[1],$title,$item->{'http_status'},\${$_[2]}); 
         } else {
              &chkout_service($_[1],$title,"unknown",\${$_[2]});
         };
       # IS HTTPS
         $port=$config {https_port};
         $title="$text{srvHTTPS} $thishost_name:";
#         if ( $port && $ttahosts[$masthost]->{secure} eq "1" ) { 
         if ( $port ) { 
              &chkout_service($_[1],$title,$item->{'https_status'},\${$_[2]});
         } else {
              &chkout_service($_[1],$title,"unknown",\${$_[2]});
         }
       # Alive Port
         $host=$item->{'dns_peer'};
         $port="";
         if  ( $h_hosts{$host}->{'ipname'} eq $host ) {
            $port=$h_hosts{$host}->{'portalive'};
            $thishost_name=$h_hosts{$host}->{'name'};
            $host=$h_hosts{$host}->{'ipname'};
         }
         $title="$text{f_portalive} $thishost_name:";
         if ( $port ) { 
              &chkout_service($_[1],$title,$item->{'ipalive'},\${$_[2]});
         } else {
              &chkout_service($_[1],$title,"unknown",\${$_[2]});
         }
       $lnum++;
 }
  
   # IS LDAP up
         $host=$config{ldap_server};
         $thishost_name=$config{ldap_servertitle};
         $title="$text{srvLDAP} $thishost_name:";
         if ( $host ) {
              $port=$config {ldap_port};
               &chkout_service($_[1],$title,$sttaparams{'ldap'}{'ldap_status'},\${$_[2]});
         } else {
              &chkout_service($_[1],$title,"unknown",\${$_[2]});
         };

  # IS LDAP2 up
         $host=$config{ldap2_server};
         $thishost_name=$config{ldap2_servertitle};
         $title="$text{srvLDAP} $thishost_name:";
         if ( $host ) {
              $port=$config {ldap2_port};
              &chkout_service($_[1],$title,$sttaparams{'ldap'}{'ldap2_status'},\${$_[2]});
         } else {
              &chkout_service($_[1],$title,"unknown",\${$_[2]});
         };

  if ( $config{'is_ldapcache'} eq "true" ) {
         # IS LDAP CACHE up
         $host=$config{ldapcache_server};
         $thishost_name=$config{ldapcache_servertitle};
         $title="$text{srvLDAPCACHE} $thishost_name:";
         if ( $host ) {
              $port=$config {ldapcache_port};
              &chkout_service($_[1],$title,$sttaparams{'ldap'}{'ldapcache_status'},\${$_[2]});
         } else {
              &chkout_service($_[1],$title,"unknown",\${$_[2]});
         };
     
         # IS LDAP2 CACHE up
         $host=$config{ldapcache2_server};
         $thishost_name=$config{ldapcache2_servertitle};
         $title="$text{srvLDAPCACHE} $thishost_name:";
         if ( $host ) {
              $port=$config {ldapcache2_port};
              &chkout_service($_[1],$title,$sttaparams{'ldap'}{'ldapcache2_status'},\${$_[2]});
         } else {
              &chkout_service($_[1],$title,"unknown",\${$_[2]});
         }; 
  }
}

sub printSTTA_config
{
 local $item;

 local @datacfg = ( 'is_masterHost', 'masterHost', 'masterHostURL',
		'ldap_type',
		'is_ldapcache', 'ldapcache_type',
		'cache_chkdefaults', 'cache_chkttalogin',
		'cache_scandebug', 'cache_domain',
		'check_maxsess', 'default_maxsess', 'check_ticket',
		'default_cat', 'order_cat', 'interface',
		'has_monitor',
		'has_cronsess',
		'sessout_timeout',
		'output_cgis',
		'debug_code',
		'check_services',
		'iferror_services',
                         );
    foreach $item (@datacfg) {
           $str_val=$config{$item}; 
           if ( $config{$item} eq "true" ) { $str_val=$text{yes}; }
           if ( $config{$item} eq "false" ) { $str_val=$text{no}; }
           if ( $config{$item} eq "none" ) { $str_val=$text{none}; }
           if ( $item eq "sessout_timeout") {
                if ( $config{$item} eq "8" ) { $str_val="1 $text{edit_hours}"; }
                if ( $config{$item} eq "12" ) { $str_val="1 $text{edit_minutes}"; }
                if ( $config{$item} eq "11" ) { $str_val="10 $text{edit_minutes}"; }
                if ( $config{$item} eq "13" ) { $str_val="10 $text{edit_seconds}"; }
                if ( $config{$item} eq "14" ) { $str_val="1 $text{edit_seconds}"; }
           } 
           if ( $_[0]  ) {
               if ( $_[1]  ) {
                    ${$_[0]}.= "STTA: ".$text{'cfg_'.$item}."=".$_[1].$str_val."\n";
               } else {
                    ${$_[0]}.= "STTA: ".$text{'cfg_'.$item}."=".$str_val."\n";
               }
           } else {
               if ( $_[1]  ) {
                   print "STTA: ".$text{'cfg_'.$item}.$_[1]."=".$_[1].$str_val."\n";
                } else {
                   print "STTA: ".$text{'cfg_'.$item}."=".$str_val."\n";
                }
           }
    }
}

# chkout_service($how_handle, $title, $message,&varout,$sep)
# $how_handle means $config{iferror_services} options: stop, warn, browse, status
# ${$_[3]} is var to keep
sub chkout_service
{
    local $respo=$text{responding_on};
    $respo=~ s/\$1//;

       if ( "$_[0]" eq "stop" ) {
             if  ( "$_[2]" =~ /$respo/ || "$_[2]" eq "unknown"){ 
                   return; 
             } else {
                    $err_msg="$_[1]  $_[2]";
                   # &SrvError(); 
                    &additional_log("STTA $_[0]", "services", "$_[2]");
                    &webmin_log("STTA $text{$_[0]}","services","$_[1]",@_[2]);
                    error("STTA $text{$_[0]}: $_[1] \n\t\"$_[2]\" \n");
             }
       } elsif ( "$_[0]" eq "warn" ) {
             if ( "$_[2]" ne "unknown" ) {
                   &webmin_log("STTA $text{$_[0]}","services","$_[1] - $_[2]");
             } else {
                   &webmin_log("STTA $text{$_[0]}","services","$_[1] - $text{unknown}");
             }
       } elsif ( "$_[0]" eq "browse" ) {
             if ( $config{iferror_services} eq "stop" ) {
                if  ( "$_[2]" =~ /$respo/ || "$_[2]" eq "unknown"){ 
                    #
                } else {
                    $err_msg="$_[1]  $_[2]";
                    &additional_log("STTA $_[0]", "services", "$_[2]");
                    &webmin_log("STTA $text{$_[0]}","services","$_[1]");
                    &SrvError(); 
                }
             }
             if ( "$_[2]" ne "unknown" ) {
                   &webmin_log("STTA $text{$_[0]}","services","$_[1] - $_[2]");
             } else {
                   &webmin_log("STTA $text{$_[0]}","services","$_[1] - $text{unknown}");
             }
       } elsif ( "$_[0]" eq "status" && $_[3] ) {
             if ( $config{iferror_services} eq "stop" ) {
                if  ( "$_[2]" =~ /$respo/ || "$_[2]" eq "unknown"){ 
                    #
                } else {
                    $err_msg="$_[1]  $_[2]";
                    &additional_log("STTA $_[0]", "services", "$_[2]");
                    &webmin_log("STTA $text{$_[0]}","services","$_[1]");
                    &SrvError(); 
                }
             }
             if ( "$_[2]" ne "unknown"  ) {
                   ${$_[3]}.= "STTA: $_[1] == $_[2] \n";
             } else {
                   ${$_[3]}.= "STTA: $_[1] == $text{unknown} \n";
             }
       } else {
             if  ( "$_[2]" =~ /$respo/ || "$_[2]" eq "unknown"){ 
                   print "STTA:  $_[1] $text{OK} \n";
             } else {
                  if ( "$_[2]" ne "unknown" ) {
                      &webmin_log("STTA $text{$_[0]}","services","$_[1] - $_[2]");
                  } else {
                      &webmin_log("STTA $text{$_[0]}","services","$_[1] - $text{unknown}");
                  }
             }
       }
}

# wsplit(string)
# Splits a string like  foo "foo \"bar\"" bazzz  into an array of words
sub wsplit
{
local($s, @rv); $s = $_[0];
$s =~ s/\\\"/\0/g;
while($s =~ /^"([^"]*)"\s*(.*)$/ || $s =~ /^(\S+)\s*(.*)$/) {
	$w = $1; $s = $2;
	$w =~ s/\0/"/g; push(@rv, $w);
	}
return \@rv;
}

# wjoin(word, word, ...)
sub wjoin
{
local(@rv, $w);
foreach $w (@_) {
	if ($w =~ /^\S+$/) { push(@rv, $w); }
	else { push(@rv, "\"$w\""); }
	}
return join(' ', @rv);
}

# dir_name(struct)
sub dir_name
{
local($dfm, $mat);
$_[0]->{'name'} =~ /^(Directory|Files|Location)(Match)?$/;
$dfm = $1; $mat = $2;
if ($mat) { return "$dfm regexp <tt>$_[0]->{'words'}->[0]</tt>"; }
elsif ($_[0]->{'words'}->[0] eq "~")
	{ return "$dfm regexp <tt>$_[0]->{'words'}->[1]</tt>"; }
else { return "$dfm <tt>$_[0]->{'words'}->[0]</tt>"; }
}

# To check if host is alive in a defined port ....
# $_[0] is the host alias
# $_[1] if is true print title
sub check_host {

  local $aliasHost=$_[0];
  local $grpalias;
  local $grpname;
  local $title;
  local $port;
  local $hosts_status;

  if ( !%h_hosts ) { %h_hosts=&list_hosts(); };
  if (defined($h_hosts{$_[0]}) ) { 
      if ( !%h_grphosts ) { %h_grphosts=&list_grphosts(); };
  } else {
      return "";
  }
  $grpalias=$h_hosts{$_[0]}->{'grpalias'};
  $grpname=$h_grphosts{$grpalias}->{'name'};
  $title="$h_hosts{$_[0]}->{name} [$grpname] ($h_hosts{$_[0]}->{ipname})";
  if ( $_[1] eq "true" ) { print "<tr><td>$title</td></tr>\n"; }
  if ( $DebugFile ) { print DebugLog "$title \n"; }
  $hosts_status=&text('responding_on',$h_hosts{$_[0]}->{portalive});
  &check_socket($h_hosts{$_[0]}->{ipname}, $h_hosts{$_[0]}->{portalive}, $rv->{'fh'}, \$hosts_status);
  &webmin_log("$h_hosts{$_[0]}->{ipname} socket","ipalive","title=>$title||status=>$hosts_status||port=>$h_hosts{$_[0]}->{portalive}",$h_hosts{$_[0]});
  if ( $DebugFile ) { print DebugLog "$hosts_status \n"; }
  return "$hosts_status";
}

sub test_minfo
{
   local $task=$_[0];
   local $where=$_[1];
   local $outFormat=$_[2];

}

sub show_numbermoment
{
    my ($now);
    if ( !$_[0] ) { 
         $now = time();
    } else {
         $now=$_[0];
    }     
    local @tm = localtime($now);

return  sprintf "[%2.2d/%s/%4.4d %2.2d:%2.2d:%2.2d]",
        $tm[3], $tm[4]+1, $tm[5]+1900, $tm[2], $tm[1], $tm[0];
}

sub out_now_filename
{
    my ($now);
    if ( !$_[0] ) { 
         $now = time();
    } else {
         $now=$_[0];
    }     
    local @tm = localtime($now);

    return  sprintf "%4.4d_%2.2d_%2.2d_%2.2d%2.2d%2.2d",
                $tm[5]+1900, $tm[4]+1, $tm[3], $tm[2], $tm[1], $tm[0];
}

# run_cmd([str])
# Display an error message and exit. The variable $whatfailed must be set
# to the name of the operation that failed.
# OUTPUT is going to FILEOUT so can be send it to Webmin Log and Screen if $no_out=false
sub run_cmd
{
  local ($t_str);
  local ($line);
  local ($line_tempf);
  $exec_str = ($exec_str) ? $exec_str : "exec"; 
  $cmd_str = ($cmd_str) ? $cmd_str : "command"; 
  
  $err_msg="";
  $err="";
 
# return false when no output 
# return true printing output does not mean error it depends on command output
# no_out by default is 0 it means to print to screen, otherwise it will go only to LOG
# $config{output_cgis} eq 1

 $t_str=$str;
 $t_str=~s/ //g; 
 if ( !$str || $t_str eq "" ) { return "" };
      
        if ( $config{output_cgis} eq 1 ) { print $text{msg_processing}." <BR>"; }

        $| = 1;

        local $temp = &tempname();
        local $outfile = &tempname();
        local $line ="$str\n";

        open(FILEOUT, ">$outfile");
        open(TEMP, ">$temp");
        print TEMP "#!/bin/sh\n";
        print TEMP $env;
	print TEMP "export $export\n" if ($export);
	print TEMP "$str\n";
	close(TEMP);
	chmod(0777, $temp);
	$got = &foreign_call("proc", "safe_process_exec",
	   		     "su root -c $temp", 0, 0,
                              *FILEOUT, undef, 1,1);   
        if ( $config{output_cgis} eq 1 && $got ) { print "<pre>\n"; }
        if ( $debug eq 0 ) {
              system("rm -f $temp 2>/dev/null");
	      unlink($temp);
        }
        close(FILEOUT);
	open(FILEOUT, $outfile);
	while(<FILEOUT>) {
		s/\r|\n//g;
                if ( $config{output_cgis} eq 1 ) { print "$_ \n"; }
                $line .= "$_\n"; 
        }
        close(FILEOUT);
        if ( $debug eq 0 ) {
             system("rm -f $outfile 2>/dev/null");
	     unlink($outfile);
        }
        if ( $temp_f) {
             $line .= "\nfile: $temp_f :::::::::::::::::::::::\n"; 
	     open(TEMPF, $temp_f);
	     while(<TEMPF>) {
		     s/\r|\n//g;
                     $line .= "$_\n"; 
                     $line_timef .= "$_\n"; 
             }
             close(TEMPF);
        }
        if ( $ens_obj ) {
             &additional_log($str, $ens_obj, $line);
        } else { 
             &additional_log($str, undef, $line);
        }
        $line_timef=~s/"/'/g;
        $line_timef=~s/\n/\\/g;
        &webmin_log($exec_str, "$cmd_str", "$got||user=>".$config{run_exec_user}."||str=>$str||cmd=>$line_timef",undef);
#        if (!$got) { if ( $config{output_cgis} eq 1 ) { print "<i>$text{'run_noout'}</i>\n"; } }
        if ( $config{output_cgis} eq 1 && $got ) { print "<pre>\n"; }
        if (!$got) { return false;}
  return true;
}

# run_tta_cmd([type_cmd,ens_obj,temp_f])
# Display an error message and exit. The variable $whatfailed must be set
# to the name of the operation that failed.
sub run_tta_cmd
{
 $exec_str = "tta"; 
 $cmd_str = $type_cmd; 
 local $tta=$config{'tta_aliascmd'};

 if ( "$type_cmd" =~ /^no_run / ) {    # Fake call to avoid running comand not breaking code
       &webmin_log("tta $type_cmd", "$ens_obj", "$temp_f",undef);
       return true;
 }
 if ( $tta_ok ne true ) { return -1 };
 if ( "$type_cmd" eq "emulatorsession" ) {
     $temp_f = &tempname();
     $str=" $tta emulatorsession  list >$temp_f";
 }
 if ( "$type_cmd" eq "list" ) {
     $temp_f = &tempname();
     $tempf = &tempname();
     open(TEMPF, ">$tempf");
     print TEMPF "--name $ens_obj\n";
     close(TEMPF);
     $str=" $tta object list_contents --file $tempf >$temp_f";
 }
 if ( "$type_cmd" eq "attributes" ) {
     $temp_f = &tempname();
     $tempf = &tempname();
     open(TEMPF, ">$tempf");
     print TEMPF "--name $ens_obj\n";
     close(TEMPF);
     $str=" $tta object list_attributes --file $tempf >$temp_f";
 }
 if ( "$type_cmd" eq "delete" ) {
       $temp_f = &tempname();
       open(TEMPF, ">$temp_f");
       print TEMPF "$ens_obj\n";
       close(TEMPF);
       $str=" $tta object delete --file $temp_f";
 }
 if ( "$type_cmd" eq "new_person" ) { $str=" $tta object new_person --file $temp_f"; }
 if ( "$type_cmd" eq "new_host" )   { $str=" $tta object new_host --file $temp_f"; }
 if ( "$type_cmd" eq "new_group" )  { $str=" $tta object new_group --file $temp_f"; }
 if ( "$type_cmd" eq "new_container") { $str=" $tta object new_container --file $temp_f"; }
 if ( "$type_cmd" eq "new_charapp" ){ $str=" $tta object new_charapp --file $temp_f"; }
 if ( "$type_cmd" eq "new_xapp" )   { $str=" $tta object new_xapp --file $temp_f"; }
 if ( "$type_cmd" eq "new_webapp" ) { $str=" $tta object new_webapp --file $temp_f"; }
 if ( "$type_cmd" eq "new_windowsapp" ) { $str=" $tta object new_windowsapp --file $temp_f"; }
 if ( "$type_cmd" eq "edit" )       { $str=" $tta object edit --file $temp_f"; }
 if ( "$type_cmd" eq "new_orgunit") { $str=" $tta object new_orgunit --file $temp_f"; }
 if ( "$type_cmd" eq "passcache")   { $str=" $tta passcache edit --file $temp_f"; }
 if ( "$type_cmd" eq "new_group" )  { $str=" $tta object new_group --file $temp_f"; }
 if ( "$type_cmd" eq "del_link" )   { $str=" $tta object remove_link --file $temp_f"; }
 if ( "$type_cmd" eq "add_link" )   { $str=" $tta object add_link --file $temp_f"; }
 if ( "$type_cmd" eq "rename" )   { $str=" $tta object rename --file $temp_f"; }
 if ($str) {
    # For TTA no errors in output commands means  OK ... so change true/false !!! 
    local $tta_status_cmd=&run_cmd($str);
    if ( $debug eq 0 ) { 
         if ( "$type_cmd" ne "attributes" &&
                  "$type_cmd" ne "emulatorsession" &&
                  "$type_cmd" ne "list" ) {
                   system("rm -f $temp_f 2>/dev/null");
	           unlink($temp_f);
         }
         if ( "$type_cmd" eq "attributes" || "$type_cmd" eq "list" ) {
                   system("rm -f $tempf 2>/dev/null");
	           unlink($tempf);
         } 
    }
    if ( $tta_status_cmd eq true ) {
        return "";
    } else {
        return true;
    }
 }
 return -1;
}

# Several calls are acepted
# To get brand info from module.info  call ("stta")
# To check brand info for one file returns true or false 
#    if is wrong size, brand or stamp return false aunless "fix"
#     call ("fileName","fix" | "",1 [debugOn]) 
# 
# To check brand info for all file returns true or false 
#    if one is wrong stop unless "fix" 
#     call ("","fix" | "",1 [debugOn]) 
sub check_brand_data
{ 
    local @brandInfo=();
    local $brandData="";
    local %minfo=&load_minfo();
    local $status_chk=true;
    
    if ( $_[0] eq $module_name ) {
         return "$minfo{brand}";
    } elsif (  "$_[0]" ne "" && -r "$root_directory/$_[0]" ) {
         %h_brandInfo=&load_brandinfo();
         @brandInfo=&getfile_branddata($_[0]);
         local @st = stat("$root_directory/$_[0]");
         my $id=$brandInfo{$_[0]}[0];
         my $fidtime=$brandInfo{$_[0]}[1];
         if ( $h_brandInfo{$_[0]}->{'size'} ne $st[7] ||
              $h_brandInfo{$_[0]}->{'brand'} ne $id ||
              $h_brandInfo{$_[0]}->{'descrip'} ne $fidtime ) {
                  &webmin_log("brand_check", "$_[0]", "error||size=>$st[7]||id=>$minfo{version}$id||desc=>$fidtime",$h_brandInfo{$_[0]});
              if ( $_[1] eq "fix" ) {
                  &dump_brandinfo("",$_[0],$_[2])
             } else {
                  $status_chk=false;
             }
         }
    } elsif ( "$_[0]" eq "" ) {
       $status_chk = &check_brand_dir($module_name,$_[1],$_[2]);
       if ( $status_chk eq "false" &&  $_[1] ne "fix" ) { return $status_chk, }
       $status_chk = &check_brand_dir("$module_name/index",$_[1],$_[2]);
       if ( $status_chk eq "false" &&  $_[1] ne "fix" ) { return $status_chk, }
       $status_chk = &check_brand_dir("$module_name/shells",$_[1],$_[2]);
       if ( $status_chk eq "false" &&  $_[1] ne "fix" ) { return $status_chk, }
       $status_chk = &check_brand_dir("$module_name/tools",$_[1],$_[2]);
    }
    return $status_chk;
}

sub check_brand_dir
{ 
    local @brandInfo=();
    local $brandData="";
    %h_brandInfo=&load_brandinfo();
    local %minfo=&load_minfo();
    local $status=true;
    
    opendir(DIR, "$root_directory/$_[0]");
       foreach $f (readdir(DIR)) { 
              next if ( -d $f );
              if ( -r "$root_directory/$_[0]/$f" && $f =~ /\.(cgi|pl|sh|js|tcl)$/) {
                  $fpath="$_[0]/$f";
                  @brandInfo=&getfile_branddata($fpath); 
                  my  @st = stat("$root_directory/$fpath");
                  my $id=$brandInfo{$fpath}[0];
                  my $fidtime=$brandInfo{$fpath}[1];
                  if ( $h_brandInfo{$fpath}->{'size'} ne $st[7] ||
                       $h_brandInfo{$fpath}->{'brand'} ne $id ||
                       $h_brandInfo{$fpath}->{'descrip'} ne $fidtime ) {
                       &webmin_log("brand_check", "$fpath", "error||size=>$st[7]||id=>$minfo{version}$id||desc=>$fidtime",$h_brandInfo{$fpath});
                       if ( $_[1] eq "fix" ) {
                           &dump_brandinfo("",$fpath,$_[2])
                       } else {
                           $status_chk=false;
                           last;
                       }
                  }
              }
       }
    closedir(DIR);   
    return $status_chk;
}

sub getfile_branddata
{
  local @brandInfo=();
  local $brandData="";
  local $lineStamp="# stta: (@#) ";
  local $revLine="# STTA Rev. ";
  local $check_next=false;

   if ( -r "$root_directory/$_[0]" && $_[0] =~ /\.(cgi|pl|sh|js|tcl)$/) {
        $check_next=false;
        open(FILEDATA,"$root_directory/$_[0]");
	        while(<FILEDATA>) {
                      if ( $check_next eq true ) {
                         if ( $_  !=~ /^$lineStamp/ ) {
                              $brandData=$_;
                              $brandData=~s/^# stta: \(\@\#\) //;
                              $brandInfo{$_[0]} = &wsplit($brandData);
                         }
                         last;
                      }
                      if ( $_ =~ /^# STTA Rev. / ) { $check_next=true; }
                 }
         close FILEDATA;
    }
   return \@brandInfo;
}

# If the key is $_[0] || make a new one 
sub dump_brandinfo
{
  local ($id) = $_[0] || "";
  $brandDataFile="$root_directory/$module_name/.brandinfofile";
  local %minfo=&load_minfo();

  if ( ! $id || $id eq ""  ) {
       # first make a new key !!!
       local $now = time();
       local @tm = localtime($now);
       local $line_tm = sprintf "[%2.2d/%s/%4.4d %2.2d:%2.2d:%2.2d]",
             $tm[3], $tm[4]+1, $tm[5]+1900,
             $tm[2], $tm[1], $tm[0];
       local %minfo=&load_minfo();
       $id = sprintf "%s-%s", $minfo{version}.$now;
  } else {
         local $now=$id;
         $now =~ s/^$minfo{version}//g;
  }
  local $fnow=&out_now_filename($now);
  if ( $_[1] ne ""  && -r "$root_directory/$_[1]" ) {
       &setfile_branddata($_[1],$id." [$fnow]");
       local @st = stat("$root_directory/$_[1]");
       if (  $h_brandInfo{$fpath}->{fname} eq $_[1] ) {
             open(BRANDFILE, "$brandDataFile");
               @ary = <BRANDFILE>;
             close BRANDFILE;
             open(OUTFILE, ">$brandDataFile");
             foreach $line (@ary) {
                  @dataline=split(/::/,$line, -1);
                  if ( $_[1] eq $dataline[0] ) {
                       print OUTFILE $_[1]."::".$id."::".$st[7]."::[".$fnow."]::\n";
                  } else {
                       print OUTFILE $line;
                  }
             }              
             close (OUTFILE);
       } else {
             open(OUTFILE, ">>$brandDataFile");
                  print OUTFILE $_[1]."::".$id."::".$st[7]."::[".$fnow."]::\n";
             close (OUTFILE);
       }
       if ( $_[2]  eq 1 && $debug gt 2) { print "$text{brandedwith}  $id $fnow\n"; }
  } elsif ( "$_[1]" eq "" ) {
         &webmin_log($config{'brand_list'}, "code", "brand",$brandInfo);
         &lock_file($brandDataFile);
         &dump_brandinfo_dir($id,$fnow,"$module_name",$_[2]); 
         &dump_brandinfo_dir($id,$fnow,"$module_name/index",$_[2]); 
         &dump_brandinfo_dir($id,$fnow,"$module_name/shells",$_[2]); 
         &dump_brandinfo_dir($id,$fnow,"$module_name/tools",$_[2]); 

         &unlock_file($brandDataFile);
         $str=$text{'user_made'}." ".$ext{brand_title},"\n";
         &additional_log('branding', "brand", $str);
         local %minfo=&load_minfo("$root_directory/$module_name/");
         $minfo{brand}=$id;
         $minfo{stamp}=$fnow;
         &write_file("$root_directory/$module_name/module.info", \%minfo);
  }
}


sub dump_brandinfo_dir
{
  local ($id) = $_[0] || "";
  local ($fnow) = $_[1] || "";
  $brandDataFile="$root_directory/$module_name/.brandinfofile";
  local %h_allbrandInfo=();
  local @list__brandfs, @listaf;

         opendir(DIR, "$root_directory/$_[2]");
             if ( $_[3]  eq 1 && $debug gt 2) { print "$text{brandedwith}  $id $fnow\n"; }
             foreach $f (readdir(DIR)) { 
                next if ( -d $f );
                if ( -r "$root_directory/$_[2]/$f" && $f =~ /\.(cgi|pl|sh|js|tcl)$/) {
                    &setfile_branddata("$_[2]/$f",$id." [$fnow]");
                    local @st = stat("$root_directory/$_[2]/$f");
                    $h_allbrandInfo{$f} = {
                                    'fname' => "$_[2]/$f",
                                    'brand' => $id,
                                    'size' => $st[7],
                                    'descrip' => $fnow
                                    };
                }
             }
         closedir(DIR);   
         foreach $item (keys (%h_allbrandInfo)) {push (@listaf,$h_allbrandInfo{$item});}
         @list__brandfs = sort {$a->{'fname'} cmp $b->{'fname'}} @listaf;
         open(BRANDFILE, ">$brandDataFile");
         foreach $brandf (@list__brandfs) {
              $linbrandf=$brandf->{'fname'}."::".$brandf->{'brand'}."::".
                      $brandf->{'size'}."::[".$brandf->{'descrip'}."]::\n";
              print BRANDFILE $linbrandf;
         }
         close BRANDFILE;
}

# Branding one file $_[0] with  $_[1] key 
sub setfile_branddata
{
  local $brandData="";
  local $lineStamp="# stta: (@#) ".$_[1];
  local $revLine="# STTA Rev. ";
  local $check_next=false;

        $check_next=false;
        my $fileNameW=&tempname();
        $fileName="$_[0]";
        $check_next=false;
        open(OUTFILE, ">$fileNameW");
        open(FILEIN, "$root_directory/$fileName") || return -1 ;
        while(<FILEIN>) {
             if ( $check_next eq true ) {
                   if ( $_  =~ /^# stta: \(@#\) / ) {
                       print OUTFILE $lineStamp."\n";
                   } else {
                       print OUTFILE $lineStamp." \n";
                       print OUTFILE $_;
                   }
                   $check_next=false;
              } else {
                  print OUTFILE "$_";
              }
              if ( $_ =~ /^# STTA Rev. / ) { $check_next=true; }
        }
        close(FILEOUT);
        close(INFILE);
        system("mv $fileNameW $root_directory/$fileName");
        system("chmod 755 $root_directory/$fileName");
        if ( $_[0] && $debug gt 2) { print "$fileName\n"; }
        return 0;
}

sub load_more_text
{
     local $module_dir="$root_directory/stta";
     foreach $l (@lang_order_list) {
                     &read_file("$module_dir/lang/$_[0]/$l", \%text);
                     }
     foreach $k (keys %text) {
             $text{$k} =~ s/\$([A-Za-z0-9\.\-\_]+)/text_subs($1,\%text)/ge;
             }
}

sub make_dir_ifnot
{
     return if ( ! $_[0] || $_[0] eq "" );
     local @dataline=split(/\//,$_[0], -1);
     local $dirname=$_[0];

     if ( $#dataline > 0 ) { $dirname =~ s/$daltaline[$#dataline]//; }
     if ( ! -d $dirname ) { system("mkdir -p $dirname")  }
}

#list_servers()
# Returns a list of all servers from the webmin servers module that can be
# managed, plus this server
sub list_servers
{
     local %rv=();
     local $i=0;
     local $srvCfgPath="$config_directory/servers";

       opendir(DIR, "$srvCfgPath");
            foreach $f (readdir(DIR)) {
                # read the help file
                next if ( -d "$srvCfgPath/$f" );
                %srvcfg=();
                if ( $f =~ /\.serv$/ ) { &read_file("$srvCfgPath/$f", \%srvcfg); }
                next if ( !$srvcfg{id} || $srvcfg{id} eq "" );
                next if ( $config{stta_hosts} =~ /$servcfg{host}/ );
                $rv{$srvcfg{'host'}} =  { 'id' => $srvcfg{'id'},
                              'host' => $srvcfg{'host'},
                              'desc' => $srvcfg{'desc'},
                              'port' => $srvcfg{'port'},
                              'ssl' => $srvcfg{'ssl'},
                              'user' => $srvcfg{'user'},
                              'pass' => $srvcfg{'pass'},
                              'type' => $srvcfg{'type'} };
                $i++;
            }
      closedir(DIR);
  return %rv
}

sub get_ttaversion
{
        open(TTAVERSFILE, "$config{tta_dir}/bin/version");
        local @ttavers = <TTAVERSFILE>;
        close TTAVERSFILE;
        local $ttaversLine="";
        foreach $line (@ttavers) {
		$line =~ s/\r|\n//g;
                if ( $ttaversLine ne "" ) { $ttaversLine .=  " - "; }
                $ttaversLine .=  $line;
        }
        return $ttaversLine;
}

# stringClip $string,[full,lead,last]
sub stringClip
{
   local $i=0, $strLong=length($_[0]), $lastPos=$strLong;

   if ( $_[1] ne "lead" ) { while ( substr($_[0],$lastPos--) =~ / / ) { } }
   if ( $_[1] eq "last" ) { return substr($_[0],0,$lastPos-1); }
   while ( substr($_[0],$i++) =~ /^ / ) { } 
   if ( $_[1] eq "lead" ) { return substr($_[0],$i-1,$strLong-$i+1) }
   # print "$i - $lastPos\n";
   if ( $_[1] eq "full" ) { return substr($_[0],$i-1,$lastPos-$i) }
}

sub check_brand_cgi
{
      my $cginame=$0 =~ /([^\/]+)$/ ? $1 : '-';
      my $cgi_obj=$cginame;
      my $cgiPath=$module_name."/".$cginame;
      if ( $cgi_obj =~ /stta_warn/ ) { return } ;
      my %h_brandInfo=&load_brandinfo();
      $cgi_obj=~ s/.cgi//;  
      my  @st = stat("$root_directory/".$h_brandInfo{$cgiPath}->{fname});
      if ( $st[7] ne $h_brandInfo{$cgiPath}->{'size'} ) {
           my $msg=&text("msgerr_brandfilesize",$cginame,$st[7],$h_brandInfo{$cgiPath}->{'size'}); 
           &redirect("stta_warn.cgi?cgi=$cginame&msg=$msg"); 
      } 
      if ( &check_brand_data($h_brandInfo{$cgiPath}->{fname}) eq "false" ) {
            my $msg=&text("msgerr_brandfile",$cginame); 
            &redirect("stta_warn.cgi?cgi=$cginame&msg=$msg"); 
      }
      foreach $item (keys (%h_brandInfo)) {
           if ( $item =~ /.pl/ ) {
              @st = stat("$root_directory/".$h_brandInfo{$item}->{fname});
              if ( $st[7] ne $h_brandInfo{$item}->{'size'} ) {
                   my $msg=&text("msgerr_brandfilesize",$item,$st[7],$h_brandInfo{$item}->{'size'}); 
                   &redirect("stta_warn.cgi?cgi=$cginame&msg=$msg"); 
              } 
              if ( &check_brand_data($h_brandInfo{$item}->{fname}) eq "false" ) {
                   my $msg=&text("msgerr_brandfile",$item); 
                   &redirect("stta_warn.cgi?cgi=$cginame&msg=$msg"); 
              }
           }
      }
}
1;  # Return true  
