[#697] ++[Re: dylan [Re: swap values(Re: call by reference)]] —
けいじゅ@SHLジャパンです.
1 message
1996/10/01
[#869] Append Member — Kouki Higuchi <luke@...>
Please let me be a participate.
1 message
1996/10/20
[#895] sleep eternaly on BOW(Re: ruby 0.99.2-961023 available) — Shin-ichiro Hara <sinara@...>
原です。
6 messages
1996/10/24
[#906] [REQ]Get Strings!<3> GETS, SUB — Shin-ichiro Hara <sinara@...>
原です。
5 messages
1996/10/27
[#907] [REQ]Get Strings!<4> SPLIT — Shin-ichiro Hara <sinara@...>
原です。
6 messages
1996/10/27
[#920] bug report(each) — keiju@... (Keiju ISHITSUKA)
けいじゅ@SHLジャパンです.
8 messages
1996/10/29
[#928] Re: hajimemashite — Itsuro Saito <saito@...>
斎藤@東大電子情報です.
9 messages
1996/10/29
[#938] ruby 0.99.3-961030 available — matz@... (Yukihiro Matsumoto)
まつもと ゆきひろです.
7 messages
1996/10/30
[#954] Rational — keiju@... (Keiju ISHITSUKA)
けいじゅ@SHLジャパンです.
23 messages
1996/10/30
[#955] Re: Rational
— matz@... (Yukihiro Matsumoto)
1996/10/30
まつもと ゆきひろです.
[#968] Re: Rational
—
1996/10/31
けいじゅ@SHLジャパンです.
[#970] Re: Rational
— matz@... (Yukihiro Matsumoto)
1996/10/31
まつもと ゆきひろです.
[#956] Re: Rational[coerce(Re: ruby 0.99.3-961030 available) ] — Shin-ichiro Hara <sinara@...>
原です。
4 messages
1996/10/30
[#965] ruby-mode — Yasuo OHBA <jammy@...>
大庭@SHLJapanです.
6 messages
1996/10/31
[ruby-list:760] httpd.rb (Re: sample/svr.rb (socket, select))
From:
Hara Shin-ichiro <sinara@...>
Date:
1996-10-05 04:19:43 UTC
List:
ruby-list #760
原です。
>黒田です.
>>sample/ にある svr.rb ですが、何度か動かして見たのですが、
>>中身を今回はじめてよみました。^^;
>>
>>これ面白いです。fork も Thread も使わずに、複数のクライアントに
>>サービスしている。
>この svr.rb を良く理解せずに httpd に書きかえていたのですが,
>netscape みたいなクライアントが, 一度に複数のコネクションを張
>ろうとすると, うまくいかない(要求したとおりのものをくれない)の
>ですが, しょうがないんでしょうか? こういう時こそ thread の出番
>なんでしょうか?
奇遇ですねー。私も朝から Thread の練習にと思って、同じことをしてい
ました。私の考えた方法は、そのまんま svr.rb をぱくって
def session(s)
# s でなんとか
s.close
$m.syncronize{ $threads -= 1 }
end
while TRUE
nsock = select(socks)
next if nsock == nil
for s in nsock[0]
if s == gs
ns = s. accept
socks.push(ns)
else
socks.delete(s)
while $threads >= $max_thread; sleep 0.1; end;
$m.syncronize{ $threads += 1 }
Thread.start{ session(s) }
end
end
end
と、いう風にしてみました。これでいいのかなー。
ちなみに Thread なし(下のスクリプトで $max_thread = 0)でもちゃ
んと netscape で読めたので、黒田さんのうまくいかない原因は別の
所にあるのではないでしょうか?
で、結論として Thread を使わないほうが倍も早いです。^^; Thread
の実装にファンクションコールの select を使っているそうなので、
どっちにしろ select を使っている事になり、Thread のご利益が少
ないのかもしれません。server の CPU が速くて、コネクションあた
りの通信速度が遅く、送るデータサイズが大きければ結果はちがうと
おもいますが。
sleep 0.1 をやめると、さらに極端にパフォーマンスが落ちます。普
通、各スレッドの働き具合をコントロールするにはどうするのでしょ
うか?
以下に httpd.rb をベタに張り付けます。いちおう手もとの CGI,
clickable map はうごいていますが、あくまで練習。けっこういい
かげんです。
---------^ httpd.rb
#!/usr/local/bin/ruby
# USAGE: httpd.rb [PORT]
$port = 80
$max_thread = 4
$host_name = "www.nagaokaut.ac.jp"
$root_dir = "/usr/local/etc/httpd"
$user_dir = "public_html"
$html_dir = $root_dir + "/htdocs"
$icons_dir = $root_dir + "/icons"
$icons_vdir = "/icons"
$cgi_dir = $root_dir + "/cgi-bin"
$cgi_vdir = "/cgi-bin"
$default_html = ["index.html", "index.shtml"]
$version = "MIME-Version: 1.0\nServer: httpd.rb/1.1\n"
require "thread" if $max_thread > 0
require "socket"
$envs = ['HTTP_REFERER','CONTENT_LENGTH','QUERY_STRING',
'REQUEST_METHOD', 'PATH_INFO', 'PATH_TRANSLATED', 'SCRIPT_NAME']
def read_head(s)
phost_name = s.peeraddr[2]
while s.gets
if /(GET|POST)\s+(\S*)\s*(HTTP.*)/i
rqst, html, vers = $1.upcase, $2, $3
ENV['REQUEST_METHOD'] = rqst
print "(#{phost_name}): ", $_
end
ENV['HTTP_REFERER'] = $1 if /Referer: *(.+)/i
ENV['CONTENT_LENGTH'] = $1 if /Content-length: *(.+)/i
break if /^\r?\n$/
end
param = ''
html, param = $1, $2 if html =~ /([^\?]+)\?(.*)/
[rqst, html, param, vers]
end
def fname_complete(fname)
if fname =~ /\/$/
for i in $default_html
filename = fname + i
if FileTest.file?(filename)
return filename
end
end
end
fname
end
def mk_local_name(html)
filename = if html =~ /^#$icons_vdir\//o
html.sub(/^#$icons_vdir/o, $icons_dir)
elsif html =~ /^\/~([^\/]+)/
html.sub(/^\/~([^\/]+)/, '/home/'+$1+"/#$user_dir/")
else
$html_dir + html
end
filename
end
def do_cgi(s, rqst, html, param)
html =~ /^(#$cgi_vdir)(\/[^\/]+)(.*)/o;
ENV['SCRIPT_NAME'] = $1 + $2
cgi, map = $cgi_dir + $2, $3
if map
ENV['PATH_INFO'] = map
ENV['PATH_TRANSLATED'] = mk_local_name(map)
end
if html !~ /^#$cgi_vdir\/nph-[^\/]+/o
head = if map then "HTTP/1.0 302 Found" else "HTTP/1.0 200 OK\n" end
head += $version
end
if param != ''
(param0 = param.dup).gsub!(/\+/, "' '")
cgi += " '" + param0 + "'"
end
if rqst == 'GET'
ENV['QUERY_STRING'] = param
body = `#{cgi}`
elsif rqst == 'POST'
str = s.read(ENV['CONTENT_LENGTH'])
t = IO.popen(cgi, "r+")
t << str
t.flush
body = t.read
t.close
end
[head, body]
end
def get_image(html)
filename = mk_local_name(html)
filename = fname_complete(filename)
if FileTest.file?(filename)
type = if filename =~ /\.([^.]+)$/; $1; else; 'plain'; end
cat = if type =~ /txt|text|htm|plain/i; 'text'; else 'image'; end
head = "HTTP/1.0 200 Document follows\n" + $version +
"Content-Type: #{cat}/#{type}\n\n"
h = open(filename)
body = h.read
h.close
elsif FileTest.directory?(filename)
head = "HTTP/1.0 302 Found\n" + $version +
"Content-Type: text/html\n" +
"Location: http://#$host_name:#$port#{html}/\n\n"
body = ''
else
head = "HTTP/1.0 404 Not Found\n" + $version +
"Content-Type: text/html\n\n"
body = "<HEAD><TITLE>NOT FOUND</TITLE></HEAD>\n" +
"<HTML><BODY><H2>File(#{html}) Not Found.</H2></BODY><HTML>\n"
end
[head, body]
end
def session(s)
$envs.each{ |e| ENV.delete(e) }
rqst, html, param, vers = read_head(s)
if html =~ /^#$cgi_vdir\//o
head, body = do_cgi(s, rqst, html, param)
else
head, body = get_image(html)
end
s << head << body
s.close
$m.syncronize{ $threads -= 1 } if $max_thread > 0
end
ENV['HTTP_HOST'] = $host_name
ENV['DOCUMENT_ROOT'] = $html_dir
if ARGV.size > 0; $port = ARGV[0]; end
ENV['SERVER_PORT'] = $port.to_s
gs = TCPserver.open($port)
socks = [gs]
printf("START on %d\n", gs.addr[1])
if $max_thread > 0
$m = Mutex.new
$threads = 0
end
while TRUE
nsock = select(socks)
next if nsock == nil
for s in nsock[0]
if s == gs
ns = s. accept
socks.push(ns)
else
socks.delete(s)
if $max_thread == 0
session(s)
else
while $threads >= $max_thread; sleep 0.1; end;
$m.syncronize{ $threads += 1 }
Thread.start{ session(s) }
# print "New Thread(#$threads threads running).\n"
end
end
end
end
---------$ httpd.rb
---===-=-=-=-=-=-=-=-=======--=-=-=-==-=-===-=-=-=-=-=-=--=-==-=--
Shin-ichro Hara(Nagaoka Univ.of Tech.)