进程与输入输出重定向
shell是如何运行程序的?
根据用户输入的字符串进行解析后,传给execvp系统函数,启动一个新的进程。比如execvp("ls",arglist)。不过exec(execvp是一组基于execve系统调用函数中的一个,他们统称为exec)系统调用从当前进程中把当前程序的机器指令清除,然后在空的进程中载入调用时指定的代码,最后运行这个新的程序。exec调整进程的内存分配使之适应新的程序对内存的要求。相同的进程,不同的内容。(但值得注意的是,子进程继承了父进程的一些资源,比如打开的文件描述符等,子进程同样可以进行使用。)
显然如果这样做,虽然启动了想执行的进程,当由于是在shell进程空间内执行的,清除了shell的内容,导致shell进程消亡了,如果想执行另一个命令,有需要启动新的shell,这显然达不到我们的要求 。解决方案就是,产生一个不影响shell进程的进程。可以调用系统函数fork(),该函数分配一个新的空间完全复制一个和调用它的进程完全一样的进程,但是新的进程只能从fork()方法之后开始运行。然后再该新进程中调用exec添加要执行的进程。当一个进程调用fork后,就有两个二进制代码完全相同的进程,而且他们都运行到相同的地方。可以通过控制fork()函数的返回值,使得两个进程开始它们自己的旅程。
代码如下:
main(){
int ret_from_fork,mypid;
mypid = getPid();
printf("before:my pid is d%\n",mypid);
ret_from_fork = fork();//该方法返回生成的子进程的进程id号。用于复制出一个进程后,他们都运行到同样的地方,所以父进程中的ret_from_fork的值是id值,而不时初值0,而子进程的ret_from_fork却没有获得值,还是0.通过这样就可以区别两个进程改变两个进程的走向。
switch(ret_from_fork){
case -1:
perror(" fork failed");
exit(1);
//以下就是子进程要执行的代码,他调用exec载入用户输入的命令指定的程序,清除进程空间执行用户指定的程序。
case 0:
execvp(arglist[0],arglist);//arglist[0]中指定用户想执行的命令名。
perror("execvp failed");
exit(1);
default:
while(wait(&exitstatus)!=ret_from_fork);
//shell程序,等待子进程运行结束后,再接受用户输入
}
}
通过以上方法就可以起到一个新的指定进程,而不会影响现在的进程。
输入输出重定向问题:
所有的Unix I/O 重定向都基于标准数据流的原理。
首先讨论重定向到文件:(通常运行的命令都是从标准输入流(键盘)获得程序输入,将执行的结果通过标准输出流打印到显示器上)
三个标准流:标准输入流,标准输出流,标准错误输出流。这三个流的每一种都是一个特别的文件描述符,分别对应:
0:stdin
1:stdout
2:stderr
Unix假设文件描述符0,1,2都已经打开,可以分别进行读,写操作了。大多数程序并不接收输出文件名,他们总是将结果写到文件描述符1,并将错误消息写到文件描述符2.所以要想将进程的输出写到文件或另一个进程的输入去,就必须重定向相应的文件描述符。可以将文件描述符1指向你想输出的文件,这样就达到了重定向的目的。虽然程序仍然向标准输出写,当却不知道输出的东西已不是留到标准输出了,而是留到了重定向的文件中去了。现在就要考虑如何实现将文件描述符与重定向文件关联起来。在此之前,先让我们了解"最低可用文件描述符"原则:当打开文件时,为此文件安排的描述符总是此数组中最低可用位置的索引。进程并不是从文件读取数据,而是从文件描述符读数据。如果将文件描述符0定位到一个文件,那么此文件就成为标准输入的源。
有二种方法实现重定位:
1,close then open
调用close(0)将标准输入的连接挂断。然后使用open打开一个想连接到的文件。当前的最低可用文件描述符是0,因此所打开的文件将被连接到标准输入上去。
2,open close dup close
该方法采用的原理类似,从楼上的电话复制一个连接到楼下,然后就可以在不断线的情况下将楼上的连接切断。
fd=open(file),获得描述符fd不是0,因为0已经被打开了。
close(0),将文件描述符0关闭。0现在已经空闲了。
dup(fd),将文件描述符fd做了一个复制。此次复制使用最低可用文件描述符号,因此获得的文件描述符是0.这样就将磁盘文件与文件描述符0连接在一起了。
close(fd),关闭文件的原始连接。只留下文件描述符0的连接。
要实现进程之间的I/O重定向,道理差不多,但是要使用管道。将管道的两端与输入输出挂接即可。
当进程创建了一个管道之后,该进程就有了连向管道两端的连接。当这个进程调用fork()的时候,他的子进程也得到了这连个连向管道的连接。父进程和子进程都可以将数据写到管道的写数据端口,并从读数据端口读出。两个进程都可以读写管道,但一个写,一个读,效率是最高的。
分享到:
相关推荐
Unix/Linux操作系统简介 GNU编译工具GCC GNU C 内存管理 文件I/O 进程管理 信号 进程间通信 多线程 网络通信
Linux作为UNIX的类UNIX系统,其网络编程原理和API在很大程度上与UNIX保持一致,因而这本书的内容对Linux开发者同样具有较高的参考价值。 内容提到了UNIX网络编程常用的两种API:套接口(sockets)和XTI(X/Open传输...
《UNIX环境高级编程》与《UNIX网络编程卷1:协议》是两本深入解析UNIX系统编程的经典著作。在深入理解这些书籍的知识点之前,我们先要了解UNIX系统的基础概念。 UNIX是一个多用户、多任务的操作系统,其设计哲学...
《Unix编程艺术》、《Unix环境高级编程(第二版)》和《Unix网络编程(第二版)》是三本在IT领域中具有深远影响力的经典著作,涵盖了Unix操作系统的核心概念、系统调用、进程管理、文件操作、网络通信等多个重要主题...
《Unix网络编程》是一套备受推崇的计算机网络编程经典著作,分为两卷,全面而深入地探讨了在Unix操作系统环境下进行网络应用开发的各种技术和实践。这两卷书籍是无数程序员和系统管理员学习网络编程的重要参考资料。...
从基础的套接口API,到进程间通信,再到高级套接字编程,作者以浅入深出的方式,将复杂的技术问题娓娓道来,使读者能够由表及里,逐渐掌握Unix网络编程的核心技术和方法。 在卷1中,W. Richard Stevens将套接字API...
《Unix网络编程》则专注于网络编程,包含以下核心内容: 1. 网络基础知识:TCP/IP协议族、OSI模型、端口与套接字概念的介绍。 2. 套接字API:讲解socket()、bind()、listen()、accept()、connect()、send()、recv...
《Linux/UNIX系统编程手册》是一本权威的指南,涵盖了操作系统的核心编程接口,为开发者提供了深入理解操作系统底层机制的窗口。源码分析是学习这些概念的最直接方式,因为它们揭示了内核如何与应用程序交互。以下是...
这本书详细介绍了socket接口,它是UNIX和其他类UNIX系统中实现网络通信的核心机制。socket接口为应用程序提供了一种标准化的方法来创建、连接和通信,无论是在局域网还是广域网上。 本书的知识点涵盖了以下几个方面...
《Unix网络编程》是一本详尽介绍Unix环境下网络编程技术的经典书籍,书中包含了大量实用的代码示例,帮助读者深入理解网络编程的核心原理与实践技巧。本文将重点分析书中两个代表性案例:简单的时间获取客户端与...
《UNIX网络编程》是计算机科学领域的一本经典著作,由W. Richard Stevens撰写,分为卷一和卷二,深入探讨了UNIX系统上的网络编程技术。这本书对于理解和掌握网络编程的基本概念、API以及实际应用有着极大的帮助。源...
根据提供的标题“Unix编程艺术中文版(非加密,带目录)”及描述“Unix编程艺术中文版”,可以推测这是一本介绍Unix系统编程原理、技巧和最佳实践的书籍。本书可能涵盖Unix系统的背景知识、核心概念、编程工具和技术...
### UNIX网络编程卷2:进程间通信核心知识点详解 #### 一、进程间通信(IPC)概述 在《UNIX网络编程卷2》中,作者深入探讨了进程间通信(Interprocess Communication, IPC)这一主题。进程间通信是操作系统中一个...
在这部分,读者将了解到如何利用Unix系统提供的网络编程接口来实现网络应用,如TCP/IP协议栈的工作原理、套接字的创建与操作、数据的发送与接收、多路复用I/O(如select和poll)、异步I/O等核心概念。同时,书中还...
《Linux-UNIX系统编程手册(上册)》是由Linux编程专家Michael Kerrisk撰写的一部权威指南,详细介绍了...通过深入学习和实践,你将能够熟练掌握Linux和UNIX系统编程的核心技能,编写出高效、稳定和安全的系统级程序。
总之,《Linux UNIX系统编程手册(下册)》是开发者深入理解Linux和UNIX内核工作原理,提升系统级编程技能的必备书籍。通过阅读和实践书中的示例,开发者可以更好地驾驭这两个强大的开源操作系统,从而开发出高效、...
《unp unix网络编程》是关于Unix系统下网络编程的经典之作,主要涵盖了网络通信的各种基础知识、原理和技术。这本书深入解析了TCP/IP协议栈的工作机制,提供了丰富的实例代码,旨在帮助开发者理解和实现网络应用。...
总的来说,《Unix高级编程》是一部全面且深入的教程,它可以帮助开发者提升对Unix/Linux系统的工作原理和编程实践的理解。通过阅读电子书并实践源码,读者可以逐步掌握Unix编程的核心技术,成为一名精通系统级编程的...
《Steven编写的UNIX网络编程》是一本深受程序员喜爱的经典之作,涵盖了UNIX系统中的网络编程核心内容,分为两卷:第一卷“套接字联网API”和第二卷“进程间通信”。作者通过深入浅出的方式,详细阐述了网络编程的...
书中的核心是"The Sockets Networking API",即套接字网络编程接口,这是Unix和类Unix系统中最广泛使用的网络通信机制。下面将详细阐述该主题的相关知识点。 一、套接字(Sockets)基础 套接字是网络编程中的基本...