在C中使用pthread调用php函数

在C中使用pthread调用php函数,php,c,multithreading,thread-safety,pthreads,Php,C,Multithreading,Thread Safety,Pthreads,我需要多线程处理一个php函数,但是当我调用一个php函数时,我得到了一个错误“Safari无法打开页面” Safari无法打开页面”‎localhost/home.php”,因为服务器意外断开了连接。这有时在服务器繁忙时发生。请等待几分钟,然后重试。 我的php文件中有这行代码 <?php echo "Hello World","<br>"; open_thread("hello"); function hello() { echo "Hello World";

我需要多线程处理一个php函数,但是当我调用一个php函数时,我得到了一个错误“Safari无法打开页面”
Safari无法打开页面”‎localhost/home.php”,因为服务器意外断开了连接。这有时在服务器繁忙时发生。请等待几分钟,然后重试。

我的php文件中有这行代码

<?php
echo "Hello World","<br>";
open_thread("hello");

function hello() {
     echo "Hello World";
}
问题

这是线程安全问题吗?如何修复它?

PHP可以构建为支持多线程SAPI的-ZTS模式-但是,重要的是要认识到使用的内存模型是不共享的

在无共享模型中,每个线程都有一个不同的解释器(编译器、执行器、所有模块全局变量、所有用户代码,全部)

这意味着各种各样的事情:

  • 线程B无法执行为线程A编译的代码。线程B必须从线程A复制代码,执行类似于pass_two的操作,然后执行代码的副本
  • 从引用对象、资源或哈希表的线程A复制的代码可能(将)在没有适当准备和/或适当的对象处理程序的情况下中断
简单地启动一个线程并尝试调用Zend注定会失败,因为它忽略了PHP的无共享特性

新线程的流程需要类似于:

void routine(void *thing) {
    ts_resource(0);

    php_request_startup();

    /* do stuff */

    php_request_shutdown();

    ts_free_thread();
}
  • ts\u resource
    :这将在新线程中初始化TSRM,进而初始化一些Zend
  • php\u request\u startup
    :初始化其余的一切,以及运行所有模块的
    RINIT
  • php\u request\u shutdown
    :此操作运行
    rshutton
    ,通常会进行清理
  • ts\u free\u thread
    :可选的free,否则将发生在进程关闭时(当TSRM最终关闭时)
事实上,如果示例流试图调用由另一个线程编译的用户代码,它也会失败:在请求启动之后,在调用用户代码之前,您需要先将代码复制到当前上下文中


在pthreads扩展源代码中可以找到关于这些在现实世界中如何工作的详细信息。

我建议您先删除任何浏览器影响,现在使用CLI SAPI。还不清楚这与C代码的关系。请注意,PHP的“pthreads”与C的pthreads(也称为POXIX线程)有所不同。PHP的“pthreads”是使用POXIX的库在C的pthreads中编写的,这就是我试图实现的。感谢您的建议。PHP中的线程。。。那是错误的。我并不反对线程,但对于像PHP这样的语言,它们是禁止使用的,因为:a)PHP中不需要线程。如果您需要线程,那么您可能需要的不仅仅是PHP。B) 如果你给很多PHP开发人员线程,他们会产生可怕的代码。保护世界不受糟糕代码的影响,保护糟糕的开发人员不伤害他们自己的理智。C) 我更喜欢在围棋中穿行(但那只是我)谢谢乔,非常感谢你的回答!。我得到了这个警告和错误。我正在使用clang编译器,是否应该安装gcc?-----------/Users/username/terminal/src/php/ext/pthread/php_pthread.c:30:5:警告:函数“php_request_shutdown”的隐式声明在C99[-Wimplicit函数声明]php_request_shutdown()中无效/Users/username/terminal/src/php/ext/pthread/php_pthread.c:32:20:错误:函数调用的参数太多,应为0,具有1个ts_free_线程(0);是代码中的错误。。。代码是示例流,尚未准备好编译;)
void routine(void *thing) {
    ts_resource(0);

    php_request_startup();

    /* do stuff */

    php_request_shutdown();

    ts_free_thread();
}