#!/usr/bin/perl -w
$data_file = '/home/fc/public_html/wall.txt';
$max_entries = 50; #
# set to '0' (zero) for infinite entries...
use CGI;
use Fcntl;
$query = new CGI;
unless ($action = $query->param('action')) {
$action = 'none';
}
print <<"EndOfText";
Content-type: text/html
The Wall
Check out what all the rabid attack monkeys have to say!
Put these crayons to chaos using the form below
Go back when your done.
EndOfText
if ($action eq 'Add Comment') {
# process the form submission
# and assemble the guestbook entry
$name = $query->param('name');
$location = $query->param('location');
$comment = $query->param('comment');
# clean up and fiddle with $name
unless ($name) {
$name = 'Anonymous';
}
if (length($name) > 50) {
$name = 'Someone with a really long name';
}
# disable all HTML tags
$name =~ s/</g;
# untaint variable
unless ($name =~ /^([^<]*)$/) {
die "couldn't untaint name: $name\n";
}
$name = $1;
# clean up and fiddle with $from_where
$from_where = "$location";
if ($from_where =~ /^[,\s]+$/) {
# nothing but commas and whitespace
$from_where = 'the trailer park';
}
if (length($from_where) > 75) {
$from_where = 'somewhere with a really long name';
}
# disable HTML tags
$from_where =~ s/</g;
# untaint variable
unless ($from_where =~ /^([^<]*)$/) {
die "couldn't untaint from_where: $from_where\n";
}
$from_where = $1;
# clean up and fiddle with $comment
if (length($comment) > 32768) {
$comment = '...more than my crayons can handle.';
}
unless ($comment) {
$comment = '...nothing...';
}
# fix line-endings
$comment =~ s/\r\n?/\n/g;
# lose HTML tags
$comment =~ s/</g;
# untaint variable
unless ($comment =~ /^([^<]*)$/) {
die "couldn't untaint comment: $comment\n";
}
$comment = $1;
# assemble finished guestbook entry
$timestamp = localtime(time);
$entry = <<"EndOfText";
$name from $from_where wrote: $comment at $timestamp
EndOfText
# open non-destructively, read old entries, write out new
sysopen(ENTRIES, "$data_file", O_RDWR)
or die "can't open $data_file: $!";
flock(ENTRIES, 2) or die "can't LOCK_EX $data_file: $!";
while() {
$all_entries .= $_;
}
$all_entries .= $entry;
if ($max_entries) {
# lop the head off the guestbook, if necessary
@all_entries = split(/
/i, $all_entries);
$entry_count = @all_entries - 1;
while ($entry_count > $max_entries) {
shift @all_entries;
$entry_count = @all_entries - 1;
}
$all_entries = join('
', @all_entries);
}
# now write out to $data_file
seek(ENTRIES, 0, 0) or die "can't rewind $data_file: $!";
truncate(ENTRIES, 0) or die "can't truncate $data_file: $!";
print ENTRIES $all_entries or die "can't print to $data_file: $!";
close(ENTRIES) or die "can't close $data_file: $!";
}
# display the guestbook
open (IN, "$data_file") or die "Can't open $data_file for reading: $!";
flock(IN, 1) or die "Can't get LOCK_SH on $data_file: $!";
while () {
print;
}
close IN or die "Can't close $data_file: $!";
# display the form
print <<"EndOfText";
Scribble on the Wall:
EndOfText