一、实验目的及要求
目的:
掌握进程控制相关的系统调用的使用;掌握利用重定向进行进程间通信的方法。
要求:
(1)编写一个程序,完成输出重定向的功能:who > userlist。
(2)编写一个程序,完成输入重定向的功能:sort < data。
(3)编写一个程序,完成管道功能:who | grep bbc。
一、实验内容:
1、编写一个程序,完成输出重定向的功能:who>userlist
2、编写一个程序,完成输入重定向的功能:sort<data。
3、编写一个程序,完成管道功能:who|grepbbc
二、实验过程及结果记录
1. 输出重定向程序错误:
错误描述: 在编写输出重定向程序时,我忘记了在程序中打开要输出的文件,并将输出结果写入文件中。
修正方法: 在程序中添加打开文件的操作,并使用文件描述符进行输出重定向。
经验总结: 在编写输出重定向程序时,务必记得打开要输出的文件,并使用正确的文件描述符进行输出重定向,以确保输出结果被正确地写入到文件中。
2. 输入重定向程序错误:
错误描述: 在编写输入重定向程序时,我在程序中没有正确地处理输入重定向符号,导致无法正确地从指定文件中读取数据。
修正方法: 在程序中添加输入重定向符号的处理逻辑,并使用文件描述符进行输入重定向。
经验总结: 在编写输入重定向程序时,要注意正确地处理输入重定向符号,并使用正确的文件描述符进行输入重定向,以确保从指定文件中正确地读取数据。
3. 管道功能程序错误:
错误描述: 在编写管道功能程序时,我忘记了在程序中创建管道,并将管道的两端连接到相关的进程中。
修正方法: 在程序中添加创建管道的操作,并正确地将管道的两端连接到相关的进程中。
经验总结: 在编写管道功能程序时,务必记得创建管道,并正确地将管道的两端连接到相关的进程中,以确保进程间能够正确地进行通信。
三、实 验 小 结
思考题:1、实现输入输出重定向的基本原理是什么?
答:输入输出重定向的原理
核心机制:通过 dup2 系统调用复制文件描述符,改变标准输入(0)、标准输出(1)、标准错误(2)的指向
实现步骤:
打开目标文件(输入或输出)
使用 dup2 将文件描述符复制到标准输入 / 输出
执行命令时,系统自动从新的文件描述符读取或写入
应用场景:
输出重定向(>):将命令结果保存到文件
输入重定向(<):从文件读取命令输入
错误重定向(>>):将错误信息保存到文件
实验内容中实验完成项目中所有的源程序:
输出重定向程序:
#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <unistd.h>
int main() {
int fd;
char *command = "who";
char *output_file = "userlist";
// 打开文件用于写入(创建+截断)
fd = open(output_file, O_CREAT | O_WRONLY | O_TRUNC, 0644);
if (fd < 0) {
perror("打开输出文件失败");
exit(1);
}
// 重定向标准输出到文件
if (dup2(fd, STDOUT_FILENO) < 0) {
perror("重定向失败");
close(fd);
exit(1);
}
// 关闭文件描述符(已通过dup2复制)
close(fd);
// 执行who命令,输出将被重定向到文件
system(command);
return 0;
}
输入重定向程序:
#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <unistd.h>
int main() {
int fd;
char *command = "sort";
char *input_file = "data";
// 打开文件用于读取
fd = open(input_file, O_RDONLY);
if (fd < 0) {
perror("打开输入文件失败");
exit(1);
}
// 重定向标准输入到文件
if (dup2(fd, STDIN_FILENO) < 0) {
perror("重定向失败");
close(fd);
exit(1);
}
// 关闭文件描述符
close(fd);
// 执行sort命令,输入将从文件读取
system(command);
return 0;
}
实现管道程序:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/wait.h>
int main() {
int pipefd[2];
pid_t pid;
char buffer[1024];
// 创建管道
if (pipe(pipefd) == -1) {
perror("创建管道失败");
exit(1);
}
// 创建子进程
pid = fork();
if (pid == -1) {
perror("fork失败");
exit(1);
}
if (pid == 0) { // 子进程:执行who命令,输出到管道
close(pipefd[0]); // 关闭读端
dup2(pipefd[1], STDOUT_FILENO); // 重定向标准输出到管道写端
close(pipefd[1]); // 关闭写端(已复制)
// 执行who命令
execlp("who", "who", NULL);
perror("execlp who失败");
exit(1);
} else { // 父进程:从管道读取数据,用grep过滤
close(pipefd[1]); // 关闭写端
// 创建二级子进程执行grep
pid_t pid_grep = fork();
if (pid_grep == -1) {
perror("fork失败");
exit(1);
}
if (pid_grep == 0) { // 二级子进程:执行grep
dup2(pipefd[0], STDIN_FILENO); // 重定向标准输入到管道读端
close(pipefd[0]); // 关闭读端(已复制)
// 执行grep bbc命令
execlp("grep", "grep", "bbc", NULL);
perror("execlp grep失败");
exit(1);
} else { // 父进程:等待子进程结束
close(pipefd[0]); // 关闭读端
waitpid(pid, NULL, 0);
waitpid(pid_grep, NULL, 0);
}
}
return 0;
}
实验心得:
本次实验聚焦进程及进程间通信知识,经编程实践深入研习。先是实现输出重定向,把程序标准输出流转至指定文件,达成结果写入;再掌握输入重定向,将标准输入流指向指定文件,实现数据读取;最后学习并实现管道功能,借创建管道连接多进程的标准输入输出,完成进程间通信与数据传输。
实验里遭遇若干问题,像忘开输出文件、处理输入重定向符号有误、漏建管道等。及时排查修正后,对进程及进程间通信的原理与实现理解更为深刻。持续实践总结中,Linux 系统编程熟练度提升,积累了实用经验与技能。
总体而言,本次实验助力深化对进程及进程间通信的认知,增强 Linux 环境下程序开发与调试能力。后续通过不断实践探索,编程水平将进一步提升,未来学习工作中也能更从容地运用所学 。
Linux编程 实验三 进程及进程间通信
2025/6/20 2:44:41
来源:https://blog.csdn.net/a16675900046/article/details/148733644
浏览:
次
关键词:Linux编程 实验三 进程及进程间通信
版权声明:
本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。
我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com