我有两个进程和一个共享内存区域,我的工作stream程就是这样。 进程A在共享内存中写入一些数据,然后等待并发送信号给其他进程B开始运行。 进程B应该从共享内存中读取一些数据,做一些东西写入结果,然后发送一个信号给进程A继续运行,这个进程B等待之后。
任何人都可以提供一个例子或地方,我可以find如何停止一个过程,我怎样才能开始再次运行的过程? 我正在使用Linux和C ++。
我已经有了信号量,但是我不喜欢的东西,就是一个进程停止从共享内存中读取所有的时间,直到它检测到它可以运行。 这就是为什么我只是在适当的时候发出信号
更新与解决scheme
Powershell打开系统控制面板而不是执行代码
将数据传递给Windows控制台控制处理程序
有没有办法确定一个Linux的PID是否暂停?
如何直接与硬件交互?
如何识别第三方应用程序使用的控件?
我select了stefan.ciobaca的答案作为最喜欢的,因为它是一个完整的解决scheme,它的作品,它有一个很好的解释。 但在所有其他的答案还有其他有趣的select。
Delphi 2K9在运行时禁用和启用组件。 奇怪的问题
C#Windows窗体:循环浏览dynamic创build的文本框,并检查是否已更改文本
下拉select控制 – Windows 8 Metro – XAML
改变基于Windows版本的控件的视觉风格
我如何将控件映射到它的设备?
这是一个如何完成的概念证明:
#include <stdio.h> #include <stdlib.h> #include <string.h> #include <signal.h> #include <sys/types.h> #include <sys/ipc.h> #include <sys/shm.h> #include <unistd.h> #include <assert.h> typedef void (*sighandler_t)(int); #define SHM_SIZE 8 /* size of shared memory: enough for two 32 bit integers */ volatile int cancontinue = 0; void halt(char *err) { perror(err); exit(1); } void handler(int signum) { assert(signum == SIGUSR1); cancontinue = 1; } int main(void) { key_t key; int id; int *data; pid_t otherpid; printf("Hi,I am the %s process and my pid is %dn",#ifdef PRODUCER_MODE "writer" #else "reader" #endif,getpid()); printf("Please give me the pid of the other process: "); scanf("%d",&otherpid); // get a pointer to the shared memory if ((key = ftok("test_concur.c",'R')) == -1) halt("ftok"); if ((id = shmget(key,SHM_SIZE,0644 | IPC_CREAT)) == -1) halt("shmget"); if ((data = shmat(id,(void *)0,0)) == (int *)(-1)) halt("shmat"); sighandler_t oldhandler = signal(SIGUSR1,handler); while (1) { #ifdef PRODUCER_MODE printf("Enter two integers: "); scanf("%d %d",data,data + 1); printf("Sending signal to consumer processn"); kill(otherpid,SIGUSR1); printf("Waiting for consumer to allow me to continuen"); while (!cancontinue); cancontinue = 0; if (*data + *(data + 1) == 0) { printf("Sum was 0,exiting...n"); break; } #else printf("Waiting for producer to signal me to do my workn"); while (!cancontinue); cancontinue = 0; printf("Received signaln"); printf("Pretending to do a long calculationn"); sleep(1); int sum = *data + *(data + 1); printf("The sum of the ints in the shared memory is %dn",sum); printf("Signaling producer I'm donen"); kill(otherpid,SIGUSR1); if (sum == 0) break; #endif } signal(SIGUSR1,oldhandler); /* detach from the segment: */ if (shmdt(data) == -1) { perror("shmdt"); exit(1); } // don't forget to remove the shared segment from the command line with // #sudo ipcs // ... and look for the key of the shared memory segment // #ipcrm -m <key> return 0; }
上面的程序实际上是两个程序,一个消费者和一个生产者,取决于你如何编译它。
您通过确保PRODUCER_MODE宏被定义来编译生产者:
#gcc -Wall -DPRODUCER_MODE -o生产者test_concur.c
消费者编译时没有定义PRODUCER_MODE宏:
#gcc -Wall -o consumer test_concur.c
用户和生产者共享一些全局内存(由数据指向的8个字节); 生产者的角色是从标准输入读取两个32位整数,并将其写入共享内存。 消费者从共享内存读取整数并计算其总和。
在将数据写入共享内存之后,生产者通过SIGUSR1向消费者发信号通知它可以开始计算。 计算完成后,消费者(通过SIGUSR1再次)发信号给生产者它可能会继续。
两个进程在总和为0时停止。
目前,每个程序开始输出其PID和从标准输入读取其他程序的PID。 这应该可能:D被更聪明的东西取代,具体取决于你在做什么。
另外,在实践中,“while(!cancontinue);”类似的循环应该被别的东西替代:D,就像信号量一样。 至少你应该在每个循环内做一个小小的睡眠。 另外,我认为你并不需要共享内存来解决这个问题,应该可以使用消息传递技术。
#./producer#./consumer
嗨,我是作家程序,我的pid是11357嗨,我是读者程序,我的pid是11358
请给我另一个过程的pid:11358请给我另一个过程的pid:11357
输入两个整数:2等待生产者指示我做我的工作
3
发送信号给用户进程接收到的信号
等待消费者让我继续假装做长时间的计算
有一段时间过去了
共享内存中的整数是5
信号生产者我完成了
输入两个整数:0等待生产者指示我做我的工作
发送信号给用户进程接收到的信号
等待消费者让我继续假装做长时间的计算
有一段时间过去了
共享内存中的整数是0
信号生产者我完成了
总和为0,退出...
我希望这有帮助。 (当你运行程序时,确保文件test_concur.c存在(它用来建立共享内存密钥(ftok函数调用)))
不完全是你所要求的,但你可以使用管道(命名或其他)来影响同步? 这将锁定负担放到已经知道如何操作的操作系统上。
只是一个想法。
对评论的回应:我想到的是使用管道而不是共享内存来获得更多的数据,并获得免费的同步。
例如:
过程A开始,建立一个双向管道, 并使用popen (3)分叉过程B.
紧随叉后:
A做了一些工作,并写入管道
B尝试读取管道,这将阻塞,直到进程A写入…
下一个:
试图读取管道,这将阻塞,直到数据可用…
B做了一些工作,并写入管道
转到第2步,直到达到结束条件。
这不是你要求的。 没有共享内存,没有信号,但它应该做的伎俩…
怎么样使用Unix域套接字而不是共享内存? 这样,每个进程都可以阻塞从套接字读取而另一个进行工作。
编辑:这是类似于dmckee的答案 ,但提供更多的控制阻塞和IPC。 然而, popen方法肯定更容易实现。
你真的需要停止进程(退出),并重新启动它,或者你只是希望它等到某个事件发生?
如果后者你应该阅读IPC和进程同步(例如信号量,互斥锁)。
如果是前者,请查看linux中init的源代码。
你在找什么叫做阻塞。 进程B应该阻塞来自进程A的调用,而进程A应该阻塞来自进程B的调用。如果进程被阻塞(等待来自其他进程的调用),它在后台闲置,并且只有在接收到时才被唤醒一个消息。
选择可能是你正在寻找的功能。
我建议使用信号来同步进程。
阅读标题,我认为SIGSTOP和SIGCONT可能是可能的,但这可能不是一个好主意; 你希望他们在正确的(安全的)地方停下来。 这就是信号灯的作用。
许多其他的IPC机制也可以达到类似的结果,但是信号量是跨进程的通信机制(你可以在一个进程中在不同线程之间使用互斥体)。
你可能也想看看增强的消息队列 ,这将使用共享内存,但隐藏所有的硬件。 它提供了阻塞和非阻塞功能(这听起来像你想阻止)。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 [email protected] 举报,一经查实,本站将立刻删除。