#!/usr/bin/perl

$MAXLINES=45;			# show the top 45 in each category
$debug='';
$recs=0;
$clirecs=0;
while (<STDIN>) {
    print if $debug;
    chop;
    if (/"\(client (.*)\)"/) {
	$clirecs++ if &getinfo($1);
    } elsif (/"client (.*)"/) {
	$clirecs++ if &getinfo($1);
    }
    $recs++;
}
print "found $clirecs client fields in $recs log records\n\n";

&showresult('Type',		\%btypcount);
&showresult('Version',		\%bvercount);
&showresult('Language',		\%langcount);

&showresult('OS',		\%oscount);
&showresult('Hardware',		\%hardcount);
&showresult('Browser',		\%browcount);
&showresult('Origin',		\%origcount);
#&showresult('Comment',		\%cmntcount);


# sort routines: descending by count, then alphabetical by name

sub descending { $$glist{$b} <=> $$glist{$a} or $a cmp $b; }

sub showresult {
    local($label, $hashlist) = @_;
    $glist = $hashlist;			# save in global var
    local($item);
    local($lcount) = 0;
    # sort descending by number of hits, then alphabetical by name
    # print the top 50 items, and ignore the others
    foreach $item (sort descending keys %$hashlist) {
	last if ++$lcount > $MAXLINES;
	printf "%-10s %-32s %8d\n", $label, $item, $$hashlist{$item};
    }
    print "[...]\n" if $lcount > $MAXLINES;
    print "\n" if $lcount;
}


sub getinfo {
  # returns TRUE if record is valid
  local($string) = @_;
  local($btype, $bversion, $info, $comment, $hardware, $browser, $origin);
  local($language, $os);
  $string =~ s/_/ /g;			# change underlines to blanks
  if ($string =~ /\((.*)\)/) {
    $btype=$`;
    $info=$1;
    $comment=$';
    return '' if $info =~ /\(/;		# embedded parentheses, invalid!
    $btype =~ s/\s+$//;			# remove trailing blanks
    if ($btype =~ s|/(.*)$||) {
      $bversion=$1;
    }
    if ($bversion =~ s| \[(.*)\]||) {
      $language=$1;
    }
    $bversion =~ s/[^.\d].*$//;	# only digits and dot allowed in version
    $btypcount{$btype}++	if $btype;
    $bvercount{$bversion}++ if $bversion;
    $langcount{$language}++ if $language;
      $comment =~ s/^\s+//;		# remove leading blanks
    $comment =~ s/:.*//;		# remove everything after colon
  } else {
    $info=$string;			# Ultraseek
    $info=~s/ .*$//;			# keep first word only
  }
  @fields=split(/\s*;\s*/, $info);
  if ($#fields == 9) {
#compatible; MSIE 5.0; AOL 4.0; Windows 98; Win9x v3; fzivcs; TFIA-ZDNET; DigExt; WHSmith Online V1.12; VNIE4 3.1.814
    $hardware=@fields[0];
    $browser =@fields[1];
    $origin  =@fields[2];
    $os      =@fields[3];
  } elsif ($#fields == 8) {
#compatible; MSIE 5.0; MSN 2.5; Windows 98; Compaq; AT&T WNS2.5 IE4.01; AT&T WNS5.0; DigExt; AT&T WNS5.0 IE5.0.01
    $hardware=@fields[0];
    $browser =@fields[1];
    $origin  =@fields[2];
    $os      =@fields[3];
  } elsif ($#fields == 7) {
#compatible; MSIE 5.0; Windows 98; Compaq; AT&T WNS IE4.0; AT&T WNS2.5 IE4.01; AT&T WNS5.0; DigExt
    $hardware=@fields[0];
    $browser =@fields[1];
    $origin  =@fields[6];
    $os      =@fields[2];
  } elsif ($#fields == 6) {
		# compatible; MSIE 3.02; Update a; AK; AOL 3.0; Windows 95; Quicken 7.0
		# compatible; MSIE 3.02; MSN 2.5; Update a; AK; AOL 3.0; Windows 95
    $hardware=@fields[0];
    $browser =@fields[1];
    if (@fields[6] =~ /Windows/) {
      $origin  =@fields[5];
      $os      =@fields[6];
    } else {
      $origin  =@fields[4];
      $os      =@fields[5];
    }
  } elsif ($#fields == 5) {	# compatible; MSIE 3.02; Update a; AK; AOL 3.0; Windows 95
    $hardware=@fields[0];
    $browser =@fields[1];
    $origin  =@fields[4];
    $os      =@fields[5];
  } elsif ($#fields == 4) {	# compatible; MSIE 3.02; Update a; AOL 3.0; Windows 95
    $hardware=@fields[0];
    $browser =@fields[1];
    $origin  =@fields[3];
    $os      =@fields[4];
  } elsif ($#fields == 3) {	# X11; U; SunOS 4.1.3_U1 sun4m; Nav
				# Macintosh; I; PPC, Nav
				# compatible; MSIE 3.0; AOL 3.0; Windows 95
				# compatible; MSIE 4.01; MSIECrawler; Windows 95
				# compatible; MSIE 4.01; Windows 95; ICONZ 4.0.1.2
    $hardware=@fields[0];
    if (@fields[3] =~ /^Nav/) {
      $browser =@fields[3];
      $os      =@fields[2];
    } else {
      $browser =@fields[1];
      if (@fields[3] =~ /^Win/) {
	$os      =@fields[3];
	$origin  =@fields[2];
      } else {
	$os      =@fields[2];
	$origin  =@fields[3];
      }
    }
  } elsif ($#fields == 2) {
    if (@fields[2] =~ /^Nav/) {	# Win95; U ;Nav
      $os      =@fields[0];
      $browser =@fields[2];
    } else {			# compatible; MSIE 4.0; Windows 95
      $hardware=@fields[0];
      $browser =@fields[1];
      $os      =@fields[2];
    }
  } elsif ($#fields == 1) {
    if (@fields[0] =~ /^Win/) {	# WinNT; I
      $os      =@fields[0];
      $browser =@fields[1];
      $browser = "$os $browser" if $browser =~ /^[A-Z]$/;
    } else {			# compatible; MSIE 2.0
      $hardware=@fields[0];
      $browser =@fields[1];
    }
  } elsif ($#fields == 0) {
    if (@fields[0] eq 'Ultraseek') {
      $browser=@fields[0];
    } else {
      $os     =@fields[0];
    }
  } else {
    print STDERR "*** $#fields+1 fields, unrecognized:\n$info\n";
  }

  $os =~ s/^\s+//;		# remove leading blanks
  if ($os =~ /Linux (.*) i\d86/) {
    $os = "Linux $1";
  }
  $os =~ s/Mac 68K/Mac 68000/;
  $os =~ s/Mac PPC/Mac PowerPC/;
  $os =~ s/WinNT/Windows NT/;
  $os =~ s/Win98/Windows 98/;
  $os =~ s/Win95/Windows 95/;
  $os =~ s/Win32/Windows 32/;
  $os =~ s/Win16/Windows 16/;
  $os =~ s/-bit//;
  $hardware =~ s/Compatible/compatible/;

  $hardcount{$hardware}++	if $hardware;
  $browcount{$browser}++	if $browser;
  $origcount{$origin}++		if $origin;
  $oscount{$os}++		if $os;
# $cmntcount{$comment}++	if $comment;

  if ($debug) {
    print "btype\t$btype   \tversion\t$bversion  \tlang\t$language\n";
    print "hardwr\t$hardware  \tbrowser\t$browser";
    print "  \torigin\t$origin" if $origin;
    print "  \tos\t$os\n";
#   print "comment\t$comment\n" if $comment;
  }
  return 'yes';
}
