之前遇到过一道题就是要求写一个程序,么父进程计算一个整数的阶乘,子进程计算从1到N 的和,然后把这两个值加起来。
其实这道题的做法有许多,这无非就是牵扯到两个进程间通信的问题,我们知道Linux进程间的通信有好多种,信号量、管道、共享内存、有名管道等等。
下面看一个共享虚存区的做法:
函数mmap()在进程的用户空间内创建一个新的虚存区。原型如下所示:
#include
#include
void *mmap(void *addr,size_t length,int prot,int flags,int fd,off_t offsize);
返回值: 成功则返回映射区起始地址, 失败则返回MAP_FAILED(-1).
参数:
addr: 指定映射的起始地址, 通常设为NULL, 由系统指定.
length: 将文件的多大长度映射到内存.
prot: 映射区的保护方式, 可以是:
PROT_EXEC: 映射区可被执行.
PROT_READ: 映射区可被读取.
PROT_WRITE: 映射区可被写入.
PROT_NONE: 映射区不能存取.
flags: 映射区的特性, 可以是:
MAP_SHARED: 对映射区域的写入数据会复制回文件, 且允许其他映射该文件的进程共享.
MAP_PRIVATE: 对映射区域的写入操作会产生一个映射的复制(copy-on-write), 对此区域所做的修改不会写回原文件.
此外还有其他几个flags不很常用, 具体查看linux C函数说明.
fd: 由open返回的文件描述符, 代表要映射的文件.
offset: 以文件开始处的偏移量, 必须是分页大小的整数倍, 通常为0, 表示从文件头开始映射.
下面我们就来看上面的求值问题的函数怎么写:
- #include<stdio.h>
- #include<unistd.h>
- #include<sys/types.h>
- #include<sys/mman.h>
- #define N 4
- int sum=0,fd;
- int i,s=1;
- int main()
- {
- int *result_ptr=mmap(0,4,PROT_READ|PROT_WRITE,MAP_SHARED|MAP_ANONYMOUS,0,0);
- int pid=fork();
- if(pid==0)
- {
- for(i=1;i<=N;i++)
- sum+=i;
- *result_ptr=sum;
- }else{
-
- wait(0);
- for(i=1;i<=N;i++)
- s*=i;
- printf("S+sum=%d\n",s+*result_ptr);
- printf("sum=%d,s=%d\n",*result_ptr,s);
- }
- }
运行结果如下所示:
由此我们可以看出这种办法是最简单的。当然我们还可以通过其他的一些方法进行参数传递等。
阅读(359) | 评论(0) | 转发(0) |