{"thread":{"id":"5527","subject":"[PATCH] gitweb: support perl 5.6","startedAt":"2006-09-09T14:59:15Z","lastAt":"2006-09-09T22:20:09Z","messageCount":2,"participants":["Sven Verdoolaege","Jakub Narebski"],"isPatch":true,"patchVersion":1,"patchTotal":null},"messages":[{"id":"26635","messageId":"20060909145914.GA25289@liacs.nl","threadId":"5527","inReplyTo":null,"subject":"[PATCH] gitweb: support perl 5.6","fromName":"Sven Verdoolaege","fromEmail":"skimo@liacs.nl","sentAt":"2006-09-09T14:59:15Z","receivedAt":"2006-09-09T14:59:15Z","isPatch":true,"sender":{"key":"skimo@kotnet.org","avatar":null},"body":"Specifically, perl 5.6 doesn't have the Encode module and\ndoesn't support the open \"-|\" list form.\n\nSigned-off-by: Sven Verdoolage <skimo@liacs.nl>\n---\nThis is take three.\nI had missed the other binmodes in the code.\n\n gitweb/gitweb.perl |  102 +++++++++++++++++++++++++++++-----------------------\n 1 files changed, 57 insertions(+), 45 deletions(-)\n\ndiff --git a/gitweb/gitweb.perl b/gitweb/gitweb.perl\nindex d89f709..7afdf33 100755\n--- a/gitweb/gitweb.perl\n+++ b/gitweb/gitweb.perl\n@@ -12,11 +12,12 @@ use warnings;\n use CGI qw(:standard :escapeHTML -nosticky);\n use CGI::Util qw(unescape);\n use CGI::Carp qw(fatalsToBrowser);\n-use Encode;\n+eval { require Encode; import Encode; };\n+our $have_encode = !$@;\n use Fcntl ':mode';\n use File::Find qw();\n use File::Basename qw(basename);\n-binmode STDOUT, ':utf8';\n+binmode STDOUT, ':utf8' if $have_encode;\n \n our $cgi = new CGI;\n our $version = \"++GIT_VERSION++\";\n@@ -347,10 +348,16 @@ sub esc_param {\n \treturn $str;\n }\n \n+sub utf8_decode {\n+\tmy $str = shift;\n+\t$str = decode(\"utf8\", $str, eval \"Encode::FB_DEFAULT\") if $have_encode;\n+\treturn $str;\n+}\n+\n # replace invalid utf8 character with SUBSTITUTION sequence\n sub esc_html {\n \tmy $str = shift;\n-\t$str = decode(\"utf8\", $str, Encode::FB_DEFAULT);\n+\t$str = utf8_decode($str);\n \t$str = escapeHTML($str);\n \t$str =~ s/\\014/^L/g; # escape FORM FEED (FF) character (e.g. in COPYING file)\n \treturn $str;\n@@ -582,6 +589,12 @@ sub git_cmd {\n \treturn $GIT, '--git-dir='.$git_dir;\n }\n \n+# returns pipe reading from git command with given arguments\n+sub git_pipe {\n+\topen my $fd, \"-|\", join(' ', git_cmd(), @_) or return undef;\n+\treturn $fd;\n+}\n+\n # returns path to the core git executable and the --git-dir parameter as string\n sub git_cmd_str {\n \treturn join(' ', git_cmd());\n@@ -593,7 +606,7 @@ sub git_get_head_hash {\n \tmy $o_git_dir = $git_dir;\n \tmy $retval = undef;\n \t$git_dir = \"$projectroot/$project\";\n-\tif (open my $fd, \"-|\", git_cmd(), \"rev-parse\", \"--verify\", \"HEAD\") {\n+\tif (my $fd = git_pipe(\"rev-parse\", \"--verify\", \"HEAD\")) {\n \t\tmy $head = <$fd>;\n \t\tclose $fd;\n \t\tif (defined $head && $head =~ /^([0-9a-fA-F]{40})$/) {\n@@ -610,7 +623,7 @@ # get type of given object\n sub git_get_type {\n \tmy $hash = shift;\n \n-\topen my $fd, \"-|\", git_cmd(), \"cat-file\", '-t', $hash or return;\n+\tmy $fd = git_pipe(\"cat-file\", '-t', $hash) or return;\n \tmy $type = <$fd>;\n \tclose $fd or return;\n \tchomp $type;\n@@ -640,7 +653,7 @@ sub git_get_hash_by_path {\n \n \tmy $tree = $base;\n \n-\topen my $fd, \"-|\", git_cmd(), \"ls-tree\", $base, \"--\", $path\n+\tmy $fd = git_pipe(\"ls-tree\", $base, \"--\", $path)\n \t\tor die_error(undef, \"Open git-ls-tree failed\");\n \tmy $line = <$fd>;\n \tclose $fd or return undef;\n@@ -719,7 +732,7 @@ sub git_get_projects_list {\n \t\t\tif (-e \"$projectroot/$path/HEAD\") {\n \t\t\t\tmy $pr = {\n \t\t\t\t\tpath => $path,\n-\t\t\t\t\towner => decode(\"utf8\", $owner, Encode::FB_DEFAULT),\n+\t\t\t\t\towner => utf8_decode($owner),\n \t\t\t\t};\n \t\t\t\tpush @list, $pr\n \t\t\t}\n@@ -748,7 +761,7 @@ sub git_get_project_owner {\n \t\t\t$pr = unescape($pr);\n \t\t\t$ow = unescape($ow);\n \t\t\tif ($pr eq $project) {\n-\t\t\t\t$owner = decode(\"utf8\", $ow, Encode::FB_DEFAULT);\n+\t\t\t\t$owner = utf8_decode($ow);\n \t\t\t\tlast;\n \t\t\t}\n \t\t}\n@@ -771,7 +784,7 @@ sub git_get_references {\n \t\topen $fd, \"$projectroot/$project/info/refs\"\n \t\t\tor return;\n \t} else {\n-\t\topen $fd, \"-|\", git_cmd(), \"ls-remote\", \".\"\n+\t\t$fd = git_pipe(\"ls-remote\", \".\")\n \t\t\tor return;\n \t}\n \n@@ -792,7 +805,7 @@ sub git_get_references {\n sub git_get_rev_name_tags {\n \tmy $hash = shift || return undef;\n \n-\topen my $fd, \"-|\", git_cmd(), \"name-rev\", \"--tags\", $hash\n+\tmy $fd = git_pipe(\"name-rev\", \"--tags\", $hash)\n \t\tor return;\n \tmy $name_rev = <$fd>;\n \tclose $fd;\n@@ -840,7 +853,7 @@ sub parse_tag {\n \tmy %tag;\n \tmy @comment;\n \n-\topen my $fd, \"-|\", git_cmd(), \"cat-file\", \"tag\", $tag_id or return;\n+\tmy $fd = git_pipe(\"cat-file\", \"tag\", $tag_id) or return;\n \t$tag{'id'} = $tag_id;\n \twhile (my $line = <$fd>) {\n \t\tchomp $line;\n@@ -881,7 +894,7 @@ sub parse_commit {\n \t\t@commit_lines = @$commit_text;\n \t} else {\n \t\t$/ = \"\\0\";\n-\t\topen my $fd, \"-|\", git_cmd(), \"rev-list\", \"--header\", \"--parents\", \"--max-count=1\", $commit_id\n+\t\tmy $fd = git_pipe(\"rev-list\", \"--header\", \"--parents\", \"--max-count=1\", $commit_id)\n \t\t\tor return;\n \t\t@commit_lines = split '\\n', <$fd>;\n \t\tclose $fd or return;\n@@ -1098,7 +1111,7 @@ sub get_file_owner {\n \t}\n \tmy $owner = $gcos;\n \t$owner =~ s/[,;].*$//;\n-\treturn decode(\"utf8\", $owner, Encode::FB_DEFAULT);\n+\treturn utf8_decode($owner);\n }\n \n ## ......................................................................\n@@ -2206,8 +2219,8 @@ sub git_summary {\n \t}\n \tprint \"</table>\\n\";\n \n-\topen my $fd, \"-|\", git_cmd(), \"rev-list\", \"--max-count=17\",\n-\t\tgit_get_head_hash($project)\n+\tmy $fd = git_pipe(\"rev-list\", \"--max-count=17\",\n+\t\t\tgit_get_head_hash($project))\n \t\tor die_error(undef, \"Open git-rev-list failed\");\n \tmy @revlist = map { chomp; $_ } <$fd>;\n \tclose $fd;\n@@ -2286,7 +2299,7 @@ sub git_blame2 {\n \tif ($ftype !~ \"blob\") {\n \t\tdie_error(\"400 Bad Request\", \"Object is not a blob\");\n \t}\n-\topen ($fd, \"-|\", git_cmd(), \"blame\", '-l', $file_name, $hash_base)\n+\t$fd = git_pipe(\"blame\", '-l', $file_name, $hash_base)\n \t\tor die_error(undef, \"Open git-blame failed\");\n \tgit_header_html();\n \tmy $formats_nav =\n@@ -2352,7 +2365,7 @@ sub git_blame {\n \t\t$hash = git_get_hash_by_path($hash_base, $file_name, \"blob\")\n \t\t\tor die_error(undef, \"Error lookup file\");\n \t}\n-\topen ($fd, \"-|\", git_cmd(), \"annotate\", '-l', '-t', '-r', $file_name, $hash_base)\n+\t$fd = git_pipe(\"annotate\", '-l', '-t', '-r', $file_name, $hash_base)\n \t\tor die_error(undef, \"Open git-annotate failed\");\n \tgit_header_html();\n \tmy $formats_nav =\n@@ -2473,7 +2486,7 @@ sub git_blob_plain {\n \t\t}\n \t}\n \tmy $type = shift;\n-\topen my $fd, \"-|\", git_cmd(), \"cat-file\", \"blob\", $hash\n+\tmy $fd = git_pipe(\"cat-file\", \"blob\", $hash)\n \t\tor die_error(undef, \"Couldn't cat $file_name, $hash\");\n \n \t$type ||= blob_mimetype($fd, $file_name);\n@@ -2491,9 +2504,9 @@ sub git_blob_plain {\n \t\t-expires=>$expires,\n \t\t-content_disposition => \"inline; filename=\\\"$save_as\\\"\");\n \tundef $/;\n-\tbinmode STDOUT, ':raw';\n+\tbinmode STDOUT, ':raw' if $have_encode;\n \tprint <$fd>;\n-\tbinmode STDOUT, ':utf8'; # as set at the beginning of gitweb.cgi\n+\tbinmode STDOUT, ':utf8' if $have_encode; # as set at the beginning of gitweb.cgi\n \t$/ = \"\\n\";\n \tclose $fd;\n }\n@@ -2515,7 +2528,7 @@ sub git_blob {\n \t\t}\n \t}\n \tmy ($have_blame) = gitweb_check_feature('blame');\n-\topen my $fd, \"-|\", git_cmd(), \"cat-file\", \"blob\", $hash\n+\tmy $fd =git_pipe(\"cat-file\", \"blob\", $hash)\n \t\tor die_error(undef, \"Couldn't cat $file_name, $hash\");\n \tmy $mimetype = blob_mimetype($fd, $file_name);\n \tif ($mimetype !~ m/^text\\//) {\n@@ -2580,7 +2593,7 @@ sub git_tree {\n \t\t}\n \t}\n \t$/ = \"\\0\";\n-\topen my $fd, \"-|\", git_cmd(), \"ls-tree\", '-z', $hash\n+\tmy $fd = git_pipe(\"ls-tree\", '-z', $hash)\n \t\tor die_error(undef, \"Open git-ls-tree failed\");\n \tmy @entries = map { chomp; $_ } <$fd>;\n \tclose $fd or die_error(undef, \"Reading tree failed\");\n@@ -2648,9 +2661,9 @@ sub git_snapshot {\n \tmy $git_command = git_cmd_str();\n \topen my $fd, \"-|\", \"$git_command tar-tree $hash \\'$project\\' | $command\" or\n \t\tdie_error(undef, \"Execute git-tar-tree failed.\");\n-\tbinmode STDOUT, ':raw';\n+\tbinmode STDOUT, ':raw' if $have_encode;\n \tprint <$fd>;\n-\tbinmode STDOUT, ':utf8'; # as set at the beginning of gitweb.cgi\n+\tbinmode STDOUT, ':utf8' if $have_encode; # as set at the beginning of gitweb.cgi\n \tclose $fd;\n \n }\n@@ -2666,7 +2679,7 @@ sub git_log {\n \tmy $refs = git_get_references();\n \n \tmy $limit = sprintf(\"--max-count=%i\", (100 * ($page+1)));\n-\topen my $fd, \"-|\", git_cmd(), \"rev-list\", $limit, $hash\n+\tmy $fd = git_pipe(\"rev-list\", $limit, $hash)\n \t\tor die_error(undef, \"Open git-rev-list failed\");\n \tmy @revlist = map { chomp; $_ } <$fd>;\n \tclose $fd;\n@@ -2721,7 +2734,7 @@ sub git_commit {\n \tif (!defined $parent) {\n \t\t$parent = \"--root\";\n \t}\n-\topen my $fd, \"-|\", git_cmd(), \"diff-tree\", '-r', @diff_opts, $parent, $hash\n+\tmy $fd = git_pipe(\"diff-tree\", '-r', @diff_opts, $parent, $hash)\n \t\tor die_error(undef, \"Open git-diff-tree failed\");\n \tmy @difftree = map { chomp; $_ } <$fd>;\n \tclose $fd or die_error(undef, \"Reading git-diff-tree failed\");\n@@ -2828,8 +2841,8 @@ sub git_blobdiff {\n \tif (defined $hash_base && defined $hash_parent_base) {\n \t\tif (defined $file_name) {\n \t\t\t# read raw output\n-\t\t\topen $fd, \"-|\", git_cmd(), \"diff-tree\", '-r', @diff_opts, $hash_parent_base, $hash_base,\n-\t\t\t\t\"--\", $file_name\n+\t\t\t$fd = git_pipe(\"diff-tree\", '-r', @diff_opts, $hash_parent_base, $hash_base,\n+\t\t\t\t\"--\", $file_name)\n \t\t\t\tor die_error(undef, \"Open git-diff-tree failed\");\n \t\t\t@difftree = map { chomp; $_ } <$fd>;\n \t\t\tclose $fd\n@@ -2842,7 +2855,7 @@ sub git_blobdiff {\n \t\t\t# try to find filename from $hash\n \n \t\t\t# read filtered raw output\n-\t\t\topen $fd, \"-|\", git_cmd(), \"diff-tree\", '-r', @diff_opts, $hash_parent_base, $hash_base\n+\t\t\t$fd = git_pipe(\"diff-tree\", '-r', @diff_opts, $hash_parent_base, $hash_base)\n \t\t\t\tor die_error(undef, \"Open git-diff-tree failed\");\n \t\t\t@difftree =\n \t\t\t\t# ':100644 100644 03b21826... 3b93d5e7... M\tls-files.c'\n@@ -2876,9 +2889,9 @@ sub git_blobdiff {\n \t\t}\n \n \t\t# open patch output\n-\t\topen $fd, \"-|\", git_cmd(), \"diff-tree\", '-r', @diff_opts,\n+\t\t$fd = git_pipe(\"diff-tree\", '-r', @diff_opts,\n \t\t\t'-p', $hash_parent_base, $hash_base,\n-\t\t\t\"--\", $file_name\n+\t\t\t\"--\", $file_name)\n \t\t\tor die_error(undef, \"Open git-diff-tree failed\");\n \t}\n \n@@ -2912,7 +2925,7 @@ sub git_blobdiff {\n \t\t}\n \n \t\t# open patch output\n-\t\topen $fd, \"-|\", git_cmd(), \"diff\", '-p', @diff_opts, $hash_parent, $hash\n+\t\t$fd = git_pipe(\"diff\", '-p', @diff_opts, $hash_parent, $hash)\n \t\t\tor die_error(undef, \"Open git-diff failed\");\n \t} else  {\n \t\tdie_error('404 Not Found', \"Missing one of the blob diff parameters\")\n@@ -2997,8 +3010,8 @@ sub git_commitdiff {\n \tmy $fd;\n \tmy @difftree;\n \tif ($format eq 'html') {\n-\t\topen $fd, \"-|\", git_cmd(), \"diff-tree\", '-r', @diff_opts,\n-\t\t\t\"--patch-with-raw\", \"--full-index\", $hash_parent, $hash\n+\t\t$fd = git_pipe(\"diff-tree\", '-r', @diff_opts,\n+\t\t\t\"--patch-with-raw\", \"--full-index\", $hash_parent, $hash)\n \t\t\tor die_error(undef, \"Open git-diff-tree failed\");\n \n \t\twhile (chomp(my $line = <$fd>)) {\n@@ -3008,8 +3021,8 @@ sub git_commitdiff {\n \t\t}\n \n \t} elsif ($format eq 'plain') {\n-\t\topen $fd, \"-|\", git_cmd(), \"diff-tree\", '-r', @diff_opts,\n-\t\t\t'-p', $hash_parent, $hash\n+\t\t$fd = git_pipe(\"diff-tree\", '-r', @diff_opts,\n+\t\t\t'-p', $hash_parent, $hash)\n \t\t\tor die_error(undef, \"Open git-diff-tree failed\");\n \n \t} else {\n@@ -3108,8 +3121,7 @@ sub git_history {\n \t}\n \tgit_print_page_path($file_name, $ftype, $hash_base);\n \n-\topen my $fd, \"-|\",\n-\t\tgit_cmd(), \"rev-list\", \"--full-history\", $hash_base, \"--\", $file_name;\n+\tmy $fd = git_pipe(\"rev-list\", \"--full-history\", $hash_base, \"--\", $file_name);\n \n \tgit_history_body($fd, $refs, $hash_base, $ftype);\n \n@@ -3150,7 +3162,7 @@ sub git_search {\n \tmy $alternate = 0;\n \tif ($commit_search) {\n \t\t$/ = \"\\0\";\n-\t\topen my $fd, \"-|\", git_cmd(), \"rev-list\", \"--header\", \"--parents\", $hash or next;\n+\t\tmy $fd = git_pipe(\"rev-list\", \"--header\", \"--parents\", $hash or next);\n \t\twhile (my $commit_text = <$fd>) {\n \t\t\tif (!grep m/$searchtext/i, $commit_text) {\n \t\t\t\tnext;\n@@ -3271,7 +3283,7 @@ sub git_shortlog {\n \tmy $refs = git_get_references();\n \n \tmy $limit = sprintf(\"--max-count=%i\", (100 * ($page+1)));\n-\topen my $fd, \"-|\", git_cmd(), \"rev-list\", $limit, $hash\n+\tmy $fd = git_pipe(\"rev-list\", $limit, $hash)\n \t\tor die_error(undef, \"Open git-rev-list failed\");\n \tmy @revlist = map { chomp; $_ } <$fd>;\n \tclose $fd;\n@@ -3299,7 +3311,7 @@ ## feeds (RSS, OPML)\n \n sub git_rss {\n \t# http://www.notestips.com/80256B3A007F2692/1/NAMO5P9UPQ\n-\topen my $fd, \"-|\", git_cmd(), \"rev-list\", \"--max-count=150\", git_get_head_hash($project)\n+\tmy $fd = git_pipe(\"rev-list\", \"--max-count=150\", git_get_head_hash($project))\n \t\tor die_error(undef, \"Open git-rev-list failed\");\n \tmy @revlist = map { chomp; $_ } <$fd>;\n \tclose $fd or die_error(undef, \"Reading git-rev-list failed\");\n@@ -3322,8 +3334,8 @@ XML\n \t\t\tlast;\n \t\t}\n \t\tmy %cd = parse_date($co{'committer_epoch'});\n-\t\topen $fd, \"-|\", git_cmd(), \"diff-tree\", '-r', @diff_opts,\n-\t\t\t$co{'parent'}, $co{'id'}\n+\t\t$fd = git_pipe(\"diff-tree\", '-r', @diff_opts,\n+\t\t\t$co{'parent'}, $co{'id'})\n \t\t\tor next;\n \t\tmy @difftree = map { chomp; $_ } <$fd>;\n \t\tclose $fd\n@@ -3341,7 +3353,7 @@ XML\n \t\t      \"<![CDATA[\\n\";\n \t\tmy $comment = $co{'comment'};\n \t\tforeach my $line (@$comment) {\n-\t\t\t$line = decode(\"utf8\", $line, Encode::FB_DEFAULT);\n+\t\t\t$line = utf8_decode($line);\n \t\t\tprint \"$line<br/>\\n\";\n \t\t}\n \t\tprint \"<br/>\\n\";\n@@ -3350,7 +3362,7 @@ XML\n \t\t\t\tnext;\n \t\t\t}\n \t\t\tmy $file = validate_input(unquote($7));\n-\t\t\t$file = decode(\"utf8\", $file, Encode::FB_DEFAULT);\n+\t\t\t$file = utf8_decode($file);\n \t\t\tprint \"$file<br/>\\n\";\n \t\t}\n \t\tprint \"]]>\\n\" .\n-- \n0.99.8c.g64e8-dirty\n"},{"id":"26656","messageId":"edveli$p2m$1@sea.gmane.org","threadId":"5527","inReplyTo":"20060909145914.GA25289@liacs.nl","subject":"Re: [PATCH] gitweb: support perl 5.6","fromName":"Jakub Narebski","fromEmail":"jnareb@gmail.com","sentAt":"2006-09-09T22:20:09Z","receivedAt":"2006-09-09T22:20:09Z","isPatch":true,"sender":{"key":"jnareb@gmail.com","avatar":"https://avatars.githubusercontent.com/u/2706?v=4"},"body":"Sven Verdoolaege wrote:\n\n> +# returns pipe reading from git command with given arguments\n> +sub git_pipe {\n> +       open my $fd, \"-|\", join(' ', git_cmd(), @_) or return undef;\n> +       return $fd;\n> +}\n> +\n\nI'm sorry, but this is not enough. For example the $file_name argument\nshould be quoted in shell, i.e. in three argument magic open \"-|\". So\neither you return to your old patch, which changes each list form of open\n\"-|\" into old three argument form (which adds penalty of additional shell\ninvocation, and is prone to shell interpretation of arguments), and\nsometimes add quotes (e.g. \"... \\'$file_name\\' ...\"), or (what would be\nbetter) to reimplement list form of open \"-|\" using two argument forking\nopen \"-|\", and doing exec in child, a la \"Safe Pipe Opens\" in perlipc(3pm).\n\n-- \nJakub Narebski\nWarsaw, Poland\nShadeHawk on #git\n"}]}