#!/usr/local/bin/perl # NAME: proxy.cgi # AUTH: James A. Bowery (jab) # NOTE: Copyright (C) 2004 # # The Electoral Corruption Killer # # Unless explicitly acquired and licensed under the TECK # Commercial License ("TCL") Version 1.0, the contents # of this file are subject to the Reciprocal Public License # ("RPL") Version 1.3 and You may not copy or use this file # in either source code or executable form, except in # compliance with the terms and conditions of the RPL. # # You may read about the Reciprocal Public License at: # http://en.wikipedia.org/wiki/Reciprocal_Public_License # # All software distributed under the Licenses is provided strictly # on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER # EXPRESS OR IMPLIED, AND THE ELECTORAL CORRUPTION KILLER HEREBY # DISCLAIMS ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, # ANY WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR # PURPOSE, QUIET ENJOYMENT, OR NON-INFRINGEMENT. # See Licenses for specific language governing rights and # limitations under the Licenses. # # BEGIN{ if(!-e 'proxy_data.pl'){ open A,">proxy_data.pl" or die "Can't initialize proxy_data.pl"; print A "1"; close A; } } use CGI::Carp; use CGI qw/:standard :debug/; use Data::Dumper; use Fcntl qw/:flock/; -e 'proxy_writable' # START CRITICAL SECTION and (open(MUTEX,">proxy_mutex") or die "Can't write proxy_mutex: $!") and (flock(MUTEX,LOCK_EX) or die "Can't lock critical section: $!"); require 'proxy_data.pl'; print header; print "\n"; $phoneRE='(\d{10})'; $billRE='([1-9]\d{0,5})'; $voteRE='(0|1|2)'; $deleteRE='(#)'; if (param()) { $op=param('op'); while($op=~s/ / /g){}; $op=~s/^\s*|\s*$|[^\d# ]//g; if(-e 'proxy_writable'){ if(($phone,$proxies)=($op=~/^$phoneRE (($phoneRE )*$phoneRE)$/)){ $citizen{$phone}->{"proxies"}=[split /\s+/,$proxies]; print "$phone throws proxy to $proxies.

\n"; }elsif(($phone)=($op=~/^$phoneRE $deleteRE$/)){ delete $citizen{$phone}->{"proxy"}; print "$phone retains proxy.

\n"; }elsif(($phone,$bill,$voteOrProxy,$vote,$proxy)=($op=~/^$phoneRE $billRE ($voteRE|$phoneRE)$/)){ $citizen{$phone}->{$bill}=$voteOrProxy; if(defined($vote)){ print "$phone votes on bill $bill "; print (('"Nay."','"Yea."','"Abstain."')[$vote]); print "

\n"; }elsif($proxy){ print "$phone throws proxy on bill $bill to $proxy.

\n"; } }elsif(($phone,$bill,$delete)=($op=~/^$phoneRE $billRE $deleteRE$/)){ print "$phone exercises no authority specific to bill $bill.

\n"; delete $citizen{$phone}->{$bill}; } } if($phone){ open A,">proxy_data.pl.new"; print A Data::Dumper->Dump([\%citizen],[qw(*citizen)]); close A; `mv proxy_data.pl.new proxy_data.pl`; }elsif(($phone,$bill)=($op=~/^$phoneRE $billRE$/)){ showVote(); }elsif(($phone)=($op=~/^$phoneRE$/)){ print "

";
        print Dumper($citizen{$phone});
        print "
\n"; }elsif(($bill)=($op=~/^$billRE$/)){ $yeas=$nays=$abstains=$absents=0; for $phone (keys %citizen){ showVote(); if($vote==1){$yeas++} elsif(!defined($vote)){$absents++} elsif($vote==0){$nays++} elsif($vote==2){$abstains++} } print "Yeas $yeas, Nays $nays, Abstains $abstains, Absents $absents\n"; }else{ print "No query processed:
\"$op\"\n" } } -e proxy_writable # END CRITICAL SECTION and (flock(MUTEX,LOCK_UN) or die "Can't unlock proxy_mutex: $!"); print "
".h1('Enter proxy query:'), start_form(-method=>'GET',-name=>'op', -id=>'op'), '
Examples:
122
    Tally the vote for bill 122.
5554274444 42
    Show how 4274444\'s vote is cast on bill 42.
5552242759
    Dump data for 2242759.';
print '
5554274444 5554271111
    Set 5554274444\'s default proxy to 5554271111.
5554882222 #
    5554882222 wants no default proxy.
5554274444 5554271111 5554273239
    Set 5554274444\'s first default proxy to 5554271111 and second to 5554273239. Add as many more as desired.
5555228222 122 1
    Set 5555228222\'s vote on bill 122 to "Yea."
5558221121 42 0
    Set 5558221121\'s vote on bill 42 to "Nay."
5554293323 9402 2
    Set 5554293323\'s vote on bill 9402 to "Abstain."
5552242759 1822 5554274444
    Set 5552242759 to throw proxy on bill 1822 to 5554274444.
5554291178 322 #
    Set 5554291178 to throw proxy on bill 322 to default proxy if any.' if -e "proxy_writable";

print '
',textfield(-id=>'op',-name=>'op',-cols=>80,-maxlength=>1000); print submit, end_form,"
"; print "
";
print "The current proxy_data.pl database:\n\n";
print Data::Dumper->Dump([\%citizen],[qw(*citizen)]);
print "
\n"; print ""; exit(0); sub showVote{ undef($vote) unless @priorPhones; push @priorPhones,$phone; if($citizen{$phone}->{$bill}=~/($voteRE|$phoneRE)/){ if($3){ print "$phone throws proxy for $bill to $3"; if(@priorPhones == $3){ print " This is a vicious cycle, hence @priorPhones is absent.

\n"; }else{ print ". "; do{local $phone=$3; showVote()}; } }else{ $vote=$2; print "$phone votes "; print (('"Nay"','"Yea"','"Abstain"')[$vote]); print ".

\n"; } }elsif($proxies=$citizen{$phone}->{"proxies"}){ my $n=0; for my $proxy (@$proxies){ $n++; print "$phone\'s #$n default proxy is $proxy. "; if(grep /$proxy/,@priorPhones){ print " This is a vicious cycle, hence $proxy is absent. "; next; }else{ do{local $phone=$proxy; showVote();} } last if defined($vote); } print "

\n"; }else{ print "$phone is absent.

\n"; } pop @priorPhones; return $vote; }