首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >在PHP中使用共享内存时未排除的错误(PHP警告: shmop_open():无法附加或创建共享内存段“无效参数”)

在PHP中使用共享内存时未排除的错误(PHP警告: shmop_open():无法附加或创建共享内存段“无效参数”)
EN

Stack Overflow用户
提问于 2017-10-20 03:35:05
回答 1查看 1.9K关注 0票数 4

我刚刚开始使用PHP中的共享内存来做一些事情。这是我的密码。

代码语言:javascript
复制
 <?php
//limit the task to be forked
$task = 100;
$process_pool = array();
//allocate 1kb memory segment to store process_pool
$process_pool_key = ftok(__FILE__,chr(0));
$process_pool_shm = shmop_open($process_pool_key,'c',0644,1024);
$datas = array();
for($i = 1; $i<= $task; $i++) {
    $pid = pcntl_fork();
    if ($pid == -1) {
        die("Can't fork child process.");
    }
    if ($pid == 0) {
        $current_pid = getmypid();
        $process_pool_size = shmop_size($process_pool_shm);
        $process_pool = @unserialize(shmop_read($process_pool_shm,0,$process_pool_size));
        //store child process data into specific memory
        $child_data  = array('pid'=>$current_pid,"data"=>[rand(),'hello']);
        $child_key = ftok(__FILE__,chr($current_pid));
   }

        $size = 1024*1024; 
        $child_shm = shmop_open($child_key,'c',0644,$size);
        shmop_write($child_shm,serialize($child_data),0);
        exit(0);
    } else {
       $process_pool[$pid] = array($pid);
       shmop_write($process_pool_shm,serialize($process_pool),0);
   }
}
while(pcntl_waitpid(-1,$status) > 0);
//Read data from all child process
foreach($process_pool as $pid => $pid_info) {
    $tmp_key = ftok(__FILE__,chr($pid));
    $size= 1024*1024;
    $tmp_shm  = shmop_open($tmp_key,'a',0644,$size);
    $org_data = shmop_read($tmp_shm,0,$size);
    $child_data = @unserialize($org_data);
    if (empty($child_data)) {
        echo "$tmp_key\n";
    }
    shmop_delete($tmp_shm);
    shmop_close($tmp_shm);
    if (!empty($child_data)) {
        $datas[$pid] = $child_data;
    }
}
var_dump(count($datas));
//var_dump(count($process_pool));
//var_dump(count(array_keys($datas)));
//var_dump(count(array_keys($process_pool)));
foreach (array_keys($process_pool) as $p_key) {
    if (!in_array($p_key,array_keys($datas))) {
        echo $p_key."\n";
    }
}
shmop_delete($process_pool_shm);
shmop_close($process_pool_shm);

上面的代码涉及几个子进程,它们保存自己的共享内存段--子进程的每个other.Shared内存段用于在子进程完成processed.And后存储数据--父进程将从子进程的共享内存段中收集数据。

在我看来,这段代码应该没有任何问题。但有些意想不到的问题是随机产生的。

有时很顺利,

代码语言:javascript
复制
/home/jhbian/pider/test/process/ReproduceProcessExample.php:60:
int(100)

有时会打击

代码语言:javascript
复制
 PHP Warning:  shmop_open(): unable to attach or create shared memory segment 'Invalid argument' in /home/jhbian/pider/test/process/ReproduceProcessExample.php on line 29
PHP Stack trace:
PHP   1. {main}() /home/jhbian/pider/test/process/ReproduceProcessExample.php:0
PHP   2. shmop_open() /home/jhbian/pider/test/process/ReproduceProcessExample.php:29

Warning: shmop_open(): unable to attach or create shared memory segment 'Invalid argument' in /home/jhbian/pider/test/process/ReproduceProcessExample.php on line 29

Call Stack:
    0.0002     366568   1. {main}() /home/jhbian/pider/test/process/ReproduceProcessExample.php:0
    0.0738     367872   2. shmop_open() /home/jhbian/pider/test/process/ReproduceProcessExample.php:29

PHP Warning:  shmop_write() expects parameter 1 to be resource, boolean given in /home/jhbian/pider/test/process/ReproduceProcessExample.php on line 30
PHP Stack trace:
PHP   1. {main}() /home/jhbian/pider/test/process/ReproduceProcessExample.php:0
PHP   2. shmop_write() /home/jhbian/pider/test/process/ReproduceProcessExample.php:30

Warning: shmop_write() expects parameter 1 to be resource, boolean given in /home/jhbian/pider/test/process/ReproduceProcessExample.php on line 30

Call Stack:
    0.0002     366568   1. {main}() /home/jhbian/pider/test/process/ReproduceProcessExample.php:0
    0.0755     368192   2. shmop_write() /home/jhbian/pider/test/process/ReproduceProcessExample.php:30

PHP Warning:  shmop_read(): count is out of range in /home/jhbian/pider/test/process/ReproduceProcessExample.php on line 49
PHP Stack trace:
PHP   1. {main}() /home/jhbian/pider/test/process/ReproduceProcessExample.php:0
PHP   2. shmop_read() /home/jhbian/pider/test/process/ReproduceProcessExample.php:49

Warning: shmop_read(): count is out of range in /home/jhbian/pider/test/process/ReproduceProcessExample.php on line 49

Call Stack:
    0.0002     366568   1. {main}() /home/jhbian/pider/test/process/ReproduceProcessExample.php:0
    0.1350    1551336   2. shmop_read() /home/jhbian/pider/test/process/ReproduceProcessExample.php:49

104785
/home/jhbian/pider/test/process/ReproduceProcessExample.php:60:
int(99)
16896

有人能指出铰链在哪里吗?

EN

回答 1

Stack Overflow用户

发布于 2019-06-28 14:54:41

当您已经创建了新的共享内存段,并且由于某种原因PHP没有关闭它时,就会发生这种情况。您需要使用"w“标志访问已经创建的段。

代码语言:javascript
复制
$shared_memory = @shmop_open($key, "c", 0644, 255);
if (false === $shared_memory) {
    $shared_memory = shmop_open($key, "w", 0644, 255);
}
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/46842033

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档