#!perl
print <<'EOF';

package veval;

sub main::veval($) {
   my $s = shift; $s =~ s/@/\\@/g;
   $s =~ s/\$\$/\\\$/g;
   $s =~ s/"/\\"/g;
   my ($ret, $nret ) = ($s);
     $ret = $nret while $ret ne ($nret = eval qq[qq[$ret]]);
   return $ret
}

package main;
use Symbol 'qualify_to_ref';

my $bound = <DATA>;
my ( $var ) = $bound =~ /^(\w+)\s/;
my $value = '';
while ( <DATA> ) {

    if ( $_ eq $bound ) {

        chomp $value;
        $subst{$var} = $value;

	$bound = <DATA>;
	( $var ) = $bound =~ /^(\w+)\s/;
	$value = '';
    }

    else {
        $value .= $_;
    }
}

die( "unexpected end of substitution data\n" ) if defined $bound;

*{qualify_to_ref($_, 'veval')} = \($subst{$_}) foreach keys %subst;

my @no_eval;

while ( @ARGV ) {
   last unless $ARGV[0] =~ /^-/;
   my $arg = shift @ARGV;
   last if $arg eq '--';

   if ( $arg =~ /^--no-eval=(.*)/ ) {
     push @no_eval, $1;
   }
   else {
     die( "unknown option to dosubst: $arg\n" );
   }
}

my %eval;
@eval{ keys %subst } = ();
delete @eval{@no_eval};
$subst{"${_}_EVAL"} = veval $subst{$_} foreach keys %eval;

while( @ARGV && $ARGV[0] =~ /(.*)=(.*)/ ) {
  $subst{$1} = $2;
  shift;
}

$re = join( '|', sort keys %subst );

while(<>) { s/[@]($re)[@]/$subst{$1}/geo; print; }

__DATA__
EOF

use Digest::MD5 qw[ md5_base64 ];

foreach ( <STDIN> ) {
    chomp;
    print $_ . ' ' . md5_base64($_), "\n";
    print '@' . $_ . '@' . "\n";
    print $_ . ' ' . md5_base64($_), "\n";
}
