ch02:進程

 
第二講 進程
內核跟蹤進程的下列信息
運行的位置
訪問的文件
信用狀(安全機制)
當前目錄
訪問的內存空間
1.進程的屬性
pid
       基本屬性pid(進程標識符)和ppid
       pid_t getpid() // 獲得本進程的進程id
       pid_t getppid() // 在子進程中執行它,獲得父進程的進程id
       舉例
       #include <stdio.h>
#include <sys/types.h>
 
int main(int argc, char*argv[])
{
              pid_t id = getpid();
              printf("this id num %d/n",id);
              return 0;
}
[root@localhost ch01]# gcc –o getpid getpid.c
[root@localhost ch01]# ./getpid
This id num 1991
 
信用狀(安全機制)
       etc/passwd、etc/group
       int setgroups(size_t num, const gid_t *list)
       int getgroups(size_t num, gid_t *lsit)
      
setuid/setgid和系統守護進程
       什麼是守護進程
       real uid、saved uid、effective uid
       int setreuid(uid_t ruid, uid_t euid) // BSD提出
       int setuid(uid_t euid) // Posix標準
uid和gid總結
       出錯返回-1,正確執行時返回0
在大部分函數原形在unistd.h中定義
int setreuid(uid_t ruid,uid_t euid) // 設置當前進程的真實用戶標示符爲ruid,以及進程的有效// 用戶標示符爲euid
int setrgid(gid_t rgid, gid_t egid) // 設置當前進程的真實組標示符爲ruid,以及進程的有效組
//標示符爲euid
 
int setuid(uid_t uid) // 如果是普通用戶調用,則將進程的有效用戶標示符設置爲uid
                     // 如果是root用戶調用,則將真實、有效和已保存的用戶標示符設置爲uid
itn setgid(gid_t gid) // 如果是普通用戶調用,則將進程的有效用戶組標示符設置爲uid
                     // 如果是root用戶調用,則將真實、有效和已保存的用戶組標示符設置爲uid
int seteuid(uid_t gid) 等價於setreuid(-1,euid)
int setegid(gid_t gid) 等價於setrgid(-1,egid)
int setgroups(size_t num, const gid_t *list) // 把當前進程的補充組設爲list
   函數原型在grp.h中
uid_t getuid() // 返回進程的真實用戶標示符
uid_t geteuid() // 返回進程的有效用戶標示符
gid_t getgid() // 返回進程的真實組標示符
gid_t getegid() // 返回進程的有效組標示符
size_t getgroups(size_t size, gid_t list[]) // 將當前進程的補充組返回到list中
函數原形在grp.h中
2.進程相關信息
程序參數
int main(int argc ,char *argv[])
extern char *environ[] // 全局變量,指向環境變量中的每個元素。聲明在<usrstd.h>中
const char *getenv(const char *name) // 如果這個值存在,返回指向全局變量中名字爲
// name值的指針,否則返回NULL
int putenv(const char *string) // Posix標準定義,具有比較好的移植性
int setenv(const char *name, const char *value, int overwrite) // BSD定義
       例:putenv(“PATH=/bin:/usr/bin”)
              setenv(“PATH”,”/bin:/usr/bin”,1)
資源使用
       int getruseage(int who ,strcut rusage *usage)
       who–RUSAGE_SELF
               RUSAGE_CHILDREN
            RUSAGE_BOTH
       #include <sys/resource.h>
       struct rusage{
        struct timeval ru_utime; // 執行用戶代碼所用的時間,包括運行用戶代碼指定的所有
//時間,不包括內核用來完成應用程序請求的
        struct timeval ru_stime; //內核用於系統請求的全部時間,其中不包括在系統調用時
//進程阻塞所花的時間
        long int ru_minflt; // 進程所造成的次要缺陷數
      long int ru_majflt; // 進程照成的主要缺陷數
      long int ru_nswap; // 進程的訪問而從磁盤調用內存的頁面數
      ……......
}
建立使用限制
       int getrlimit(int resource ,struct rlimit *rlim)
       int setrlimit(int resource,const struct rlimit *rlim)
       struct rlimit
{
              long int rlim_cur; // 軟限制值是多少
              long int rlim_max; // 應限制是多少
}
RLIMIT_AS // 進程處於內存的最大數量
RLIMIT_CORE // 由內核生成的core文件的最大大小
RLIMIT_CPU // 全部cpu時間
RLIMIT_DATA // 數據存儲的最大容量
RLIMIT_FSIZE // 打開文件的最大數目
RLIMIT_MEMLOCK
RLIMIT_NOFILE // 打開文件的最大數
RLIMIT_NPROC // 進程可以產生的最大子進程數目
RLIMIT_RSS // 可以隨時使用的內存容量
RLIMIT_STACK // 堆棧存儲區的最大容量
3.進程基本元素
創建子進程
       #include <unistd.h>
       pid_t fork();
       特別之處:返回兩次
       舉例
       #include <sys/types.h>
#include <stdio.h>
#include <unistd.h>
 
int main(void)
{
              pid_t child;
if (!(child=fork()))
              {
                     printf("/nin child/n");
                     _exit(0);
              }
              printf("in parent -- child is %d/n",child);
              return 0;
}
[root@localhost ch01]# gcc –o forkd forkd.c
[root@localhost ch01]# ./forkd
 
in child
in parent – child is 1918
等待子進程結束
       pid_t wait4(pid_t pid, int *status, int options, struct rusage *rusage);
WIFEXITED(status) //是否正常退出 WEXITSTATUS(status) //返回進程的退出代碼
WISIGNALED(status) //是否被信號終止   WTERMSIG(status) // 終止進程的信號的號碼
       WIFSTOPPED(status)//進程已被信號終止 WSTOPSIG(status) //返回停止進程的信號
       pid_t wait(int *status)
       pid_t waitpid(pid_t pid, int *status, int options)
       pid_t wait3(int *status, int options ,strcut rusage rusage)
運行新進程
       int execl(const char *path, const char *arg0,….);
       int execlp(const char *file, const char *arg0,…);
       int execle(const char *path, const char *arg0,…);
       int execv(const char *path, const char **argv);
       int execvp(const char *file, const char **argv);
       int execve(const char *file, const char **argv);
       運行成功沒有返回;失敗返回-1
       execl(“/bin/cat”,”/bin/cat”,”/etc/passwd”, ”/etc/group”, NULL);
       char * argv[] = {“./cat”, ”/etc/passwd”, “/etc/group”, NULL};
       execv(“/bin/cat”, argv);
       char *newenv[] = {“PATH = /bin:/usr/bin”,”HOME=/home/sweethome”,NULL}
       execle(“/usr/bin/env”, ”/usr/bin/env”, NULL, newenv);
       char *argv[]={“/usr/bin/env”, NULL};
       char *newenv[]={“PATH=/bin:usr/bin”, ”HOME=/home/sweethome”, NULL}
       execve(“/usr/bin/env”, argv, newenv);
       execlp(“cat”, “cat”, “/etc/passwd”, “/etc/group”, NULL);
       char *argv[]={“./cat”, “/etc/passwd”, “/etc/group”, NULL};
       execvp(“cat”, argv);
終止
       void exit(int exitcode);
       void _exit(int exitcode);
       int kill(pid_t pid, int signum);
4.簡單子進程
system()
       int system(const char *cmd) // 首先fork一個exec系列的函數,在這個中運行了一個shell的子程序,然後用這個shell運行cmd命令。原來的程序等待子進程退出,然後返回類似於wait函數的返回。
       /bin/sh
       示例
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/wait.h>
 
int main()
{
              int result;
              result = system("exec ls -l");
              if (!WIFEXITED(result)){
                     printf("abnormal exit/n");
              }
              return 0;
}
[root@localhost ch01]# gcc –o testsystem testsystem.c
[root@localhost ch01]# ./testsystem
總用量 304
-rwx------    1 root     root        11791 5月 16 22:10 a.out
-rwx------    1 root     root          162 5月 21 21:50 ~$ch02.doc
-rwx------    1 root     root        95232 5月 21 21:57 ch02.doc
-rwx------    1 root     root        11791 5月 16 22:11 forkd
-rwx------    1 root     root          218 5月 16 22:09 forkd.c
-rwx------    1 root     root        11649 5月 10 20:32 getpid
-rwx------    1 root     root          144 5月 10 20:32 getpid.c
-rwx------    1 root     root        11693 5月 21 22:05 testsystem
-rwx------    1 root     root          211 5月 21 22:05 testsystem.c
-rwx------    1 root     root            0 5月 21 22:06 test.tmp
-rwx------    1 root     root        94720 5月 16 22:45 ~WRL0001.tmp
-rwx------    1 root     root        94208 5月 21 21:50 ~WRL0003.tmp
-rwx------    1 root     root        94208 5月 21 21:52 ~WRL0005.tmp
-rwx------    1 root     root        95232 5月 21 21:56 ~WRL2785.tmp
-rwx------    1 root     root        94208 5月 21 21:52 ~WRL4030.tmp
從進程讀或寫
FILE *popen(const char *cmd, const char *mode)
int pclose(FILE *stream);
5.會話和進程組
會話
控制終端
進程組
孤兒進程組
發佈了27 篇原創文章 · 獲贊 0 · 訪問量 7萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章