身体里没什么可放的。
答案1
进程需要有一个父进程 (PPID)。尽管内核不是一个真正的进程,但它仍然手工制作了一些真实的进程,例如至少是 init,并且给自己提供了进程 ID 0。根据操作系统的不同,它可能会也可能不会在ps
输出中显示为进程,但始终会显示作为 PPID:
例如在 Linux 上:
$ ps -ef|head
UID PID PPID C STIME TTY TIME CMD
root 1 0 0 09:09 ? 00:00:00 /sbin/init
root 2 0 0 09:09 ? 00:00:00 [kthreadd]
root 3 2 0 09:09 ? 00:00:00 [ksoftirqd/0]
...
在 Solaris 上:
$ ps -ef|head
UID PID PPID C STIME TTY TIME CMD
root 0 0 0 Oct 19 ? 0:01 sched
root 5 0 0 Oct 19 ? 11:20 zpool-rpool1
root 1 0 0 Oct 19 ? 0:13 /sbin/init
root 2 0 0 Oct 19 ? 0:07 pageout
root 3 0 1 Oct 19 ? 117:10 fsflush
root 341 1 0 Oct 19 ? 0:15 /usr/lib/hal/hald --daemon=yes
root 9 1 0 Oct 19 ? 0:59 /lib/svc/bin/svc.startd
...
另请注意, pid 0
(以及-1
与此相关的其他负值)具有不同的含义,具体取决于使用它们的函数,例如kill
,fork
和waitpid
。
最后,虽然init
进程传统上是给定 pid 的#1
,但当像 Solaris 区域那样使用操作系统级虚拟化时,情况就不再是这样了,因为可以有多个进程init
在运行:
$ ps -ef|head
UID PID PPID C STIME TTY TIME CMD
root 4733 3949 0 11:07:25 ? 0:26 /lib/svc/bin/svc.configd
root 4731 3949 0 11:07:24 ? 0:06 /lib/svc/bin/svc.startd
root 3949 3949 0 11:07:14 ? 0:00 zsched
daemon 4856 3949 0 11:07:46 ? 0:00 /lib/crypto/kcfd
root 4573 3949 0 11:07:23 ? 0:00 /usr/sbin/init
netcfg 4790 3949 0 11:07:34 ? 0:00 /lib/inet/netcfgd
root 4868 3949 0 11:07:48 ? 0:00 /usr/lib/pfexecd
root 4897 3949 0 11:07:51 ? 0:00 /usr/lib/utmpd
netadm 4980 3949 0 11:07:54 ? 0:01 /lib/inet/nwamd
答案2
有两个任务具有特殊的进程 ID:swapper 或 sched 具有进程 ID 0,负责分页,就像前面示例中的 jlliagre 一样,实际上是内核的一部分,而不是普通的用户模式进程。
进程ID 1通常是init进程,主要负责启动和关闭系统。最初,进程 ID 1 并没有通过任何技术措施专门为 init 保留:它只是作为内核调用的第一个进程的自然结果而具有此 ID。较新的 Unix 系统通常具有可视为“进程”的附加内核组件,在这种情况下,PID 1 会主动保留给 init 进程,以保持与旧系统的一致性。
答案3
一般来说,0 经常用来表示“空引用”。这意味着即使 0 值存在,您也可能不会使用它,因为您希望零表示特殊值。