【Linux程序设计】之进程间的通信

这个系列的博客贴的都是我大二的时候学习Linux系统高级编程时的一些实验程序,都挺简单的。

实验题目:Linux环境下的进程间通信

实验目的:熟悉进程通信中信号概念及信号处理;掌握进程间的管道通信编程;了解进程间的内存共享编程。

实验内容:

一、信号

设计程序,满足如下要求:

1、编程程序:每隔1秒显示“running….”一次,显示8次后,程序结束。应用函数alarm,在程序开始运行5秒后发送信号SIGALRM,并实现:1)程序接收到SIGALRM信号就被终止;2)自定义信号处理函数,在程序接收到SIGALRM信号后,循环显示三次“handling SIGALRM”。

 1 #include<stdio.h>
 2 #include<unistd.h>
 3 #include<signal.h>
 4 #include<stdlib.h>
 5 int main()
 6 {
 7     alarm(5);
 8     int i;
 9     for(i=0;i<=7;i++)
10     {
11     printf("running…\n");
12     sleep(1);
13     }
14     return 0;
15 }
 1 #include<stdio.h>
 2 #include<unistd.h>
 3 #include<signal.h>
 4 #include<stdlib.h>
 5 void fun()
 6 {
 7     int i=0;
 8     for(i=0;i<=2;i++)
 9     {
10         printf("handling SIGALRM \n");
11     }
12 }
13 int main()
14 {
15     (void)signal(SIGALRM,fun);
16     alarm(5);
17     int i;
18     for(i=0;i<=7;i++)
19     {
20     printf("running…\n");
21     sleep(1);
22     }
23     return 0;
24 }

2、设计一个程序,要求用户进程创建一个子进程,子进程发送SIGSTOP将自身挂起,父进程向子进程发出SIGKILL信号,子进程收到此信号,结束子进程的运行。

 1 #include<stdio.h>
 2 #include<unistd.h>
 3 #include<stdlib.h>
 4 #include<signal.h>
 5 int main()
 6 {
 7     pid_t pid;
 8     pid=fork();
 9     int ret;
10     if(pid <0)
11     {
12         printf("Error Exit!\n");
13         exit(1);
14     }
15     else if(pid==0)
16     {
17         raise(SIGSTOP);
18         exit(0);
19     }
20     else
21     {
22         printf("子进程的进程号是:%d\n",pid);
23         if(waitpid(pid,NULL,WNOHANG)==0)
24         {
25             if(ret=kill(pid,SIGKILL)==0)
26             {
27                 ptintf("fun kill‘s return is %d,pid is%d\n",ret,pid);
28             }
29         }
30     }
31     return 0;
32 }

3、设计一个程序,要求程序运行后进入无限循环,要求主程序运行时,即使用户按下中断键(Ctrl+Z和Ctrl+\),也不能影响正在运行的程序,即让信号处于阻塞状态,当主体程序运行完毕后才进入自定义信号处理函数,当用户再次按下中断键(Ctrl+Z和Ctrl+\)后,结束程序运行。

 1 #include<stdio.h>
 2 #include<unistd.h>
 3 #include<signal.h>
 4 #include<sys/types.h>
 5 #include<stdlib.h>
 6 void fun_z()
 7 {
 8     printf("you press Ctrl+z\n");
 9     printf("Ctrl + z is useable now!\n");
10     signal(SIGTSTP,SIG_DFL);
11
12 }
13 void fun_d()
14 {
15     printf("you press ‘Ctrl+\‘ \n");
16     printf("Ctrl + d is useable now!\n");
17     signal(SIGQUIT,SIG_DFL);
18
19 }
20 int main()
21 {
22     int i;
23     sigset_t set,pendset;
24     struct sigaction action;
25     signal(SIGTSTP,fun_z);
26     signal(SIGQUIT,fun_d);
27     if(sigemptyset(&set)<0)
28         perror("init sign error!");
29     if(sigaddset(&set,SIGTSTP)<0)
30         perror("add ctrl+z error!\n");
31     if(sigaddset(&set,SIGQUIT)<0)
32             perror("ass ‘ctrl+\‘ error!\n");
33     while(1)
34     {
35         printf("Ctrl +z and ‘Ctrl +\‘ is zuse!\n");
36         sleep(2);
37     }
38
39     return 0;
40 }

二、管道

1、设计一个程序,要求创建一个管道,复制进程,父进程往管道中写入字符串“how are you!”,子进程从管道中读取并输入字符串“how are you!”。

 1 #include<stdio.h>
 2 #include<stdlib.h>
 3 #include<sys/types.h>
 4 #include<sys/wait.h>
 5 #include<unistd.h>
 6 #include<string.h>
 7 int  main()
 8 {
 9     pid_t result;
10     int n;
11     int pipe_fd[2];
12     char buf1[100],buf2[100];
13     memset(buf1,0,sizeof(buf1));
14         if(pipe(pipe_fd)<0)
15         {
16             printf("error!\n");
17             return -1;
18         }
19     result=fork();
20     if(result<0)
21     {
22         printf("error!\n");
23         exit(0);
24     }
25     else if(result==0)
26     {
27         close(pipe_fd[1]);
28         if((n =read(pipe_fd[0],buf1,100))>0)
29         {
30             printf("child read %d char,char is %s\n",n,buf1);
31             close(pipe_fd[0]);
32             exit(0);
33         }
34     }
35     else
36     {
37         close(pipe_fd[0]);
38         printf("please input pipe word \n");
39         fgets(buf2,sizeof(buf2),stdin);
40         if(write(pipe_fd[1],buf2,strlen(buf2))!=-1)
41             printf("parent write to child is: %s\n",buf2);
42         close(pipe_fd[1]);
43         waitpid(result,NULL,0);
44         exit(0);
45     }
46
47     return 0;
48 }

2、设计一个程序,要求用popen创建管道,实现“rpm -qa | grep nfs”的功能。

3、设计一个程序,要求创建一个管道PIPE,复制进程,父进程运行命令“ls –l”,把运行结果写入管道,子进程从管道中读取“ls -l”的结果,把读出的作为输入接着运行“grep .c”。

三、共享内存

1、设计一个程序,要求创建进程,父子进程通过匿名映射实现共享内存

 

时间: 2024-10-12 17:54:35

【Linux程序设计】之进程间的通信的相关文章

Linux/UNIX之进程间的通信(2)

进程间的通信(2) 有三种IPC我们称为XSI IPC,即消息队列.信号量以及共享存储器,它们之间有很多相似之处. 标识符和键 每个内核的IPC结构(消息队列.信号量或共享存储段)都用一个非负整数的标识符加以引用.例如,为了对一个消息队列发送或取消息,只需要知道其队列标识符.与文件描述符不同,IPC标识符不是小的整数.当一个IPC结构被创建,以后被删除时,与这种结果相关的标识符连续加1,知道达到一个整型数的最大值,然后又回到0. 标识符是IPC对象的内部名.为使多个合作进程能够在同一IPC对象上

linux 进程间的通信

现在linux使用的进程间通信方式:(1)管道(pipe)和有名管道(FIFO)(2)信号(signal)(3)消息队列(4)共享内存(5)信号量(6)套接字(socket) 为何进行进程间的通信:A.数据传输:一个进程需要将它的数据发送给另一个进程,发送的数据量在一个字节到几M字节之间B.共享数据:多个进程想要操作共享数据,一个进程对共享数据的修改,别的进程应该立刻看到.C.通知事件:一个进程需要向另一个或一组进程发送消息,通知它(它们)发生了某种事件(如进程终止时要通知父进程).D.资源共享

Linux进程间的通信

一.管道 管道是Linux支持的最初Unix IPC形式之一,具有以下特点: A. 管道是半双工的,数据只能向一个方向流动: B. 需要双工通信时,需要建立起两个管道: C. 只能用于父子进程或者兄弟进程之间(具有亲缘关系的进程): D. 单独构成一种独立的文件系统:管道对于管道两端的进程而言,就是一个文件,但它不是普通的文件,它不属于某种文件系统,而是自立门户,单独构成一种文件系统,并且只存在与内存中. 匿名管道的创建:该函数创建的管道的两端处于一个进程中间,在实际应用中没有太大意义;因此,一

Linux进程间的通信方法

linux进程间的通信方法总结如下 通过fork函数把打开文件的描述符传递给子进程 通过wait得到子进程的终结信息 通过加锁的方式,实现几个进行共享读写某个文件 进行间通过信号通信,SIGUSR1和SIGUSR2实现用户定义功能 利用pipe进行通信 FIFO文件进行通信 mmap,几个进程映射到同一内存区 SYS IPC 消息队列,信号量(很少用) UNIX Domain Socket,常用

Linux/UNIX进程间的通信(1)

进程间的通信(1) 进程间的通信IPC(InterProcessCommunication )主要有以下不同形式: 半双工管道和FIFO:全双工管道和命名全双工管道:消息队列,信号量和共享存储:套接字和STREAMS 管道 pipe函数 当从一个进程连接到另一个进程时,我们使用术语管道.我们通常是把一个进程的输出通过管道连接到另一个进程的输入. 管道是由调用pipe函数创建的: #include<unistd.h> int pipe(intpipefd[2]); 经由参数pipefd返回两个文

Linux进程间的通信方法简介

一.本地进程间的通信方式: 1.管道(pipe) 利用管道文件可以进行进程间数据的通信,通常是具有血缘关系的父子进程间的通信方式. 管道通信为半双工模式,父子进程可以通过调用内核中的read()和write()命令来向管道文件进行读写操作. 管道通信是基于硬盘内的文件,所以I/O速度较低. 2.消息队列 消息队列是一种类似链表的数据结构,存放于内存中,因此I/O速度较管道更快,通过ipcs -q命令可以查看当前系统中被创建的消息队列. 多个不同进程可以使用同一个消息队列进行通信,消息队列中的数据

Linux 线程与进程,以及通信

http://blog.chinaunix.net/uid-25324849-id-3110075.html 部分转自:http://blog.chinaunix.net/uid-20620288-id-3025213.html 1.首先要明确进程和线程的含义: 进程(Process)是具有一定独立功能的程序关于某个数据集合上的一次运行活动,是系统进行资源分配和调度的一个独立单位.与程序相比,程序只是一组指令的有序集合,它本身没有任何运行的含义,只是一个静态实体.进程是程序在某个数据集上的执行,

进程间的通信:管道

进程间的通信:管道 Linux中将命令联系到一起使用实际上就是把一个进程的输出通过管道传递给另一个进程的输入,这些都是shell封装好的,对标准输入和输出流进行了重新连接,使数据流从键盘输入经过两个程序最终输出到屏幕上.如下: cmd1|cmd2 进程管道 在两个程序之间传递数据最简单的方法就是使用popen()和pclose()了.原型如下: #include <stdio.h> FILE *popen(const char *command, const char *open_mode);

Nginx学习——Nginx进程间的通信

nginx进程间的通信 进程间消息传递 共享内存 共享内存还是Linux下提供的最主要的进程间通信方式,它通过mmap和shmget系统调用在内存中创建了一块连续的线性地址空间,而通过munmap或者shmdt系统调用可以释放这块内存.使用共享内存的优点是当多个进程使用同一块共享内存时,在不论什么一个进程改动了共享内存中的内容后,其它进程通过訪问这段共享内存都可以得到改动后的内容. Nginx定义了ngx_shm_t结构体.用于描写叙述一块共享内存, typedef struct{ //指向共享

swoole进程间如何通信

Swoole进程间通信的方式 管道pipe 管道用于进程之间的数据交互,Linux系统本身提供了pipe函数用于创建一个半双工通信管道.半双工的通信方式中数据只能单向流动(一端只读一端只写),只能在具有亲缘关系(父子进程)的进程之间使用. 管道是进程间通信IPC中最基础的方式,管道有两种类型分别是命名管道.匿名管道. 匿名管道:专门用于具有血缘关系的进程之间,完成数据传递.命名管道:可以用在任何两个进程之间,Swoole中的管道都是匿名管道. 在Swoole中利用eventfd和UnixSock