1bbc059fb7c243f1fed1d7001666187ea80e7fcf hiram Sat Nov 16 11:00:05 2024 -0800 correctly safely escape all inputs refs #32596 diff --git src/hg/gar/asr.cgi.pl src/hg/gar/asr.cgi.pl index b17558c..375f30e 100755 --- src/hg/gar/asr.cgi.pl +++ src/hg/gar/asr.cgi.pl @@ -1,133 +1,136 @@ #!/usr/bin/perl ## ## asr -- Assembly Request - receive assembly build requests ## +use CGI; use URI::Escape; +use HTML::Entities; -# use strict; -# use warnings; +use strict; +use warnings; my $httpRefer = "noReference"; my $referDomain = "noDomain"; my $domainMustBe = "ucsc.edu"; my $httpReferMustBe = "assemblySearch.html"; # obscure the email address from source tree robot scanning my $myAddr = 'hclawson at ucsc dot edu'; $myAddr =~ s/ at /@/; $myAddr =~ s/ dot /./; my $legitimateFrom = $myAddr; my $sendTo = $myAddr; my $Cc = $myAddr; my $bounceAddr = $myAddr; my $genArkRequestGroup = 'genark-request-group at ucsc dot edu'; $genArkRequestGroup =~ s/ at /@/; $genArkRequestGroup =~ s/ dot /./; -# DBG -$genArkRequestGroup = $myAddr; +# DBG - uncomment this to prevent email to genArkRequestGroup +# $genArkRequestGroup = $myAddr; -if (defined($ENV{'HTTP_REFERER'})) { - my @a = split('/', $ENV{'HTTP_REFERER'}); +my $query = CGI->new; + +my $referer = "noReferer"; + +if (exists($ENV{'HTTP_REFERER'}) && defined($ENV{'HTTP_REFERER'})) { + $referer = CGI->escapeHTML($ENV{'HTTP_REFERER'}); + my @a = split('/', $referer); $httpRefer = $a[-1]; # should be "assemblyRequest.html" $httpRefer =~ s/\?.*//; # remove arguments if present my @b = split('\.', $a[-2]); $referDomain = "$b[-2].$b[-1]"; # should be "ucsc.edu" } -print "Content-type: text/html\n\n"; +print $query->header(-type => 'text/html'); print "<html><head><title>Assembly Search Request assembly build</title></head>\n"; print "<body>\n"; # QUERY_STRING name=some%20name&email=some@email.com&asmId=GCF_000951035.1_Cang.pa_1.0 my %incoming = ( "name" => "noName", "email" => "noEmail", "asmId" => "noAsmId", "betterName" => "noBetterName", "comment" => "noComment", ); my $validIncoming = 0; my $extraneousArgs = 0; -if (defined($ENV{"QUERY_STRING"})) { - my $qString = $ENV{"QUERY_STRING"}; - my @idVal = split("&", $qString); - foreach $id (@idVal) { - my ($tag, $value) = split("=", $id, 2); +foreach my $tag ($query->param) { + my $value = $query->escapeHTML(uri_unescape($query->param($tag))); # only accept known inputs, the five defined above for %incoming defaults if (defined($incoming{$tag}) && defined($value)) { - $incoming{$tag} = uri_unescape( $value ); + $incoming{$tag} = $value; ++$validIncoming; - } - ++$extraneousArgs if (!defined($incoming{$tag})); + } else { + ++$extraneousArgs; } } if ( ($validIncoming != 5) || ($extraneousArgs > 0) || ($referDomain ne $domainMustBe) || ($httpRefer ne $httpReferMustBe) ) { # not a legitimate request from our own business, do nothing. - printf STDERR "# ERROR: cgi-bin/asr invalid something: %d %d %s %s\n", $validIncoming, $extraneousArgs, $referDomain, $httpRefer; - printf "<p>HTTP_REFERER: %s</p>\n", $ENV{'HTTP_REFERER'}; - printf "<p># ERROR: cgi-bin/asr invalid something: %d %d %s %s</p>\n", $validIncoming, $extraneousArgs, $referDomain, $httpRefer; + printf STDERR "# ERROR: cgi-bin/asr invalid request %d %d %s %s\n", $validIncoming, $extraneousArgs, $referDomain, $httpRefer; + printf "<p>HTTP_REFERER: %s</p>\n", $referer; + printf "<p># ERROR: cgi-bin/asr invalid request %d %d %s %s</p>\n", $validIncoming, $extraneousArgs, $referDomain, $httpRefer; printf "<h3>err exit at end of asr</h3>\n"; print "</body></html>\n"; exit 0; } printf "<ul>\n"; printf "<li> name: '%s'</li>\n", $incoming{"name"}; printf "<li>email: '%s'</li>\n", $incoming{"email"}; printf "<li>asmId: '%s'</li>\n", $incoming{"asmId"}; printf "<li>betterName: '%s'</li>\n", $incoming{"betterName"}; printf "<li>comment: '%s'</li>\n", $incoming{"comment"}; printf "</ul>\n"; my $DS=`date "+%F %T"`; chomp $DS; +my $cleanEmail = $incoming{"email"}; +$cleanEmail =~ s/@/ at /; +$cleanEmail =~ s/\./ dot /g; open (FH, "|/usr/sbin/sendmail -f \"${bounceAddr}\" -t -oi"); printf FH "To: %s Reply-to: %s Return-path: %s Cc: %s Subject: asr request: %s name: '%s' email: '%s' asmId: '%s' betterName: '%s' comment: '%s' date: '%s' -", $sendTo, $incoming{"email"}, $legitimateFrom, $Cc, $incoming{"asmId"}, $incoming{"name"}, $incoming{"email"}, $incoming{"asmId"}, $incoming{"betterName"}, $incoming{"comment"}, ${DS}; +", $sendTo, $incoming{"email"}, $legitimateFrom, $Cc, $incoming{"asmId"}, decode_entities($incoming{"name"}), decode_entities($cleanEmail), decode_entities($incoming{"asmId"}), decode_entities($incoming{"betterName"}), decode_entities($incoming{"comment"}), ${DS}; close (FH); -my $cleanEmail = $incoming{"email"}; -$cleanEmail =~ s/@/ at /; -$cleanEmail =~ s/\./ dot /g; - # and then send the email to the google group with the cleanEmail in text if ( $genArkRequestGroup ne $myAddr ) { # debugging do not send mail twice open (FH, "|/usr/sbin/sendmail -f \"${bounceAddr}\" -t -oi"); printf FH "To: %s Reply-to: %s Return-path: %s Subject: asr request: %s name: '%s' email: '%s' asmId: '%s' betterName: '%s' comment: '%s' date: '%s' -", $genArkRequestGroup, $legitimateFrom, $legitimateFrom, $incoming{"asmId"}, $incoming{"name"}, $cleanEmail, $incoming{"asmId"}, $incoming{"betterName"}, $incoming{"comment"}, ${DS}; +", $genArkRequestGroup, $legitimateFrom, $legitimateFrom, $incoming{"asmId"}, decode_entities($incoming{"name"}), decode_entities($cleanEmail), decode_entities($incoming{"asmId"}), decode_entities($incoming{"betterName"}), decode_entities($incoming{"comment"}), ${DS}; close (FH); } print "</body></html>\n";