#!/usr/bin/perl 
use strict;

my $BIBLIST_VERSION = '1.2';

my @REFS_FILES = ('refers.db');

my @REFS;      
$REFS[0]='';

my @ALLREFS;
my %REFSORDERED;
my %ALLFORMATSTRINGS;
my $CITE_FORMAT;my $REF_FORMAT;

my $ORDERING=''; #must contain key-field, like AUTHORL, or TITLE

my $reservedLABEL='LABEL';
my $reservedTYPE ='TYPE' ;
my $reservedURL='URL';


my $reservedAUTHOR ='AUTHOR'; #must be in the form '5;' - 5=five authors must be shown.
                              #                          ';'=1st author from the 2nd should be separated by ';'
my $reservedAND_SEPARATOR='|'; #what have to be put before the last author goes after this!!!
my $reservedET_AL='{ \it{et al}}'; #if number of authors more than shown will be added after the last one.


my $reservedDOLLAR = '$';
my $reservedARRAYSEP = '|';
my $reservedCOMMENTSYMBOL = '%';
my $SEPARATOR = "----------\n";

my $reservedHASH_KEY = 'HASH_KEY_'; 
my $reservedEMTY_FIELD_SIGN = '???';  #will be written instead of emty fields
my $reservedNONUMBER = 'NONUMBER';  # if NONUMBER is given in the ref_format or cite_format, then no number will be put in the output.
                                    # for example
                                    # Normally:  [4] Author, F.M. Interesting Articles' Journal
                                    # NONUMBER       Author, ....
#--------------------------------------
my $BIBITEM = '%'."\n".'\item'."\n".'% {';

my $reservedBEGINBIBLIO='begin{biblio}';  #options for biblio starts like this
my $reservedENDBIBLIO  ='end{biblio}';    #and end like this!
my $reservedLEFTSTART  ='[';              #TYPE[FORMAT_STRING]
my $reservedRIGHTEND   =']';              #so, example:
  # ARTICLE[$AUTHOR0FL, M; $/  {\bf $YEAR$}, $VOL$] 
my $reservedCITE_FORMAT='cite_format=';  #must be in the form cite_format=^{%s}
my $reservedREF_FORMAT ='ref_format=';   # the same
my $reservedORDERING   ='ordering=';     #must be in the form ordering=AUTHORL. If no this field is given, then "asis" implied
my $reservedS_STRING   ='%s';
my $reservedS_STRING1  ='\%s';
my $reservedSTANDARD_CITE_FORMAT = "[$reservedS_STRING]";   # default values
my $reservedSTANDARD_REF_FORMAT  = "[$reservedS_STRING]";   # for references formats

my %HASH_REFS;  #CHANGE IT LATER!!!

my $verbosity_level=1;   # 5 is max
my $optionsINSERT_EMPTY_FIELDS_SIGN = 1;
my $optionsKEEP_BIBITEM_AND_CITE    = 1; 
my $optionsHTML_OUTPUT = 0; 

my $optionsABBREVIATIONS =0; # use abbreviations tex-file 

my $httpprefix='';

my $OUT_TEX  ='';   #'allrefs.tex';
my $FORMAT_NAME ='';#'macromolecules';#$TEX_NAME;  # file where all rules are!
my $ABBR_NAME = 'abbr.tex';  #abbreviations file

##############################################3


&read_inline_arguments;
&check_for_important_arguments;

if ($verbosity_level > 0)
{print "\nThis is biblist utility version $BIBLIST_VERSION\n";
    print 'Author R.Stepanyan <rstepanyan@yahoo.com>',"\n\n"};
print "output file is     <$OUT_TEX>;\n";
print "formats are in     <$FORMAT_NAME>;\n"; 
print 'refs databases are <';
foreach my $qq (@REFS_FILES) {print "$qq "};
print ">.\n\n";

my $REFS_FILE;
foreach  $REFS_FILE (@REFS_FILES)
{ 
  &make_list_of_refs_in_dbase($REFS_FILE);  #makes list of all refs in @REFS
  if($verbosity_level > 4)
    {print "read_ref_datafile <$REFS_FILE> first time: done...\n";}
};


my $i=0;
for($i=0; $i<scalar(@REFS); $i++)
{
    $REFS[$i] = $REFS[$i+1]; 
};
$#REFS--; #now $REFS[0] is also used!!!!

&read_formats_and_speak_to_me; 


foreach  $REFS_FILE (@REFS_FILES)
{ #print $REFS_FILE, "-------\n";
  &read_ref_datafile($REFS_FILE);  # all data will be stored in @ALLREFS - array of hashes
  if($verbosity_level > 4)
    {print "read_ref_datafile <$REFS_FILE> done...\n";}
};
if($verbosity_level > 4){print "\n";}

&order_this_list;
if($verbosity_level > 4)
    {print "ordering of refs is done...\n";}


if($optionsHTML_OUTPUT)
{
   open(OUTTEX, "> $OUT_TEX");
   print OUTTEX '<html>',"\n";
   print OUTTEX '<head>',"\n";
   print OUTTEX ' <meta HTTP-EQUIV="Content-Type" CONTENT="text/html; charset=iso-8859-1">',"\n";
   print OUTTEX ' <meta NAME="Generator" CONTENT="biblist.pl">',"\n";
   print OUTTEX ' <title>The bibliography list</title>',"\n";
   print OUTTEX '</head>',"\n";
   print OUTTEX '',"\n";
   &insert_abbreviations_of_journals;
   print OUTTEX '<dl compact><dd>',"\n";
   &print_all_references_into_tex_in_html_format;
   print OUTTEX '</dl>',"\n";
   print OUTTEX '',"\n";
   print OUTTEX '',"\n";
   print OUTTEX '',"\n";
   print OUTTEX '',"\n";
   print OUTTEX '',"\n";
   print OUTTEX '',"\n";
   print OUTTEX '</html>',"\n";
   close(OUTTEX);

}
else
{
   open(OUTTEX, "> $OUT_TEX");

   print OUTTEX '\documentstyle[12pt,a4]{article}',"\n";
   #print OUTTEX  '\documentstyle[aps,manuscript]{revtex}',"\n";
   print OUTTEX  '\title{List of references \\\ Generated by "biblist.pl"}',"\n";
   print OUTTEX  '\date{\today}',"\n";
   print OUTTEX  '\begin{document}\maketitle',"\n";
   
   &insert_abbreviations_of_journals;

   print OUTTEX  'This list of references is generated from the following data-files:\newline',"\n",'\begin{center}{\it{';
   for(my $RI=0; $RI<scalar(@REFS_FILES);$RI++)
   { if($RI+1<scalar(@REFS_FILES)){print OUTTEX "$REFS_FILES[$RI], "}
     else {print OUTTEX "$REFS_FILES[$RI]"};
   };
   print OUTTEX  '}}\end{center}',"\n";
   #print OUTTEX '\begin{thebibliography}',"\n";
   print OUTTEX  '\newcounter{bibliocounterrr}';
   print OUTTEX  '\begin{list}';
   print OUTTEX  '{\bfseries\upshape', '\arabic{bibliocounterrr}}';
   print OUTTEX  '{\usecounter{bibliocounterrr}',"\n";
   print OUTTEX  '\setlength{\labelwidth}{1cm}\setlength{\leftmargin}{0cm}',"\n";
   print OUTTEX  '\setlength{\labelsep}{0.5cm}\setlength{\rightmargin}{0cm}',"\n";
   print OUTTEX  '\setlength{\parsep}{0.5ex plus0.2ex minus0.1ex}',"\n";
   print OUTTEX  '\setlength{\itemsep}{1ex plus0.2ex}',"\n"; 
   print OUTTEX  '%\slshape',"\n";
   print OUTTEX  '}',"\n";
   &print_all_references_into_tex_in_bibitem_format;
   print OUTTEX '\end{list}',"\n";
   #print OUTTEX '\end{thebibliography}',"\n";

   print OUTTEX  '\end{document}';
   close(OUTTEX);
}


exit(0);








################################################
sub print_all_references_into_tex_in_html_format
{ my ($item1, $item); my $thecounter=1; 
  #print OUTTEX '%Generated by biblio',"\n";
  for(my $i=0;$i<scalar(@REFS);$i++)
  {$item  = @REFS[$i];
    foreach $item1 (@ALLREFS)  #loop 1
     {if($item eq ${$item1}{"$reservedLABEL"}) 
       { my $thetype=uc(${$item1}{"$reservedTYPE"}); # IN THE UPPER CASE!
	 if($ALLFORMATSTRINGS{"$thetype"} eq '') 
	 {  print OUTTEX '<dt>  <a name="',${$item1}{"$reservedLABEL"} ,'">',$thecounter,'</a></dt>',"\n";
            $thecounter++;
            print OUTTEX "No format string for TYPE \"$thetype\". Skipping record \"$item\"!\n";
            print STDERR "No format string for TYPE <$thetype>. Skipping record <$item>!\n";
	     last;
	 };
     
         
         print OUTTEX "\n",'<dt>  <a name="',${$item1}{"$reservedLABEL"} ,'">',$thecounter,'</a></dt>',"\n";
	 $thecounter++;
	 #print $thetype,"-->",$ALLFORMATSTRINGS{"$thetype"}, "\n";
         
         print OUTTEX '<dd> ';   
	 &formated_output($ALLFORMATSTRINGS{"$thetype"},%{$item1}); #CHANGE $FORMAT_STRING1 HERE!!!
	 if(${$item1}{"$reservedURL"} ne '')
          {
             print OUTTEX '<br><a href="';
             my $theurl=${$item1}{"$reservedURL"};
             if($theurl =~ m/http:\/\//)
                 {print OUTTEX $theurl,'">';}   
             else{print OUTTEX $httpprefix,$theurl,'">';} 
             print OUTTEX ${$item1}{"$reservedURL"};
             print OUTTEX '</a>';  
          };      
         print OUTTEX '<br> &nbsp; </dd>',"\n";
	 #next;
       
	 last; #this is last for loop 1
       }
     };
     
  }; 
  #print OUTTEX '%',"\n",'%End of Generated by biblio',"\n";  
  
}
#-----------------------------------------------------------
sub print_all_references_into_tex_in_bibitem_format
{ my ($item1, $item); 
  print OUTTEX '%Generated by biblio',"\n";
  for(my $i=0;$i<scalar(@REFS);$i++)
  {$item  = @REFS[$i];
    foreach $item1 (@ALLREFS)  #loop 1
     {if($item eq ${$item1}{"$reservedLABEL"}) 
       { my $thetype=uc(${$item1}{"$reservedTYPE"}); # IN THE UPPER CASE!
	 if($ALLFORMATSTRINGS{"$thetype"} eq '') 
	 {  print OUTTEX $BIBITEM,$item,'}',"\n";
            print OUTTEX "No format string for TYPE \"$thetype\". Skipping record \"$item\"!\n";
            print STDERR "No format string for TYPE <$thetype>. Skipping record <$item>!\n";
	     last;
	 };
     
         print OUTTEX $BIBITEM,$item,'}',"\n"; #,$CITE_FORMAT;
	 
	 #print $thetype,"-->",$ALLFORMATSTRINGS{"$thetype"}, "\n";
            
	 &formated_output($ALLFORMATSTRINGS{"$thetype"},%{$item1}); #CHANGE $FORMAT_STRING1 HERE!!!
	 print OUTTEX "\n";
	 #next;
       
	 last; #this is last for loop 1
       }
     };
     
  }; 
  print OUTTEX '%',"\n",'%End of Generated by biblio',"\n";  
  
}
#-----------------------------------------------------------
sub order_this_list
{   #??? TO BE DONE!!!!!!! 
    #for(my $i=0; $i<scalar(@REFS); $i++){ print "$i ->>> $REFS[$i] --\n"};
    
    unless($ORDERING eq '')
    {    
       my $do_ordering=1;
       while($do_ordering)
       {   $do_ordering=0;
	   for(my $i=1; $i<scalar(@REFS); $i++)
	   {
	       if(&keyfield($REFS[$i-1]) gt &keyfield($REFS[$i]) ) 
	        {($REFS[$i-1], $REFS[$i]) = ($REFS[$i], $REFS[$i-1]); $do_ordering =1 }
	   }
       };
    };
    
    for(my $i=0; $i<scalar(@REFS); $i++){ $REFSORDERED{"$REFS[$i]"} = $i+1};
    #foreach $item (keys %REFSORDERED){ print  $item,"--->",$REFSORDERED{"$item"},"\n"}
};

sub  keyfield
{
    my $a = @_[0];
    
    foreach my $item (@ALLREFS) 
    { 
	#   print ${$item}{"LABEL"},"-->",${$item}{"VOL"},"\n"; 
	if(${$item}{"$reservedLABEL"} eq $a) {return uc(${$item}{"$ORDERING"})}
    };    
    return '';
};
#---------------------------------------------------
sub read_ref_datafile 
#________________________________________________ 
#reads references file. Data stored in @ALLREFS
#structure of the refs-file:
#LABEL=3dFlex
#TYPE=article
#AUTHORL=subbotin
#TITLE={Microphase separation within comb-like copolymer with attractive  side-chains: computer simulations1.}
#JOURNAL=   Macromol. Theory and Simul1.
#----------<10pieces>
#
#At the end should be Enter, so better to put EOF after it in the
#next line
#
{ my $current_ref_number=0; my $line;
  my @fields; my %CURRENT_RECORD;

  my $it_is_label=1; my $save_current_field=0;
 
  my $item;
  my $REFS_FILE = @_[0];
  
  open(RF, $REFS_FILE)|| die "Could not open $REFS_FILE: $!";
  while($line = <RF>)
  {   next if $line =~ /^\s*$/; # skip blank lines
      next if (substr(trim($line),0,1) eq $reservedCOMMENTSYMBOL);
      if($line ne $SEPARATOR)
      {
        $line=trim($line);
        @fields = split(/=/, $line);

        @fields = trim(@fields);
        
        if($fields[0] eq $reservedLABEL)
        {
	    foreach $item (@REFS) 
            { if($item eq $fields[1]) #this label is in REFS
               { $save_current_field = 1 } 
            }
        };
        
        if($save_current_field)
	{ if($fields[0] eq $reservedLABEL){$CURRENT_RECORD{$fields[0]} = $fields[1]; }
	  else
	  {
	      if($CURRENT_RECORD{$fields[0]} ne '')
	      {
		  $fields[1]=trim($fields[1]);
		  $CURRENT_RECORD{$fields[0]}="$CURRENT_RECORD{$fields[0]}$reservedARRAYSEP$fields[1]" ;	      
	      }
	      else
	      {$CURRENT_RECORD{$fields[0]} = trim($fields[1]); }
	  };    
              #MUST change it to read fields with many '=' in the body text!!!
          #print "$fields[0] == $CURRENT_RECORD{$fields[0]}\n";
        }
      }
      else
      {
	if($save_current_field)
	{  %{$ALLREFS[$current_ref_number]} = %CURRENT_RECORD;  
	# Now erase everything from the hash!!!
	   my @allkeysfromhash = keys %CURRENT_RECORD;
           foreach $item (@allkeysfromhash){delete($CURRENT_RECORD{$item})};
	   
           $current_ref_number++; #print "-------\n";
        };
        $save_current_field = 0;
      }; 
  };
  close(RF);
};

#----------------------------------------------------------
sub read_formats_and_speak_to_me
#calls read_format_string  and also produces output about results
{
&read_format_strings;
if($verbosity_level > 3)
{print "\nread_format_strings from <$FORMAT_NAME> done...\n\n";
 printf("%16s | %s\n","TYPE","FORMAT STRING");
 printf("%15s--+-%s\n","---------------","---------------------------------------------------");
 foreach my $key (keys %ALLFORMATSTRINGS)
   { printf("%16s | %s\n",$key,$ALLFORMATSTRINGS{$key})};
 for(my $i=0;$i<70;$i++){print "-";};print "\n";
};
if($CITE_FORMAT eq '')
{ print STDERR "Citation format not found or wrong in <$FORMAT_NAME>. Assuming default!\n";
  $CITE_FORMAT = $reservedSTANDARD_CITE_FORMAT
};
if(uc($CITE_FORMAT) eq $reservedNONUMBER){$CITE_FORMAT='';}; #????????
if($REF_FORMAT  eq '')
{ print STDERR "Citation reference format not found or wrong in <$FORMAT_NAME>. Assuming default!\n";
  $REF_FORMAT  = $reservedSTANDARD_REF_FORMAT
};

#print "$CITE_FORMAT  $REF_FORMAT \n";
if($verbosity_level > 0)
 {   print "\n!!! Citation format:$CITE_FORMAT. Reference format=$REF_FORMAT.\n    Ordering:";
     if($ORDERING eq ''){print "as is\n\n"}else {print " key field is <$ORDERING>\n\n"} 
 };

}

#----------------------------
sub read_format_strings
# this function reads formats for references from file $FORMAT_NAME
# this can be just header in the decument (tex-file) or separate file!
{my $line='';
 my $start_interpreting=0; # 0 - not started yet
                           # 1 - interpreting
  
 my @justarray; 

    if($verbosity_level > 3){print "Format strings are in <$FORMAT_NAME>\n\n"}

    open(FRM, "$FORMAT_NAME") || die "Could not open $FORMAT_NAME: $!";
    while(<FRM>)
    {   my $hash_key=''; my $hash_value='';
	$line = $_; #print $line;
        $line = trim($line);
        next if $line =~ /^\s*$/; # skip blank lines
        next if (substr(trim($line),0,1) ne $reservedCOMMENTSYMBOL);
                 #skip lines, starting NOT from %
        next if (substr(trim($line),0,2) eq "$reservedCOMMENTSYMBOL$reservedCOMMENTSYMBOL");
        $line = substr(trim($line),1);
        $line=trim($line);
        next if $line =~ /^\s*$/;
        if($line eq $reservedBEGINBIBLIO){$start_interpreting=1;next;};
        if($line eq $reservedENDBIBLIO){ close(FRM); return;};

           
        if(not $start_interpreting){next;};

          #OK, now no shit in this line!  
        if($verbosity_level > 4){print $line," is read from <$FORMAT_NAME>\n";};
        @justarray=split(//,$line);

        #try to find if this is "cite_format" or "ref_format"
        my $format='';
        ($format) = ($line =~ /$reservedCITE_FORMAT([^,\n]*)/); 
        if($format ne '')
	   {if(($format =~ m/$reservedS_STRING1/)||($format =~/$reservedNONUMBER/))    
              { $CITE_FORMAT = $format; 
                if($verbosity_level > 4){print "Citation format=$format\n\n";}
                next;
	      }
	    else
	     {print STDERR "Unknown citation format \"$format\". Assuming standard=",
                            "$reservedSTANDARD_CITE_FORMAT\n";
              $CITE_FORMAT = $reservedSTANDARD_CITE_FORMAT ; next;
             }
           }  ;
         # now try to find "ref_format" 
        ($format) = ($line =~ /$reservedREF_FORMAT([^,\n]*)/); 
        if($format ne '')
	   {if($format =~ m/$reservedS_STRING1/)    
              { $REF_FORMAT = $format; 
                if($verbosity_level > 4){print "Citation reference format=$format\n\n";};
                next;
	      }
	    else
	     {print STDERR "Unknown reference format \"$format\". Assuming standard: ",
                            "$reservedSTANDARD_REF_FORMAT\n";
              $REF_FORMAT = $reservedSTANDARD_REF_FORMAT ; next;
             }
           }        
        ($format) = ($line =~ /$reservedORDERING([^,\n]*)/); 
	if($format ne '') 
	   {$ORDERING = trim($format); 
	    if($verbosity_level > 4){print "Key field for refs ordering=$ORDERING\n\n";}; 
	    next;
	   } ;
	
	my $this_is_key=1;
	
        my $narray=scalar(@justarray);
        for(my $i=0;$i< $narray-1; $i++)
        { 
	    if(($this_is_key)&&($justarray[$i] eq $reservedLEFTSTART))
                {$this_is_key = 0; next;};
          if($this_is_key)
            {$hash_key ="$hash_key$justarray[$i]";} 
	  else
            {$hash_value = "$hash_value$justarray[$i]"}
     	};
        if($justarray[$narray-1] ne $reservedRIGHTEND)
          {
            print STDERR "Format string \"$line\" must end with \"$reservedRIGHTEND\"!\n";
            print STDERR "This is fatal error. Exiting...";
            exit(1);
          };
        $hash_key=trim($hash_key);
        #now analize $hash_key. It must be puur symbolic!
        unless($hash_key=~ /^[A-Za-z0-9]+$/)
          {print STDERR "Key field \"$hash_key\" in  \"$line\" must include only A-Z,a-z,0-9\n";
           print STDERR "This is fatal error. Exiting...";
           exit(1);
          };
      
        my $hash_key1=uc($hash_key);

        if (($hash_key1 ne $hash_key)&&($verbosity_level>2))
           {print " WARNING!!! Key field\n   \"$hash_key\" in \"$line\"\n converted to uppercase!!!\n"};
        $ALLFORMATSTRINGS{$hash_key1} = $hash_value;
        
    };
    close(FRM);


};
#--------------------------------------
sub make_list_of_refs_in_dbase

#
{ my $current_ref_number=0; my $line;
  my @fields; my %CURRENT_RECORD;

  my $it_is_label=1; my $save_current_field=0;
 
  my $item;
  my $REFS_FILE = @_[0];
  
  open(RF, $REFS_FILE)|| die "Could not open $REFS_FILE: $!";
  while($line = <RF>)
  {   next if $line =~ /^\s*$/; # skip blank lines
      next if (substr(trim($line),0,1) eq $reservedCOMMENTSYMBOL);
      if($line ne $SEPARATOR)
      {
        $line=trim($line);
        @fields = split(/=/, $line);

        @fields = trim(@fields);
        
        if($fields[0] eq $reservedLABEL)
        {
	    my $REFS_N = scalar(@REFS);
            if(scalar(@fields)>2)
            {  for(my $i=2;$i<scalar(@fields);$i++)
	       {$fields[1] = "$fields[1].$fields[$i]"}
	    };
            $REFS[$REFS_N] = $fields[1];
        };
       }; 
  };
  close(RF);
};

#------------------------------------------------------------

sub formated_output
# takes format string in the form
# $FORMAT_STRING ='$AUTHOR5F L;$ {\bf $YEAR$}, $VOL$ - $NUMBER$' ; 
# and hash
# of the type
# my %HASH_REFS= ('AUTHOR' => 'Stepanyan',
#                 'YEAR'   => '2000',
#                 'VOL'    => '12',
#                 'RT'     => 'qq');  
# of course fields in hash can be any.
# Then makes output of the hash into stdout
# according to the format string.
# File with file handle OUTTEX must be opened for writing!!!!
{
my @in_arguments = @_;  #take all arguments of this function

my $FORMAT_STRING=$in_arguments[0]; # the first MUST be the format string

my %HASH_REFS;  #all the rest of arguments 
                #must be put into this hash

my $i; #next lines make hash from array
for($i=1;$i<scalar(@in_arguments)-1;$i=$i+2)
{ $HASH_REFS{$in_arguments[$i]} = $in_arguments[$i+1]
};


my @format_char_array; # all chars from the format string 
my @format_array;      # if format_string='$AUTHOR$ {\bf 2}'
                       # then format array will be
                       # ('HASH_KEY_AUTHOR',' {\bf 2}')

@format_char_array = split(//, $FORMAT_STRING);

my $start_flag = 0; # when I see $ I do $start_flag=1
                    # when I see it again I do     =0
                    # I do it to cath al $xxxx$ things!  

my $counter=0;      # just counter for the @format_array
			      

my $char;

###print "-----\n";
foreach $char (@format_char_array)
{
    ###print "$char\n";
    if($char ne $reservedDOLLAR) # if it is NOT '$'
    { # add this char and don't bother yourself with it! 
      $format_array[$counter] = $format_array[$counter] . $char;
    }     
    else   # oooh, this is '$'
    { 
      if($start_flag == 0){$start_flag = 1}   #if it is start of command
      else{$start_flag = 0};                  #if it is end of command
      $counter++;
      if($start_flag == 1)                    #if this will be command 
                           #add HASH_KEY before the name of it!
         {$format_array[$counter] = $reservedHASH_KEY;};
      
    }
};
###print "-----\n";
###foreach $char (@format_array)
###{ print "|$char|\n"};

my $char1; my $post_author='';

my @author_fields; 
my $last_sep=''; # 'R.R.Stepanyan',$last_sep,'A.A.Subbotin' - example
my   @author_name_key; my @author_seps;

foreach $char (@format_array) 
{   ($char1) = ( $char =~ /$reservedHASH_KEY([^}]*)/ );
    # $char1=trim($char1);
    #$char=trim($char);
    $#author_fields = -1;
    if($char1 ne '')
    { if((not($char1 =~ m/$reservedAUTHOR/))&&($HASH_REFS{$char1} eq '')) #this is not author 
	# and this field is empty
      { if($optionsINSERT_EMPTY_FIELDS_SIGN)
          {print OUTTEX $reservedEMTY_FIELD_SIGN}; #OUTTEX is opened!
        if($verbosity_level > 1) #complain about absence of field
	  {print STDERR "Field <$char1> in the record <$HASH_REFS{$reservedLABEL}> is empty!\n"};
      }
      elsif($char1 =~ m/$reservedAUTHOR/)      
      { ($post_author) = ($char1 =~ /$reservedAUTHOR([^\$]*)/); # what if after AUTHOR ??
	  @author_fields=split(//,$post_author);
      
          my $iaf=0; #number of names in one author (last, first, middle name = 3)
	  my $saf=0; #number of separators
	  my $start=0;
	  my $max_n_of_aut=0;#max num of authors to show. If 0 then unlimited!  ??????????
	  
	  my $and_word=''; #have to be before the last author if number of outhors>1
	  
	  while($author_fields[$start] =~ /^[0-9]+$/)
	  {$max_n_of_aut="$max_n_of_aut$author_fields[$start]";
	   $start++;  
	  };
	  
	  my $niaf;
	  $niaf=scalar(@author_fields);
	  $#author_name_key = -1; $#author_seps = -1; #to make them clean!
	  
	  for(my $ii=$start; $ii<$niaf; $ii++)
	  {    
	      if($author_fields[$ii] =~/^[A-Za-z]+$/)
	          {$author_name_key[$iaf] = "$reservedAUTHOR$author_fields[$ii]"; $iaf++; $saf++;}
	      elsif($author_fields[$ii] ne $reservedAND_SEPARATOR) 
	          {$author_seps[$saf] = "$author_seps[$saf]$author_fields[$ii]"}
	      else{$and_word = substr($post_author,$ii+1); 
	           $ii=$niaf+1; #to finish the loop
	          }
	  };
	  
	  $last_sep=$author_seps[$saf]; 
    
	  #Thus we have 
	  #  @author_name_key  - array of the type (AUTHORL, AUTHORF, AUTHORM)
	  #  @author_seps      - $author_seps[1] is what should be placed after AUTHORF, 0-th - after AUTHORL
	  #  $last_sep         - should be placed after the complete name of one person!	  
	      
          #print $HASH_REFS{'AUTHORL'} ;     
	  my $n_of_aut=0 ; my $schet=0; my @avtor;
          #HOW MANY AUTHOR WE HAVE??? We should find MAXIMUM!!
	  
          while($schet < scalar(@author_name_key) )    
	  {  @avtor = split(/\|/,$HASH_REFS{$author_name_key[$schet]}); #
	     if($n_of_aut < scalar(@avtor)){$n_of_aut = scalar(@avtor)}; #number of authors
	     $schet++; 
	  };
          # Now number of authors is in the $n_of_aut

	  
	  my $print_etal = 0;      #?????????????
	  if(($max_n_of_aut > 0)&&($max_n_of_aut < $n_of_aut)){$n_of_aut=$max_n_of_aut; $print_etal=1;}
	  # now number of authors to display is '$n_of_aut'!
	  
	  my $jj; #counter for all names of one author!
	  my $max_jj = scalar(@author_name_key);
	  
	  for(my $ii=0;$ii<$n_of_aut;$ii++)    # $ii is number of aut to display
	  {
	      for($jj=0;$jj<$max_jj  ;$jj++) # $jj  is counter of name of the same person
	      {
		  #print OUTTEX $author_seps[$jj];
		  @avtor = split(/\|/,$HASH_REFS{$author_name_key[$jj]});
		  @avtor = trim(@avtor);
		  if($avtor[$ii] ne ''){print OUTTEX $author_seps[$jj];
	      
		                        print OUTTEX $avtor[$ii];};
	      };
	      
	      
	      if($ii<$n_of_aut-2){print OUTTEX $last_sep;}; #for all except the last
	      if($ii == $n_of_aut-2)
	      {  if(($n_of_aut>2)||(trim($and_word) eq "")){print OUTTEX $last_sep};
	         if(($n_of_aut>1)&&($print_etal == 0)){print OUTTEX " $and_word ";}
	         
              };
	  };   
	  #print $last_sep;
	  if($print_etal){print OUTTEX $reservedET_AL;}
      }    
      else
      {
	  print OUTTEX $HASH_REFS{$char1};
      };      
      
    
    }
    else{print OUTTEX $char};    
};
#print "\n";
};
#---------------------------------------------------

sub read_inline_arguments
{my $DD='--'; my $D='-';
 my $counter=0; my $current='';
 my $guess;

for($counter=0;$counter<scalar(@ARGV);$counter++)
{
 #print "$item \n";
 $current = $ARGV[$counter];
 
#------------------------------------------------------------
 #first check if it has '--' at the beginning
 ($guess) = ($current =~/$DD([^ ]*)/);
 if(($guess ne '')&&(substr($current,0,2) eq $DD))
 {  
    my $nothing=0;
    SWITCH: {
      if ($guess eq "help")   {&print_help_info;    exit(0);} 	
      if ($guess eq "version"){&print_version_info; exit(0);}  
	
      #options     
      if ($guess eq "nobibitem") 
         { $optionsKEEP_BIBITEM_AND_CITE=0; last SWITCH; }
      if ($guess eq "not_insert_empty_field_sign") 
         { $optionsINSERT_EMPTY_FIELDS_SIGN=0 ; last SWITCH; }

      #reserved words
      if ($guess eq 'separator') 
         { $counter++;  $SEPARATOR=$ARGV[$counter]; last SWITCH; }

      if ($guess eq 'etal') 
         { $counter++;  $reservedET_AL=$ARGV[$counter]; last SWITCH; }
      if ($guess eq 'empty_field_sign') 
         { $counter++;  $reservedEMTY_FIELD_SIGN=$ARGV[$counter]; last SWITCH; }
      if ($guess eq 'html') 
         { $optionsHTML_OUTPUT = 1; last SWITCH; }
      if ($guess eq 'prefix') 
         { $counter++;  $httpprefix=$ARGV[$counter]; last SWITCH; }         
      
    $nothing = 1;
    };
    if($nothing){print STDERR "Unknown option <$current>!!! Exiting!\n"; exit(1);}
    else{next};
   };
 #-------------------------------------------------------------------
 #second: check if it has '-' at the beginning
 ($guess) = ($current =~/$D([^ ]*)/);
 if(($guess ne '')&&(substr($current,0,1) eq $D))
 {  
    my $nothing=0;
    SWITCH: {
      #options
      if ($guess eq "h") 
         { &print_help_info; exit(0)} 
      if ($guess eq "o") 
         { $counter++; $OUT_TEX=$ARGV[$counter]; last SWITCH; }
      if ($guess eq "f") 
         { $counter++; $FORMAT_NAME=$ARGV[$counter]; last SWITCH; }
      if ($guess eq "d") 
         { my $itis=1; my $whatis='';
           while($itis)
           {
	       $counter++; 
               #unless($counter < scalar(@ARGV)-1){$counter--;last SWITCH;}
               $whatis = $ARGV[$counter];
               if((substr($whatis,0,2) eq $DD)||(substr($whatis,0,1) eq $D))
               {$counter--; $itis=0;} 
               else{$REFS_FILES[$itis-1] = $whatis; $itis++};
	   };
           if(scalar(@REFS_FILES)<1){print STDERR "Invalid format of -d option";}
           last SWITCH; 
         }

      if ($guess eq "a") 
         { $counter++; $ABBR_NAME=$ARGV[$counter]; $optionsABBREVIATIONS=1; last SWITCH; }


      if ($guess eq "v") 
         { $counter++; $verbosity_level=$ARGV[$counter]; last SWITCH; }

      #reserved words
      #if ($guess eq 'etal') 
      #   { $counter++;  $reservedET_AL=$ARGV[$counter]; last SWITCH; }
    $nothing = 1;
    };
    if($nothing){print "Unknown option <$current>!!! Exiting!\n"; exit(1);}
    else{next};
 };
 #---------------------------------------------------------------------
 #so, this is not switch

}

};

#----------------------------------
sub check_for_important_arguments
{
 
    if($OUT_TEX eq ''){$OUT_TEX = "biblist.output.tex"};
    if(scalar(@REFS_FILES) == 0)
      {print STDERR "You must select at least one refs dbase file with -d option!!!";
       print STDERR "Exiting!\n";   
       exit(1)
      };
 
 
      if($FORMAT_NAME eq '')
       {print STDERR "You must select one formats file with -f option!!!";
       print STDERR "Exiting!\n";   
       exit(1)
       };  
}; 
#-----------------------------------
sub  print_version_info
{
print "biblist v.$BIBLIST_VERSION \n";
print "Written by R.Stepanyan.\n\n";
print "This is free software. There is NO warranty! \n";
print "Redistribution of this software is covered by the terms of";
print "the GNU General Public License.\n";
print "For more information, please, contact rstepanyan\@yahoo.com\n";
};
#-----------------------------------------------
sub  print_help_info
{
print "biblist v.$BIBLIST_VERSION \n";
print "biblist [-o outfile] [-f formatfile] -d dbasefile(s) [other keys] \n";
print "\n";
print "-v <number> - verbosity level (0-5)\n";
print "-h (--help) - this help\n";
print "--version   - version information\n";
print "\n";
print "About the other parameters see readme.1st \n";
print "\n";
#print "\n";
};

#----------------------------------------------------
sub trim {
    my @out = @_;
    for (@out) {
        s/^\s+//;
        s/\s+$//;
    }
    return wantarray ? @out : $out[0];
}
#------------------------------------------------------------------------------
sub insert_abbreviations_of_journals # $OUTTEX must be opened already
{ my $aline='';
  if($optionsABBREVIATIONS==1)
  {  open(ABBR,"$ABBR_NAME");

     if($optionsHTML_OUTPUT){print OUTTEX "<br>";}  else{print OUTTEX "\n"; };

     while(<ABBR>)
     {  $aline = $_;
        print OUTTEX "$aline" ;
        if($optionsHTML_OUTPUT){print OUTTEX "<br>";} ;
     }
     close(ABBR);

     if($optionsHTML_OUTPUT){print OUTTEX "<br>";}  else{print OUTTEX "\n"; }
     return 0;
  }
  else 
  {  return 0;
  }
};
