`
tomhibolu
  • 浏览: 1430783 次
文章分类
社区版块
存档分类
最新评论

*exec,source和fork的区别*

 
阅读更多
exec和source都属于bash内部命令(builtins commands)在bash下输入man exec或man source可以查看所有的内部命令信息。

bash shell的命令分为两类:外部命令和内部命令外部命令通过系统调用或独立的程序实现的,如sed、awk等等。内部命令由特殊的文件格式(.def)所实现,如cd、history、exec等等。

在说明exec和source的区别之前,先说明一下fork的概念。

fork是linux的系统调用,用来创建子进程(child process)。子进程是父进程(parent process)的一个副本,从父进程那里获得一定的资源分配以及继承父进程的环境。子进程与父进程唯一不同的地方在于pid(process id)。

环境变量(传给子进程的变量,遗传性是本地变量和环境变量的根本区别)只能单向从父进程传给子进程。不管子进程的环境变量如何变化,都不会影响父进程的环境变量。

shell script:

有两种方法执行shell scripts,一种是新产生一个shell,然后执行相应的shell scripts;一种是在当前shell下执行,不再启用其他shell。
新产生一个shell然后再执行scripts的方法是在scripts文件开头加入以下语句
#!/bin/sh

一般的script文件(.sh)即是这种用法。这种方法先启用新的sub-shell(新的子进程),然后在其下执行命令。
另外一种方法就是上面说过的source命令,不再产生新的shell,而在当前shell下执行一切命令。

source:

source命令即点(.)命令

在bash下输入man source,找到source命令解释处,可以看到解释"Read and execute commands from filename in the current shell environment and ..."。从中可以知道,source命令是在当前进程中执行参数文件中的各个命令,而不是另起子进程(或sub-shell)。source filename or .filename 执行filename中的命令。

exec:

在bash下输入man exec,找到exec命令解释处,可以看到有"No new process is created."这样的解释,这就是说exec命令不产生新的子进程。那么exec与source的区别是什么呢?

exec命令在执行时会把当前的shell process关闭,然后换到后面的命令继续执行。

======================================================================================================================

下面我们写个脚本来测试一下,这样你就会很容易的读懂我上面所说的东西~

1.sh

#!/bin/bash
A=B
echo "PID for 1.sh before exec/source/fork:$$"
export A
echo "1.sh: \$A is $A"
case $1 in
exec)
echo "using exec..."
exec ./2.sh ;;
source)
echo "using source..."
. ./2.sh ;;
*)
echo "using fork by default..."
./2.sh ;;
esac
echo "PID for 1.sh after exec/source/fork:$$"
echo "1.sh: \$A is $A"

2.sh

#!/bin/bash
echo "PID for 2.sh: $$"
echo "2.sh get \$A=$A from 1.sh"
A=C
export A
echo "2.sh: \$A is $A"

=================》》》》》》》》》》》

测试结果:

[root@node2 ~]$ ./1.sh fork
PID for 1.sh before exec/source/fork:10175
1.sh: $A is B
using fork by default...
PID for 2.sh: 10176
2.sh get $A=B from 1.sh
2.sh: $A is C
PID for 1.sh after exec/source/fork:10175
1.sh: $A is B

=============================================
[root@node2 ~]$ ./1.sh source
PID for 1.sh before exec/source/fork:10185
1.sh: $A is B
using source...
PID for 2.sh: 10185
2.sh get $A=B from 1.sh
2.sh: $A is C
PID for 1.sh after exec/source/fork:10185
1.sh: $A is C

=============================================
[root@node2 ~]$ ./1.sh exec
PID for 1.sh before exec/source/fork:10194
1.sh: $A is B
using exec...
PID for 2.sh: 10194
2.sh get $A=B from 1.sh
2.sh: $A is C
[cpsuser@cps-svr-153 zy]$

=============================================

从以上结果可以看出:

1.执行source和exec的过程中没有产生新的进程,而fork是默认的运行方式,在运行的过程中会产生新的进程,也就是子进程

2.source和exec的区别在于exec执行完毕后没有输出进程,也就是说运行完毕2.sh后直接退出了,没有返回1.sh

3.fork和source的最后一句输出分别为:1.sh: $A is B (fork,说明它运行的环境不一样,要不然输出的应该是C)

1.sh: $A is C(source,说明从始至终都是在一个shell中执行)

小节:

source 指定脚本中的命令在同一个shell中运行(默认shell中的命令都是创建sub-shell,然后执行。执行完后,返回父shell)
fork 就是创建sub-shell运行脚本中的命令,和默认运行方式相同。
exec 和source相似,区别就是,运行完毕命令后退出,不会返回父shell
分享到:
评论

相关推荐

    高级Bash脚本编程指南

    - **进程控制**:fork, exec, wait等用于创建和管理子进程。 - **函数指针**:通过eval实现函数的动态调用。 通过学习并实践这些知识点,你将能够编写出高效、易读的Bash脚本,解决日常的系统管理问题,实现自动...

    我的APUE2读书笔记

    进程可以由其他进程通过`fork`和`exec`函数创建。 **2. 命令行参数和环境变量** 当进程启动时,可以通过命令行传递参数,也可以设置环境变量。 **3. Unix中C程序的存储空间基本布局** 包括文本段、数据段、堆栈等...

    UsefulSourceCodes_ForUtilities_source_c_code_utiltities_useful_源

    6. **系统调用**:如`fork()`, `exec()`, `wait()`等,用于创建子进程、执行新程序和等待进程结束,常用于编写shell脚本或者系统级别的工具。 7. **网络编程**:如果源代码涉及到网络工具,可能用到了`socket()`, `...

    详解Shell脚本中调用另一个Shell脚本的三种方式

    本文将详细讲解在Shell脚本中调用其他Shell脚本的三种常见方法:`fork`、`exec`以及`source`,并提供实例以帮助理解它们的工作原理和应用场景。 1. **fork** `fork`是最常见的调用方式,它会在当前Shell环境中创建...

    linux_unix_shell

    2. **进程控制**:使用fork、exec和wait等函数创建和管理子进程,实现复杂的进程间通信。 3. **错误处理**:通过set -e选项,可以设定脚本在遇到错误时立即退出,提高脚本的健壮性。 4. **脚本调试**:使用set -x...

    apue.2e source code

    1. **系统调用**:了解如何使用`fork()`, `exec()`, `wait()`, `pipe()`, `socket()`等系统调用来创建子进程、执行新程序、进程间通信以及网络通信。 2. **文件I/O**:包括基本的文件操作,如`open()`, `close()`, ...

    最新版本linux libc库实现源码

    5. **进程管理**:包括`fork`, `exec`, `wait`等函数,它们用于创建、控制和通信进程。源码会揭示如何在用户空间和内核空间之间切换。 6. **网络编程**:`socket`, `bind`, `connect`, `accept`等网络函数,这些是...

    操作系统实验指导书

    - **硬链接与软链接**:理解硬链接和软链接的区别及应用场景 **知识点3:文件系统管理** - **文件系统检查** (`fsck`):使用 `fsck` 检查文件系统的一致性 - **磁盘空间管理** (`df`, `du`):使用 `df` 查看磁盘...

    在Shell脚本中调用另一个脚本的三种方式讲解

    这里我们将详细介绍三种在Shell脚本中调用另一个脚本的方法:`fork`、`exec`和`source`。 1. **Fork方法**: Fork是最基本的方式,通过在脚本中直接调用`./foo.sh`或`path/to/foo.sh`来执行另一个脚本。这种方式会...

    [unix.v6.v7.源码].unix.v6.v7.src.source.code

    在`sys`和`proc`子目录中的源码,展示了如何使用系统调用来控制进程,如`fork()`、`exec()`和`wait()`等。 3. **内存管理**:这些早期版本的UNIX使用了页式虚拟内存管理,源码中的`vm`子目录包含了内存分配和页面...

    orange's os source code

    源码中会列出各种系统调用(如fork、exec、read、write等),以及它们如何被调用和实现。 7. **安全与权限管理**:这部分源码涉及用户和进程的权限设置、访问控制列表(ACL)和能力模型等,这些都是保证系统安全的...

    进程门神 源码 sourcecode

    1. **进程控制**:这通常涉及到使用操作系统提供的系统调用,如`fork()`用于创建新进程,`exec()`用于替换当前进程的执行体,`wait()`和`waitpid()`用于等待子进程结束,以及`kill()`用于发送信号到进程。...

    GNU/Linux环境编程第二版 源码

    4. **进程和线程管理**:`fork()`, `exec()`系列函数用于创建和替换进程,`wait()`和`waitpid()`用于等待子进程结束。多线程编程中,`pthread_create()`、`pthread_join()`和互斥锁(`pthread_mutex_t`)等用于线程的...

    猪哥的嵌入式linux公房菜

    - **进程管理**:fork、exec、wait等。 **4. 主流嵌入式Linux动态扩展技术比较分析** - **动态加载**:按需加载模块。 - **热插拔技术**:设备即插即用的支持。 **5. Linux动态库剖析** - **加载机制**:动态链接...

    gdb命令速查1

    3. **同时调试父进程和子进程**:`set follow-fork-mode mode`,mode可以是parent或child。 4. **查看线程信息**:`info threads`。 5. **打印所有线程堆栈**:`thread apply all bt`。 6. **Solaris上的线程信息**...

    NodeJs高级编程英文版

    5. **进程和子进程(Process and Child Process)**:用于管理和创建子进程,如`spawn`、`exec`和`fork`。 **三、Node.js进阶技术** 1. **中间件(Middleware)**:如Express框架中的中间件,用于构建web应用。 2. **...

    Linux系统下C编程入门

    - **fork()**: 创建一个新的进程,新进程称为子进程,原始进程称为父进程。 - **exec()**: 用来替换当前进程的映像,但不会创建新的进程。 #### 三、文件操作 文件操作是任何程序的重要组成部分,Linux系统提供了...

    linux操作系统下c语言编程入门与提高

    - **进程创建**:在Linux中,可以使用`fork()`创建新进程,`exec()`家族函数加载新的程序。 - **进程通信**:包括管道、信号量、共享内存、消息队列等方法,允许进程间交换数据。 5. **文件操作** - **标准I/O库...

    unix-os教学课件第六章unix系统编程基础-automake.pptx

    - `fork()`, `exec()`, `wait()`: 进程管理。 - `mmap()`, `munmap()`: 内存映射。 - **常用库函数**: - `malloc()`, `free()`: 内存分配。 - `strlen()`, `strcat()`: 字符串操作。 - `time()`, `sleep()`: ...

    Linux C编程一站式学习

    10. **进程与线程**:理解Linux下的进程和线程概念,使用fork、exec、wait等函数创建和管理进程,使用pthread库创建和同步线程。 通过深入学习以上内容,你将能够熟练地在Linux环境下进行C编程,实现各种功能,解决...

Global site tag (gtag.js) - Google Analytics