2011-11-12 4 views
1

以下のスクリプトからPerlに関する質問があります。 $user変数の入力がjoeshmo; ls -l;の場合、perlはprint $userというコードがコーディングされている場合にのみjoeshmoを出力します。私の直感は、joeshmo; ls -l;のすべてが印刷されるべきだと私に伝えます。ただし、ユーザ変数を指に与えて実行すると、joeshmoとls -lの両方が実行されます。私は上記の文ではPerl変数保存されたデータと正規表現の部分だけを出力する

if (($user !~ /^[a-z_A-Z0-9]+[-+%]*[a-z_A-Z0-9]+$/)){ 
die "The entered user name uses characters not of the alphanumeric form or the \"-\", \"+\", or \"%\"!"; 
} 
else{ 

のような文で変数$userに許可されている入力を制限しようとしていますので、私はこれを聞いて、私はプログラムが死ぬことを引き起こすことはありません入力のみが持つ文であることを信じています英数字とアンダースコアの後に、 - 、+、%文字(必要な場合)、そして英数字とアンダースコアの別のラウンドが続きます。しかし、正規表現は、$user変数の最初の部分だけを評価し、joeshmo; ls -l;の場合のようにすべてを評価しません。正規表現はjoeshmoでのみ評価されます。

私が理解できない別の興味深い情報は、$user変数が印刷されたときにセミコロンが表示されない理由です。それらがあれば、私はそれらを検索することができますが、印刷されていないので、正規表現で評価することはできません。

私はこれらの問題についてお手伝いします。

#!/usr/bin/perl 

use CGI; 
use CGI::Carp qw(fatalsToBrowser); 
$q = new CGI; 

print $q->header, 
    $q->start_html('Finger User'), 
    $q->h1('Finger User'); 
print "<pre>\n"; 

$user = $q->param("user"); 
print "\n"; 
print $user; 
print "\n\n"; 

if (($user !~ /^[a-z_A-Z0-9]+[-+%]*[a-z_A-Z0-9]+$/)){ 
die "The entered user name uses characters not of the alphanumeric form or the \"-\", \"+\", or \"%\"!"; 
} 
else{ 
print `/usr/bin/finger -s $user`; 
} 

print "</pre>"; 
print $q->end_html; 

答えて

4

私はあなたがすべてで$userls -lを取得しているとは思いません。そうだった場合は、$user !~ /^\w+[-+%]*\w+$/と書かれた方が良い正規表現が一致し、dieが実行されます。私はいくつかの実装では、上記の(いくつかのサーバの実装で)と同等になるようにセミコロン(;)は、クエリ文字列でセパレータとして使用することが可能

/cgi-bin/something.pl?user=joeshmo; ls -l; 

としてこのスクリプトを呼び出していることを推測しています:

/cgi-bin/something.pl?user=joeshmo& ls -l& 

ので、ls -l部分がuserの一部とは見なされないであろう。

/cgi-bin/something.pl?user=joeshmo%3B%20ls%20-l%3B 

、その後、あなたはあなたのls -lを参照してdieをトリガーする必要があります:セミコロンとスペースをコードするURLを試してみてください。 ;は時々セパレータとして許可されていることを

理由は&もエンティティをエンコードするためにHTMLで使用されているので、HTML属性に表示されるすべてのアンパサンドが&amp;としてエンコードされなければならないか、混乱を危険にさらしているということです。例えば、これは多くの場合、不正な動作になります。

<a href="http://example.com?a=b&reg=c"> 

が、これはしません:HTML4 spec

<a href="http://example.com?a=b&amp;reg=c"> 

は、W3は推奨しています。

[...] HTTPサーバーの実装者、特にCGI実装者は、 ";" "&"の代わりに "&"文字をこのようにエスケープする手間を省く。

+0

お返事ありがとうございます。これはセミコロンで、HTMLフォームからバックエンドのCGIスクリプトにスペースが送られますか? CGIスクリプトがHTMLフォームからデータを取得する方法であるからです。 – tpar44

+0

@ tpar44:ブラウザーはすべてを適切にエンコードする必要がありますが、手動でURLを入力する場合や、 ''要素のリンクを手作業で構築する場合は、すべてURLエンコードする必要があります。 –