C语言实现父进程主动终止子进程的方法总结

 更新时间:2023年10月16日 09:17:10   作者:java 乐山  
一般的情况,子进程自己运行完后,执行exit 或者return 后,父进程wait.  waitpid收回子进程,但子进程是一个循环等待状态不主动退出,父进程可以采用文中介绍的几种方法,需要的朋友可以参考下

1.如子进程是循环状态

子进程循环等待键盘的输入,如父进程模拟键盘输入一个字符,子进程收到就跳出scanf()。同理,如是socket 的accept()等待,也可以发送一字符,让子进程跳出等待。

 
#include <string.h>
#include <stdio.h>
#include <fcntl.h>
#include <linux/input.h>
#include <linux/uinput.h>
#include <stdio.h>
#include <unistd.h>
#include <wait.h>
void mn_key(int fd,int kval)
{
	struct input_event event;
	event.type = EV_KEY;
	event.value = 1;
	event.code = kval;
	write(fd,&event,sizeof(event)) ;
	event.type = EV_SYN;
	event.code = SYN_REPORT;
	event.value = 0;
    write(fd, &event, sizeof(event));
	memset(&event, 0, sizeof(event));
	event.type = EV_KEY;
	event.code = kval;
	event.value = 0;
	write(fd, &event, sizeof(event));
	event.type = EV_SYN;
	event.code = SYN_REPORT;
	event.value = 0;
    write(fd, &event, sizeof(event));
}
int main()
{   int stat;
    pid_t pid=fork();
	if(pid==0){
		while(1){
		    char c[20];
	    	scanf("%s",c);
			if(!strcmp(c,"0")){       //接收到0字符,子进程退出
				puts("zjc over");
				return 0;
			}
		    printf("zjc:%s\n",c);
		}
	}
	sleep(10);  //10秒后,中止子进程的运行。   
    int	fd = open("/dev/input/event3",O_RDWR);  //每个机器的event(n)可能不同。
	if(fd<=0){
	    puts("keyboad error");        //dev/input/event3  权限chmod 777 要能读写
		return -1;
	}
	mn_key(fd,KEY_0);
	mn_key(fd,KEY_ENTER);
    mn_key(fd,KEY_ENTER);      //不清楚为什麽要两行
	wait(&stat);
	close(fd);
}

2.上面的方法不通用,可以说是特例,下面的方法采用kill()函数,可以说是通用方法,采用管道先把子进程号传到父进程,再用kill函数。此方法非常暴力,直接杀死子进程,不管它是否结束。

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#include <sys/socket.h>
#include <wait.h>
#include <signal.h>
#include <sys/prctl.h>
#include <sys/types.h>
int main(void){
//	int stat;
	int zf[2];
	pipe(zf);         //此句必须放在fork()语句前
	pid_t pid=fork();
	if(pid==0){
		pid_t pid1=getpid();
		printf("z:%d\n",pid1);
		write(zf[1],&pid1,4);
	     while(1){
			char c[10];
			scanf("%s",c);
			if(!strcmp(c,"~")){
				puts("zjc over");
				exit(0);
			}
			printf("%s\n",c);
		 }
	}
	sleep(3);       
	pid_t bz;
	read(zf[0],&bz,4);     //父进程取得子进程号
	printf("f:%d\n",bz);  
    kill(bz,1);            //关闭子进程
//	wait(&stat);     
	return 0;
}

3. 父进程用sigqueue() 发送终止信号,子进程signal() 收到父进程信号,改变循环标志位,退出循环,再退出子进程。此种方法文明不粗暴。此处父进程不能用raise函数,因为此函数只能向本进程发送信号。

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#include <sys/socket.h>
#include <wait.h>
#include <sys/types.h>
#include <signal.h>
int main(void){
	 union sigval si;
	 si.sival_int=0;
	int stat;
	pid_t zf[2];
	pipe(zf);
	pid_t pid=fork();
	if(pid==0){
		pid_t id=getpid();
		write(zf[1],&id,4);
		int t=1;
		void handle(int sig){
			printf("%d\n",sig);
			t=0;                
		}
		signal(20,&handle);    
		while(t){
			puts("zjc");
			sleep(1);
		}
		printf("%d\n",t);    //t=0
		exit(0);
	}
	int bz;
	read(zf[0],&bz,4);
	sleep(2);
    sigqueue(bz,20,si);
	wait(&stat);
	return 0;
}

sigqueue可以为非子进程的不关联进程发信号,只要知道对方的进程号就行了,可以用有名管道把进程号先传给对方进程。突然想到,可不可以用这个发信号的方法来执行进程间的互斥等操作。多进程主要用于多任务,比如需要同时运行两个以上执行动作的场景。

对于被安装信号的进程来讲,进程内代码执行与信号触发是异步的。信号好象是硬件的中断。条件产生了,操作系统就触发信号,执行信号的默认函数动作。执行完后,又继续执行进程的代码。

信号可以安装在一个进程内,再由本进程触发完成动作,如定时。

这个信号感觉非常有用,感觉这才是真正的多任务,进程间可以互不影响,一个进程完成某个动作后,触发信号通知另一个进程,(在触发信号之前,另一个进程可以干别的事情)。告诉它,我已完成,你可以怎么办。

以上就是C语言实现父进程主动终止子进程的方法总结的详细内容,更多关于C语言父进程终止子进程的资料请关注脚本之家其它相关文章!

相关文章

  • C语言中多维数组的内存分配和释放(malloc与free)的方法

    C语言中多维数组的内存分配和释放(malloc与free)的方法

    写代码的时候会碰到多维数组的内存分配和释放问题,在分配和释放过程中很容易出现错误。下面贴上一些示例代码,以供参考。
    2013-05-05
  • 基于OpenCV读取摄像头实现单个人脸验证MFC程序

    基于OpenCV读取摄像头实现单个人脸验证MFC程序

    这篇文章主要为大家详细介绍了基于OpenCV读取摄像头实现单个人脸验证MFC程序,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2019-08-08
  • C++超详细讲解析构函数

    C++超详细讲解析构函数

    既然在创建对象时有构造函数(给成员初始化),那么在销毁对象时应该还有一个清除成员变量数据的操作咯,析构函数与构造函数功能相反,析构函数不是完成对象的销毁,局部对象销毁工作是由编译器完成的。而对象在销毁时会自动调用析构函数,完成类的一些资源清理工作
    2022-06-06
  • 全局静态存储区、堆区和栈区深入剖析

    全局静态存储区、堆区和栈区深入剖析

    在C++中,内存可分为系统数据区,自由存储区,文本区,const数据区,全局静态区,堆区和栈区
    2012-11-11
  • C++中正则表达式的使用方法详解

    C++中正则表达式的使用方法详解

    几乎所有的编程语言都支持正则表达式。 C++从C++11开始直接支持正则表达式。除了编程语言之外,大多数文本处理程序都使用正则表达式。本文将探讨正则表达式的一般细节以及C++编程方面的细节,感兴趣的可以学习一下
    2022-05-05
  • QT应用启动失败排查方法小结

    QT应用启动失败排查方法小结

    启动QT应用经常会碰到应用启动失败,qt platform plugin无法启动,本文就来介绍一下QT应用启动失败排查方法小结,具有一定的参考价值,感兴趣的可以了解以下
    2023-09-09
  • C/C++中组合详解及其作用介绍

    C/C++中组合详解及其作用介绍

    这篇文章主要介绍了C/C++中组合的详解及其作用介绍,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2021-09-09
  • 简单谈谈C++ 头文件系列之(iosfwd)

    简单谈谈C++ 头文件系列之(iosfwd)

    本文给大家分享的是小编关于头文件系列的(iosfwd)的简单讲解,所谓iosfwd,其实就是“input output stream forward”,下面我们来详细看看
    2017-02-02
  • C++特殊类设计概念与示例讲解

    C++特殊类设计概念与示例讲解

    本文介绍C++中三种特殊类设计模式:单例模式、工厂模式和代理模式。通过详细讲解每种设计模式的实现原理和应用场景,帮助读者理解和掌握这些常用的面向对象设计模式,并提供示例代码和技巧,便于实际应用
    2023-04-04
  • 带你了解C++this指针的用法及其深究

    带你了解C++this指针的用法及其深究

    这篇文章主要介绍了C++中this指针的用法,对初学者而言是非常重要的概念,必须加以熟练掌握,需要的朋友可以参考下,希望能给你带来帮助
    2021-08-08

最新评论