PHP IPC函数,shm,shmop,message——共享内存函数,消息队列,与c/c++通讯

--enable-sysvsem.  信号量,个人感觉最好是无锁无信号设计速度更快

--enable-sysvshm.  shm*函数,将php变量放入共享内存,单一id可以插入多个php变量,自动序列化,用于php之间通讯

--enable-sysvmsg. 消息队列函数,无需手动控制内存大小,php之间通讯,(应该可以与c通讯,但是应该没有现成的c端代码)

 

以上,默认是开启的。

--enable-shmop shmop共享内存操作函数,可以与c/c++通讯

 

测试了消息队列(cli模式下),感觉非常适合php之间通讯,所以不研究shm了

[php]  view plain copy
  1. <?php  
  2. /* 
  3.  * class msg 
  4.  * Use for communication between php and php; 
  5.  * Create at: 12:08 2012/10/31 
  6.  * Author: leixun([email protected]) 
  7.  * version 1 - 14:01 2012/10/31 
  8.  */  
  9.   
  10. class msg{  
  11.     private $id;  
  12.     private $msg_id;  
  13.     private $_serialize = true;  
  14.   
  15.     /** 
  16.      * @param $_id ID 
  17.      */  
  18.     public function msg($_id$_serialize = true){  
  19.         $this->id = $_id;  
  20.         $this->msg_id = msg_get_queue ( $_id );  
  21.         $this->_serialize = $_serialize;  
  22.         if ($this->msg_id === false) {  
  23.             die(basename(__FILE__).'->'.__LINE__.': Unable to create message quee');  
  24.         }  
  25.     }  
  26.   
  27.     /** 
  28.      * @data data to send 
  29.      * @type message type 
  30.      */  
  31.     public function send( $data$type = 1, $blocking = false )  
  32.     {  
  33.         if (!msg_send ($this->msg_id, $type$data$this->_serialize, $blocking$msg_err))  
  34.         {  
  35.             return "Msg not sent because $msg_err\n";  
  36.         }  
  37.         return true;  
  38.     }  
  39.   
  40.     /** 
  41.      * @param $type message type 
  42.      * @param $maxsize The maximum size of message to be accepted, 
  43.      */  
  44.     public function receive($type = 1 , $maxsize = 1024 )  
  45.     {  
  46.         $rs = msg_receive ( $this->msg_id , $type ,  $type , $maxsize , $message , $this->_serialize, MSG_IPC_NOWAIT , $errorcode);  
  47.         if($rs)  
  48.             return $message;  
  49.         else  
  50.             return false;  
  51.     }  
  52.   
  53.     public function remove()  
  54.     {  
  55.         msg_remove_queue($this->msg_id);  
  56.     }     
  57. }  


 

[php]  view plain copy
  1. <?php  
  2. //写消息的进程  
  3. define('base_path' , dirname(__FILE__));  
  4. include(base_path.'/msg.php');  
  5.   
  6. $arr = array(999999999,999999999,999,999);  
  7. $block_size = strlen(serialize($arr));  
  8.   
  9. $count = 1000;  
  10.   
  11. $msg = new msg(1);  
  12.   
  13.   
  14. while(1){  
  15.     $arr = array(rand(1,999999999),rand(1,999999999),999,999);  
  16.     $msg->send($arr);  
  17.     sleep(rand(3,5));  
  18. }  
  19. echo 'Done';  


 

[php]  view plain copy
  1. <?php  
  2. //读消息的进程  
  3. define('base_path' , dirname(__FILE__));  
  4. include(base_path.'/msg.php');  
  5.   
  6. $arr = array(999999999,999999999,999,999);  
  7. $block_size = strlen(serialize($arr));  
  8.   
  9. $count = 1000;  
  10.   
  11. $msg = new msg(1);  
  12.   
  13.   
  14. while(1){  
  15.   
  16.     var_dump($msg->receive());  
  17.     sleep(4);  
  18. }  


我查阅资料,发现c也有消息队列函数,令我很兴奋,找了一个c的列子,c本身消息队列收发成功了。然后我尝试php和c对发,因为c发送的的是c的结构体struct,所以我寻求php生成c结构体struct的办法,我用了pack,搜索了pack,或者php struct,出来的文章都是同一篇,完全不正确的,经过记录c发送的数据,然后将我用php pack的数据做对比,发现数据是一模一样的,但是,发送给c,c无法解析。还好我有点儿php扩展基础,找到php的消息函数,一看:我失望了,php的消息函数发送的struct是固定的,一个int和一个char[1],经过一番测试之后,能将一个数字和一个字符串发送给c了

PHP代码:

[php]  view plain copy
  1. $id =  msg_get_queue ( 1 );  
  2.     if (!msg_send ($id, 317, "sdsadsdsds", false, true, $msg_err))  
  3.     {  
  4.         return "Msg not sent because $msg_err\n";  
  5.     }  


C代码:

[cpp]  view plain copy
  1. #include <stdio.h>  
  2. #include <stdlib.h>  
  3. #include <fcntl.h>  
  4. #include <string.h>  
  5. #include <unistd.h>  
  6. #include <sys/types.h>  
  7. #include <sys/ipc.h>  
  8. #include <sys/msg.h>  
  9. #define MAX_TEXT 512  
  10. #define BUFSIZE BUFSIZ  
  11.   
  12. struct msg_st {  
  13.     long mtype;  
  14.     char mtext[1];  
  15. };  
  16.   
  17. void logst(struct msg_st some_data);  
  18.   
  19. int main(int argc,char **argv)  
  20. {  
  21.         while(1){  
  22.               
  23.             int msgid1;  
  24.             struct msg_st some_data1;  
  25.             int msg_to_recevie = 0;  
  26.             if((msgid1= msgget((key_t)1,0666|IPC_CREAT)) == -1)  
  27.             {  
  28.                 perror("msgget");  
  29.                 exit(EXIT_FAILURE);  
  30.             }         
  31.             if(msgrcv(msgid1,(void *) &some_data1, BUFSIZ, msg_to_recevie , 0) == -1)  
  32.             {  
  33.                 perror("msgrcv");  
  34.                 exit(EXIT_FAILURE);  
  35.             }  
  36.             printf("recevier mssage : %s, type= %d;\n", some_data1.mtext, some_data1.mtype);  
  37.             //printf("%s, %d\n", msg_text, strlen(msg_text));  
  38.               
  39.             if(msgctl(msgid1,IPC_RMID,0) == -1)  
  40.             {  
  41.                 fprintf(stderr,"msgctl(IPC_RMID) failed \n");  
  42.                 exit(EXIT_FAILURE);  
  43.             }  
  44.             //break;  
  45.             sleep(1);  
  46.         }     
  47.       
  48. }  


 

如果反之,c应该也能发送一个整型和一个字符串给php,要想实现发送自定义的数据,那么就只能自己写扩展了!



你可能感兴趣的:(PHP,ipc,通讯)