<img src="xx.cgi">で画像を表示させるには?

[上に] [前に] [次に]
すし屋 1998/10/23(金) 04:39:13
Perlでカウンタを作りたいのですが、

--xx.cgi--
print "Content-type: image/gif\n\n";

open(IMAGE, 'xx.gif');
$size = (-s IMAGE);
binmode(IMAGE);
sysread(IMAGE, $image, $size);
close(IMAGE);

binmode(STDOUT);
syswrite(STDOUT, $image, $size);
--eof--

として、<img src="xx.cgi">
とやるとなぜか表示されないのです。
STDOUTをファイルに指定すると、きちんとxx.gifと同じファイルができあがります。
#ローカルで実験しています。Windowsです。

B-Cus 1998/10/23(金) 04:44:31
winは知りませんが、気になった点としては、
・binmodeの前にサイズを計算して大丈夫でしょうか(asciiで計算されない?)
・img srcではなく、直接xx.cgiを読むと画像は表示されるのでしょうか。

 print "Content-type: image/gif\n\n";
 open(IMAGE, 'xx.gif');
 binmode(IMAGE);
 binmode(STDOUT);
 print <IMAGE>;

だとどうでしょう。あと、もしサイズを求めるんなら
Content-length: を出力すると親切かも。

B-Cus 1998/10/23(金) 05:04:15
あるいは binmode(STDOUT) の前に Content-type を表示して
しまっているので、binmodeがうまく働いてない、というのはダメ?

つまり
 binmode(STDOUT)→print "Content-type: ..";
の順にするとか。

…うーん、どれもこれもタトくさいなぁ。

かっくん 1998/10/23(金) 11:15:51

私の場合、サーバ上では

open (IMG, "$gifname");
print "Content-type: image/gif\n\n";
print <IMG>;
close(IMG);

これだけで表示されますが、ローカルで
AN-HTTPD + perl for Win32の場合は壊れて表示されます。
これはHTTPDかperlのどちらかのバグだと思います。


mo [E-Mail] 1998/10/23(金) 21:34:04
perl の記述に誤りがあります。

誤:print <IMG>;
正:{local($/); print <IMG>; }

<> 演算子は "\n" が現れる所までしか読みません。
一度に全てのデータを読み取るには、$/ を未定義、あるいは
空文字列にします。

mo [E-Mail] 1998/10/24(土) 00:45:09
すみません。私が間違っていました。

print <IMG>;

で OK なはずです。何をぼけていたんだろうか。

すし屋 1998/10/24(土) 03:36:52
みなさんありがとうございます。
僕が上に書いたスクリプトをサーバー上で試したのですが、(binmode()は消しました)
なぜか動きませんでした。
B-Cusさんの発言の物もいろいろ組み合わせて試したのですが、だめでした。
ブラウザからではなくDOSからPerl.exeを使って試したところ最終バイトまで出力されるので、
#ビープ音が鳴りつつ(^^;;
かっくんさんのは全く同じ症状です。画像の情報をブラウザで表示すると、40バイトだけ出力されています。
サーバー上では動作します。

とりあえず、かっくんさんのスクリプトをお借りしますm(_ _)m。

そこでふと、とほほさんのカウンタはローカルで、動作するのかと思い、実験しました。
やはりPerl for win32かAn HTTPdを疑ってみることにします。
ローカル依存の話で申し訳ございませんでした。

一応解決としておきます。
みなさんありがとうございました。

すし屋 1998/10/24(土) 03:44:48
妙な文のまま送ってしまったので、出直します。ごめんなさい。

みなさんありがとうございます。
僕が上に書いたスクリプトをサーバー上で試したのですが、(binmode()は消しました)
なぜか動きませんでした。
B-Cusさんの発言の物もいろいろ組み合わせて試したのですが、だめでした。
ブラウザからではなくDOSからPerl.exeを使って試したところ最終バイトまで出力されるので、
#ビープ音が鳴りつつ(^^;;
AnHTTPdなのでは?と思っています。

かっくんさんのは全く同じ症状です。画像の情報をブラウザで表示すると、40バイトだけ出力されています。
サーバー上では動作します。

とりあえず、かっくんさんのスクリプトをお借りしますm(_ _)m。

そこでふと、とほほさんのカウンタはローカルで、動作するのかと思い、実験しました。
結果は「perl for win32+AnHTTPdでは動かず」でした。
やはりPerl for win32かAn HTTPdを疑ってみることにします。
ローカル依存の話で申し訳ございませんでした。

一応解決としておきます。
みなさんありがとうございました。

ひろぼー 1998/10/28(水) 07:55:46
Perl for win32 で read("file.jpg", $buff, 256); とすると、0x1A (^Z) が現れた所で読込が中断されます。<>演算子も同様。
DOSでは正常な動作だと思います。binmodeは必要では?
すし屋さんの「最後まで出力された」のが不思議ですが・・・

一番最初のスクリプトがうまくいかなかったのは、
printで出力したヘッダ行がバッファリングされるのに対し、
syswriteはバッファを飛ばして出力してしまうので、
ヘッダ行はバッファに残ったままになってるんじゃないですかね?
syswriteじゃなくて、単純にprintかwriteを使えばいいのでは?
あるいは、printの後ろにフラッシュ処理を入れて見るとか
  $s = select(STDOUT); $| = 1; select($s); print "";

はずしてたらごめんなさいね。

ひろぼー 1998/10/30(金) 07:28:00
すし屋さん、もう見てないかも知れないけど、
嘘書いてしまったこともあり再登場です。
write命令はCのfwriteに対応するものじゃなかったんですね。

フラッシュ処理を入れたものも動きましたが、以下の方が簡単。
Perl for Win32 + AnHTTPd で確認。
 open(IMAGE, 'xx.gif');
 binmode(IMAGE);
 $size = read(IMAGE, $image, -s IMAGE);
 close(IMAGE);
 print "Content-type: image/gif\n\n";
 binmode(STDOUT);
 print $image;

[上に] [前に] [次に]