免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 2031 | 回复: 7

socket实例可以通过pack 发送到另一个进程吗? [复制链接]

论坛徽章:
1
操作系统版块每日发帖之星
日期:2016-06-12 06:20:00
发表于 2016-12-10 16:59 |显示全部楼层
比如有两个进程 分别跑两个服务


  1. use IO::Select;
  2. use IO::Socket;
  3. $srv = IO::Socket::INET->new(Listen => 1, LocalPort => 8080);
  4. $alive = IO::Select->new( $srv );
  5. while(@ready = $alive->can_read) {

  6.     foreach $conn (@ready) {
  7.         if($conn == $srv) {
  8.             # Create a new socket
  9.             $new = $srv->accept;
  10.             $alive->add($new);
  11.         }
  12.         else {
  13.    $len = $conn->recv($buffer,1024,0);
  14.            # print "$buffer \n";

  15.             $conn->send("HTTP/1.0 200 OK\r\nConnection: keep-alive\r\nServer: A-server \r\nContent-Type: text/html\r\nContent-Length: 16\r\n\r\nThis is A server");

  16.         }
  17.     }
  18. }
复制代码


B服务




  1. use IO::Select;
  2. use IO::Socket;
  3. $srv = IO::Socket::INET->new(Listen => 1, LocalPort => 9090);
  4. $alive = IO::Select->new( $srv );
  5. while(@ready = $alive->can_read) {

  6.     foreach $conn (@ready) {
  7.         if($conn == $srv) {
  8.             # Create a new socket
  9.             $new = $srv->accept;
  10.             $alive->add($new);
  11.         }
  12.         else {
  13.    $len = $conn->recv($buffer,1024,0);
  14.            # print "$buffer \n";

  15.             $conn->send("HTTP/1.0 200 OK\r\nConnection: keep-alive\r\nServer: B-server \r\nContent-Type: text/html\r\nContent-Length: 16\r\n\r\nThis is B server");

  16.         }
  17.     }
  18. }
复制代码

有没有办法 将第一个进程建立好的连接 $conn 发送到第二个进程里面的@ready?



论坛徽章:
42
19周年集字徽章-周
日期:2019-10-14 14:35:31平安夜徽章
日期:2015-12-26 00:06:30数据库技术版块每日发帖之星
日期:2015-12-01 06:20:002015亚冠之首尔
日期:2015-11-04 22:25:43IT运维版块每日发帖之星
日期:2015-08-17 06:20:00寅虎
日期:2014-06-04 16:25:27狮子座
日期:2014-05-12 11:00:00辰龙
日期:2013-12-20 17:07:19射手座
日期:2013-10-24 21:01:23CU十二周年纪念徽章
日期:2013-10-24 15:41:34IT运维版块每日发帖之星
日期:2016-01-27 06:20:0015-16赛季CBA联赛之新疆
日期:2016-06-07 14:10:01
发表于 2016-12-13 08:23 |显示全部楼层
进程间共享句柄是不行的,还是老实用IPC吧。
不明白你的目的,想实现proxy? 管道就可以。
你把流送过去也是可以的,

论坛徽章:
1
操作系统版块每日发帖之星
日期:2016-06-12 06:20:00
发表于 2016-12-13 12:38 |显示全部楼层
本帖最后由 yakczh_cu 于 2016-12-13 12:52 编辑

回复 2# laputa73


  1.   require 5.002;
  2.     use strict;
  3.     BEGIN { $ENV{PATH} = '/usr/ucb:/bin' }
  4.     use Socket;
  5.     use Carp;

  6.     $|=1;

  7.     sub spawn;  # forward declaration
  8.     sub logmsg {
  9.         open LOG,'>>log.txt';
  10.         print LOG "\n$0 $: @_ at ", scalar localtime, "\n"


  11.     }



  12.     my $port = shift || 80;
  13.     my $proto = getprotobyname('tcp');
  14.     $port = $1 if $port =~ /(\d+)/; # untaint port number

  15.     socket(Server, PF_INET, SOCK_STREAM, $proto)        || die "socket: $!";
  16.     setsockopt(Server, SOL_SOCKET, SO_REUSEADDR,
  17.                                         pack("l", 1))   || die "setsockopt: $!";
  18.     bind(Server, sockaddr_in($port, INADDR_ANY))        || die "bind: $!";
  19.     listen(Server,SOMAXCONN)                            || die "listen: $!";

  20.     print  "\n master server   $§  started on port $port";

  21.     my $waitedpid = 0;
  22.     my $paddr;

  23.     sub REAPER {
  24.         $waitedpid = wait;
  25.         $SIG{CHLD} = \&REAPER;  # loathe sysV
  26.         logmsg "reaped $waitedpid" . ($? ? " with exit $?" : '');
  27.     }

  28.     $SIG{CHLD} = \&REAPER;

  29.     for ( $waitedpid = 0;
  30.           ($paddr = accept(Client,Server)) || $waitedpid;
  31.           $waitedpid = 0, close Client)
  32.     {
  33.         next if $waitedpid and not $paddr;
  34.         my($port,$iaddr) = sockaddr_in($paddr);
  35.         my $name = gethostbyaddr($iaddr,AF_INET);

  36.         logmsg "connection from $name [",
  37.                 inet_ntoa($iaddr), "]
  38.                 at port $port";

  39.         spawn sub {
  40.             #print "Hello there, $name, it's now ", scalar localtime, "\n";

  41.             logmsg "\n this is worker $§ ";
  42.             print "HTTP/1.0 200 OK\r\nConnection: close\r\n\r\n<h1> this is $§" </h1>";
  43.                 or confess "can't exec fortune: $!";

  44.         };

  45.     }

  46.     sub spawn {
  47.         my $coderef = shift;

  48.         open(STDIN,  "<&Client")   || die "can't dup client to stdin";
  49.         open(STDOUT, ">&Client")   || die "can't dup client to stdout";
  50.         open(STDERR, ">&STDOUT") || die "can't dup stdout to stderr";

  51.         #print $coderef;

  52.         unless (@_ == 0 && $coderef && ref($coderef) eq 'CODE') {
  53.             confess "usage: spawn CODEREF";
  54.         }

  55.         my $pid;
  56.         if (!defined($pid = fork)) {
  57.             logmsg "cannot fork: $!";
  58.             return;
  59.         } elsif ($pid) {
  60.             logmsg "FORK OK  $pid";
  61.             return; # I'm the parent
  62.         }
  63.         # else I'm the child -- go spawn
  64. #        print "\nchild ->",$;

  65.      logmsg "\n spawn wrap   worker    $§";


  66.        &$coderef();

  67. sleep(1);
  68. #       exit 0;
  69.     }

复制代码

用管道确实可以    但是这样写来一个请求就会Spawn 一下新的perl进程, 如果要象nginx那样,启动固定数量的 worer  该怎么写?

论坛徽章:
1
操作系统版块每日发帖之星
日期:2016-06-12 06:20:00
发表于 2016-12-13 12:38 |显示全部楼层

重复代码删除

本帖最后由 yakczh_cu 于 2016-12-13 12:44 编辑

perl代码数据库报错,发重复了,请删除

论坛徽章:
1
操作系统版块每日发帖之星
日期:2016-06-12 06:20:00
发表于 2016-12-13 12:39 |显示全部楼层

perl代码数据库报错,发重复了

本帖最后由 yakczh_cu 于 2016-12-13 12:43 编辑

 perl代码数据库报错,发重复了

论坛徽章:
42
19周年集字徽章-周
日期:2019-10-14 14:35:31平安夜徽章
日期:2015-12-26 00:06:30数据库技术版块每日发帖之星
日期:2015-12-01 06:20:002015亚冠之首尔
日期:2015-11-04 22:25:43IT运维版块每日发帖之星
日期:2015-08-17 06:20:00寅虎
日期:2014-06-04 16:25:27狮子座
日期:2014-05-12 11:00:00辰龙
日期:2013-12-20 17:07:19射手座
日期:2013-10-24 21:01:23CU十二周年纪念徽章
日期:2013-10-24 15:41:34IT运维版块每日发帖之星
日期:2016-01-27 06:20:0015-16赛季CBA联赛之新疆
日期:2016-06-07 14:10:01
发表于 2016-12-14 08:30 |显示全部楼层
那不一样,父子进程之间是有关联的,父进程的内存空间会复制到子进程,包括句柄
你可以看看mojo之类的prefork-worker代码,都是类似的。

论坛徽章:
1
操作系统版块每日发帖之星
日期:2016-06-12 06:20:00
发表于 2016-12-14 19:18 |显示全部楼层
回复 7# laputa73

如果是单独的进程, 不是 写在一份代码里的,  有没有办法可以通过管道通信?

论坛徽章:
42
19周年集字徽章-周
日期:2019-10-14 14:35:31平安夜徽章
日期:2015-12-26 00:06:30数据库技术版块每日发帖之星
日期:2015-12-01 06:20:002015亚冠之首尔
日期:2015-11-04 22:25:43IT运维版块每日发帖之星
日期:2015-08-17 06:20:00寅虎
日期:2014-06-04 16:25:27狮子座
日期:2014-05-12 11:00:00辰龙
日期:2013-12-20 17:07:19射手座
日期:2013-10-24 21:01:23CU十二周年纪念徽章
日期:2013-10-24 15:41:34IT运维版块每日发帖之星
日期:2016-01-27 06:20:0015-16赛季CBA联赛之新疆
日期:2016-06-07 14:10:01
发表于 2016-12-14 22:50 |显示全部楼层
可以通过命名管道实现独立进程的ipc.
进程间通信还有文件、共享内存、数据库、内存数据库、socket通信等。
你可以看看骆驼书的进程间通信一节
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP